/*
* Copyright (C) 2001, Novell Inc.
+ * Copyright (C) 2010 Kevin O'Connor <kevin@koconnor.net>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
unsigned char quant[4][64];
struct dec_hufftbl dhuff[4];
struct in in;
+
+ int height, width;
};
static int getbyte(struct jpeg_decdata *jpeg)
return jpeg;
}
-int jpeg_check_size(struct jpeg_decdata *jpeg, unsigned char *buf
- , int width, int height)
-{
- jpeg->datap = buf;
- getbyte(jpeg);
- getbyte(jpeg);
- readtables(jpeg, M_SOF0);
- getword(jpeg);
- getbyte(jpeg);
- if (height != getword(jpeg) || width != getword(jpeg))
- return 0;
- return 1;
-}
-
-int jpeg_decode(unsigned char *buf, unsigned char *pic,
- int width, int height, int depth,
- struct jpeg_decdata *jpeg)
+int jpeg_decode(struct jpeg_decdata *jpeg, unsigned char *buf)
{
int i, j, m, tac, tdc;
- int mcusx, mcusy, mx, my;
- int max[6];
- if (!jpeg || !buf || !pic)
+ if (!jpeg || !buf)
return -1;
jpeg->datap = buf;
if (getbyte(jpeg) != 0xff)
i = getbyte(jpeg);
if (i != 8)
return ERR_NOT_8BIT;
- if (((getword(jpeg) + 15) & ~15) != height)
- return ERR_HEIGHT_MISMATCH;
- if (((getword(jpeg) + 15) & ~15) != width)
- return ERR_WIDTH_MISMATCH;
- if ((height & 15) || (width & 15))
+ jpeg->height = getword(jpeg);
+ jpeg->width = getword(jpeg);
+ if ((jpeg->height & 15) || (jpeg->width & 15))
return ERR_BAD_WIDTH_OR_HEIGHT;
jpeg->info.nc = getbyte(jpeg);
if (jpeg->info.nc > MAXCOMP)
|| jpeg->dscans[2].hv != 0x11)
return ERR_NOT_YCBCR_221111;
- mcusx = width >> 4;
- mcusy = height >> 4;
-
-
idctqtab(jpeg->quant[jpeg->dscans[0].tq], jpeg->dquant[0]);
idctqtab(jpeg->quant[jpeg->dscans[1].tq], jpeg->dquant[1]);
idctqtab(jpeg->quant[jpeg->dscans[2].tq], jpeg->dquant[2]);
dec_initscans(jpeg);
+ return 0;
+}
+
+void jpeg_get_size(struct jpeg_decdata *jpeg, int *width, int *height)
+{
+ *width = jpeg->width;
+ *height = jpeg->height;
+}
+
+int jpeg_show(struct jpeg_decdata *jpeg, unsigned char *pic, int width
+ , int height, int depth, int bytes_per_line_dest)
+{
+ int m, mcusx, mcusy, mx, my, mloffset, jpgbpl;
+ int max[6];
+
+ if (jpeg->height != height)
+ return ERR_HEIGHT_MISMATCH;
+ if (jpeg->width != width)
+ return ERR_WIDTH_MISMATCH;
+
+ jpgbpl = width * depth / 8;
+ mloffset = bytes_per_line_dest > jpgbpl ? bytes_per_line_dest : jpgbpl;
+
+ mcusx = jpeg->width >> 4;
+ mcusy = jpeg->height >> 4;
+
jpeg->dscans[0].next = 6 - 4;
jpeg->dscans[1].next = 6 - 4 - 1;
jpeg->dscans[2].next = 6 - 4 - 1 - 1; /* 411 encoding */
IFIX(128.5), max[0]);
idct(jpeg->dcts + 64, jpeg->out + 64, jpeg->dquant[0],
IFIX(128.5), max[1]);
- idct(jpeg->dcts + 128, jpeg->out + 128,
- jpeg->dquant[0], IFIX(128.5), max[2]);
- idct(jpeg->dcts + 192, jpeg->out + 192,
- jpeg->dquant[0], IFIX(128.5), max[3]);
- idct(jpeg->dcts + 256, jpeg->out + 256,
- jpeg->dquant[1], IFIX(0.5), max[4]);
- idct(jpeg->dcts + 320, jpeg->out + 320,
- jpeg->dquant[2], IFIX(0.5), max[5]);
+ idct(jpeg->dcts + 128, jpeg->out + 128, jpeg->dquant[0],
+ IFIX(128.5), max[2]);
+ idct(jpeg->dcts + 192, jpeg->out + 192, jpeg->dquant[0],
+ IFIX(128.5), max[3]);
+ idct(jpeg->dcts + 256, jpeg->out + 256, jpeg->dquant[1],
+ IFIX(0.5), max[4]);
+ idct(jpeg->dcts + 320, jpeg->out + 320, jpeg->dquant[2],
+ IFIX(0.5), max[5]);
switch (depth) {
case 32:
col221111_32(jpeg->out,
- pic + (my * 16 * mcusx + mx) * 16 * 4,
- mcusx * 16 * 4);
+ pic + (my * 16 * mloffset + mx * 16 * 4),
+ mloffset);
break;
case 24:
col221111(jpeg->out,
- pic + (my * 16 * mcusx + mx) * 16 * 3,
- mcusx * 16 * 3);
+ pic + (my * 16 * mloffset + mx * 16 * 3),
+ mloffset);
break;
case 16:
col221111_16(jpeg->out,
- pic + (my * 16 * mcusx + mx) * (16 * 2),
- mcusx * (16 * 2));
+ pic + (my * 16 * mloffset + mx * 16 * 2),
+ mloffset);
break;
default:
return ERR_DEPTH_MISMATCH;
#endif
+#ifdef __LITTLE_ENDIAN
+#define PIC(yin, xin, p, xout) \
+( \
+ y = outy[(yin) * 8 + xin], \
+ STORECLAMP(p[(xout) * 3 + 2], y + cr), \
+ STORECLAMP(p[(xout) * 3 + 1], y - cg), \
+ STORECLAMP(p[(xout) * 3 + 0], y + cb) \
+)
+#else
#define PIC(yin, xin, p, xout) \
( \
y = outy[(yin) * 8 + xin], \
STORECLAMP(p[(xout) * 3 + 1], y - cg), \
STORECLAMP(p[(xout) * 3 + 2], y + cb) \
)
+#endif
#ifdef __LITTLE_ENDIAN
#define PIC_16(yin, xin, p, xout, add) \