2008-09-12 12:23:09     Faster JPEG encoding - files attached

Document created by Aaronwu Employee on Aug 9, 2013
Version 1Show Document
  • View in full screen mode

2008-09-12 12:23:09     Faster JPEG encoding - files attached

Frank Van Hooft (CANADA)

Message: 62061   

 

I'd been wanting to speed up JPEG encoding on the blackfin. Initially I'd been using FFMPEG, and it's fast thanks to the optimisations coded by the ADI folks. But FFMPEG caused me troubles due to its constant malloc'ing & free'ing of memory; over time I was getting Out Of Memory failures due to memory fragmentation. So I turned to the LIBJPEG library, which is much simpler, but slower due to not being optimised.

 

The bulk of the time in JPEG encoding is spent in the DCT algorithm. libjpeg ships with 3 different DCT implementations; float, accurate integer, fast integer, all coded in C. I recoded the fast integer routine, jfdctfst.c, into blackfin assembler. The new file, attached, is jfdctfst_bfin.S. The new function name is jfdctfst_bfin

 

Cycle counts (measured by me on a BF537) are:

 

Original jfdctfst.c function:        2507 cycles

New jfdctfst_bfin.S function:      1058 cycles

 

Also attached is a slightly edited Makefile containing a rule for building the .S file.

 

To try this new function, do the following:

 

1) Copy the two attached files into your libjpeg directory. The Makefile will overwrite the existing Makefile; you may want to make a copy of your original first.

 

2) Call the new function. I did it by editing the jfdctfst.c file so it calls the jfdctfst_bfin function instead. This might not be the most elegant, but it works. Add the following function prototype to the jfdctfst.c file:

 

     void jfdctfst_bfin (DCTELEM *buf);

 

Then call the new assembler function at the beginning of the jpeg_fdct_ifast function:

 

     jfdctfst_bfin (data);

     return;

 

So now, when your libjpeg application calls the fast integer DCT routine, it's actually using the assembler version.

 

 

 

Some final notes. I'm not making any guarantees on this code. All I can say is, it works for me. I've tested it as best I can by feeding sample vectors through it, comparing the results to the original .c source, and it appears correct. JPEG images produced also appear correct. I'm sure it's not optimally fast - no doubt a smarter brain than mine can improve on this. But it's a big improvement over the C version - good enough for me. Enjoy.

 

 

 

 

 

Makefile

jfdctfst_bfin.S

QuoteReplyEditDelete

 

 

2008-09-12 15:24:41     Re: Faster JPEG encoding - files attached

Robin Getz (UNITED STATES)

Message: 62076   

 

Frank:

 

Thanks. The person (Tom) who was looking at putting the optimized Blackfin code into libjpeg - is still planning on doing this - I think he was just stuck with a few things, and got bumped onto something else for a bit. Hopefully between what he has, and what you have done, we can get things that work, which are fast.

 

Thanks again.

 

-Robin

QuoteReplyEditDelete

 

 

2008-09-15 23:32:59     Re: Faster JPEG encoding - files attached

Sonic Zhang (CHINA)

Message: 62199   

 

Recorded in patch tracker.

 

http://blackfin.uclinux.org/gf/project/uclinux-dist/tracker/?action=TrackerItemEdit&tracker_item_id=4424

QuoteReplyEditDelete

 

 

2008-12-05 01:42:14     Re: Faster JPEG encoding - files attached

andy (UNITED STATES)

Message: 66375   

 

I followed the instructions. Upon make I get the following error messages:

 

cc    -c -o jfdctfst_bfin.o jfdctfst_bfin.S

jfdctfst_bfin.S: Assembler messages:

jfdctfst_bfin.S:157: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:167: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:169: Error: missing ']'

jfdctfst_bfin.S:169: Error: junk at end of line, first unrecognized character is `@'

jfdctfst_bfin.S:178: Error: no such instruction: `lsetup (.rowtop,.rowend)LC0=P1>>1'

jfdctfst_bfin.S:209: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:210: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:211: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:212: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:213: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:214: Error: bad expression

jfdctfst_bfin.S:214: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:215: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:216: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:217: Error: bad expression

jfdctfst_bfin.S:217: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:230: Error: bad expression

jfdctfst_bfin.S:230: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:240: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:241: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:251: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:252: Error: no such instruction: `r4 >>>=8'

jfdctfst_bfin.S:254: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:255: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:266: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:277: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:278: Error: bad expression

jfdctfst_bfin.S:278: Error: missing ')'

jfdctfst_bfin.S:278: Error: junk at end of line, first unrecognized character is `R'

jfdctfst_bfin.S:279: Error: no such instruction: `r6 >>>=8'

jfdctfst_bfin.S:280: Error: no such instruction: `r7 >>>=8'

jfdctfst_bfin.S:281: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:282: Error: no such instruction: `r0 <<=8'

jfdctfst_bfin.S:292: Error: bad expression

jfdctfst_bfin.S:292: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:302: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:303: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:304: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:305: Error: invalid character '[' in mnemonic

jfdctfst_bfin.S:311: Error: no such instruction: `p0 +=32'

jfdctfst_bfin.S:323: Error: no such instruction: `lsetup (.coltop,.colend)LC0=P1>>1'

jfdctfst_bfin.S:340: Error: no such instruction: `p0 +=32'

jfdctfst_bfin.S:342: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:343: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:344: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:345: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:360: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:361: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:362: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:363: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:364: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:365: Error: bad expression

jfdctfst_bfin.S:365: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:366: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:367: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:368: Error: bad expression

jfdctfst_bfin.S:368: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:382: Error: bad expression

jfdctfst_bfin.S:382: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:390: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:391: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:401: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:402: Error: no such instruction: `r4 >>>=8'

jfdctfst_bfin.S:403: Error: no such instruction: `r1 >>>=16'

jfdctfst_bfin.S:404: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:405: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:406: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:407: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:408: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:420: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:430: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:431: Error: bad expression

jfdctfst_bfin.S:431: Error: missing ')'

jfdctfst_bfin.S:431: Error: junk at end of line, first unrecognized character is `R'

jfdctfst_bfin.S:432: Error: no such instruction: `r6 >>>=8'

jfdctfst_bfin.S:433: Error: no such instruction: `r7 >>>=8'

jfdctfst_bfin.S:434: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:435: Error: no such instruction: `r0 <<=8'

jfdctfst_bfin.S:445: Error: bad expression

jfdctfst_bfin.S:445: Error: junk at end of line, first unrecognized character is `,'

jfdctfst_bfin.S:459: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:460: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:461: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:462: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:463: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:464: Error: junk at end of line, first unrecognized character is `='

jfdctfst_bfin.S:465: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:466: Error: junk at end of line, first unrecognized character is `['

jfdctfst_bfin.S:471: Error: junk at end of line, first unrecognized character is `('

jfdctfst_bfin.S:472: Error: no such instruction: `rts'

make: *** [jfdctfst_bfin.o] Error 1

 

How should I get it compile?

 

QuoteReplyEditDelete

 

 

2008-12-05 01:52:27     Re: Faster JPEG encoding - files attached

Yi Li (CHINA)

Message: 66376   

 

Andy,

 

Please use blackfin toolchain to build (e.g, the bfin-uclinux-gcc).

 

-Yi

QuoteReplyEditDelete

 

 

2009-06-09 21:19:09     Re: Faster JPEG encoding - files attached

Frank Van Hooft (CANADA)

Message: 75417   

 

I know this is an old thread, but presumably I'm not the only one needing a faster JPG encoder.

 

The clever folks over at Surveyor robots www.surveyor.com wrote a pretty good JPEG encoder. I took their code, added RGB support, and did a number of optimizations. The bottom line is that for my test image, libjpeg with the fast DCT takes around 260 ms. This new code takes 96 ms.  It produces results visually identical (as far as I can see, and I've certainly looked) to libjpeg.

 

It's a real credit to the surveyor code that we were able to get it running so fast.

 

You can find the code in the surveyor forums. You might find it easier to pull it off my website here:

 

blog.frankvh.com/2009/06/09/blackfin-fast-jpeg-encoding/

 

simply because I also provide instructions on how to use it.

 

Hopefully this will benefit someone else.

QuoteReplyEditDelete

 

 

2009-06-09 21:29:39     Re: Faster JPEG encoding - files attached

Mike Frysinger (UNITED STATES)

Message: 75419   

 

we've integrated optimized dct into the libjpeg in the trunk/2009R1 svn branches

Attachments

Outcomes