From 1fd361a1ea06e44286c213ca1f814f49306fdc43 Mon Sep 17 00:00:00 2001 From: giraffedata Date: Sat, 19 Aug 2006 03:12:28 +0000 Subject: Create Subversion repository git-svn-id: http://svn.code.sf.net/p/netpbm/code/trunk@1 9d0c8265-081b-0410-96cb-a4ca84ce46f8 --- converter/other/cameratopam/ljpeg.c | 141 ++++++++++++++++++++++++++++++++++++ 1 file changed, 141 insertions(+) create mode 100644 converter/other/cameratopam/ljpeg.c (limited to 'converter/other/cameratopam/ljpeg.c') diff --git a/converter/other/cameratopam/ljpeg.c b/converter/other/cameratopam/ljpeg.c new file mode 100644 index 00000000..18423f4f --- /dev/null +++ b/converter/other/cameratopam/ljpeg.c @@ -0,0 +1,141 @@ +#define _BSD_SOURCE /* Make sure string.h containst strcasecmp() */ +#include +#include +#include +#include + +#include "pm.h" + +#include "global_variables.h" +#include "util.h" +#include "decode.h" +#include "bayer.h" + +#include "ljpeg.h" + + +/* + Not a full implementation of Lossless JPEG, just + enough to decode Canon, Kodak and Adobe DNG images. + */ + +int +ljpeg_start (FILE * ifp, struct jhead *jh) +{ + int i, tag, len; + unsigned char data[256], *dp; + + init_decoder(); + for (i=0; i < 4; i++) + jh->huff[i] = free_decode; + fread (data, 2, 1, ifp); + if (data[0] != 0xff || data[1] != 0xd8) return 0; + do { + fread (data, 2, 2, ifp); + tag = data[0] << 8 | data[1]; + len = (data[2] << 8 | data[3]) - 2; + if (tag <= 0xff00 || len > 255) return 0; + fread (data, 1, len, ifp); + switch (tag) { + case 0xffc3: + jh->bits = data[0]; + jh->high = data[1] << 8 | data[2]; + jh->wide = data[3] << 8 | data[4]; + jh->clrs = data[5]; + break; + case 0xffc4: + for (dp = data; dp < data+len && *dp < 4; ) { + jh->huff[*dp] = free_decode; + dp = make_decoder (++dp, 0); + } + } + } while (tag != 0xffda); + jh->row = calloc (jh->wide*jh->clrs, 2); + if (jh->row == NULL) + pm_error("Out of memory in ljpeg_start()"); + for (i=0; i < 4; i++) + jh->vpred[i] = 1 << (jh->bits-1); + zero_after_ff = 1; + getbits(ifp, -1); + return 1; +} + +int +ljpeg_diff (struct decode *dindex) +{ + int len, diff; + + while (dindex->branch[0]) + dindex = dindex->branch[getbits(ifp, 1)]; + diff = getbits(ifp, len = dindex->leaf); + if ((diff & (1 << (len-1))) == 0) + diff -= (1 << len) - 1; + return diff; +} + +void +ljpeg_row (struct jhead *jh) +{ + int col, c, diff; + unsigned short *outp=jh->row; + + for (col=0; col < jh->wide; col++) + for (c=0; c < jh->clrs; c++) { + diff = ljpeg_diff (jh->huff[c]); + *outp = col ? outp[-jh->clrs]+diff : (jh->vpred[c] += diff); + outp++; + } +} + +void +lossless_jpeg_load_raw(void) +{ + int jwide, jrow, jcol, val, jidx, i, row, col; + struct jhead jh; + int min=INT_MAX; + + if (!ljpeg_start (ifp, &jh)) return; + jwide = jh.wide * jh.clrs; + + for (jrow=0; jrow < jh.high; jrow++) { + ljpeg_row (&jh); + for (jcol=0; jcol < jwide; jcol++) { + val = curve[jh.row[jcol]]; + jidx = jrow*jwide + jcol; + if (raw_width == 5108) { + i = jidx / (1680*jh.high); + if (i < 2) { + row = jidx / 1680 % jh.high; + col = jidx % 1680 + i*1680; + } else { + jidx -= 2*1680*jh.high; + row = jidx / 1748; + col = jidx % 1748 + 2*1680; + } + } else if (raw_width == 3516) { + row = jidx / 1758; + col = jidx % 1758; + if (row >= raw_height) { + row -= raw_height; + col += 1758; + } + } else { + row = jidx / raw_width; + col = jidx % raw_width; + } + if ((unsigned) (row-top_margin) >= height) continue; + if ((unsigned) (col-left_margin) < width) { + BAYER(row-top_margin,col-left_margin) = val; + if (min > val) min = val; + } else + black += val; + } + } + free (jh.row); + if (raw_width > width) + black /= (raw_width - width) * height; + if (!strcasecmp(make,"KODAK")) + black = min; +} + + -- cgit 1.4.1