📄 ov511_decomp.c
字号:
/*****************
**** IDCT 1D ****
*****************/
#define IDCT_1D(c0, c1, c2, c3, in) \
do { \
tmp1=((c0)*DeZigZag[in])+((c2)*DeZigZag[(in)+2]); \
tmp2=(c1)*DeZigZag[(in)+1]; \
tmp3=(c3)*DeZigZag[(in)+3]; \
} while (0)
#define COMPOSE_1(out1, out2) \
do { \
tmp=tmp1+tmp2+tmp3; \
temp[out1] = tmp>>15; \
tmp=tmp1-tmp2-tmp3; \
temp[out2] = tmp>>15; \
} while (0)
#define COMPOSE_2(out1, out2) \
do { \
tmp=tmp1+tmp2-tmp3; \
temp[out1] = tmp>>15; \
tmp=tmp1-tmp2+tmp3; \
temp[out2] = tmp>>15; \
} while (0)
/* j = 0 */
IDCT_1D(a, b, c, d, 0); COMPOSE_1( 0, 56);
IDCT_1D(a, b, c, d, 8); COMPOSE_1( 1, 57);
IDCT_1D(a, b, c, d, 16); COMPOSE_1( 2, 58);
IDCT_1D(a, b, c, d, 24); COMPOSE_1( 3, 59);
/* j = 1 */
IDCT_1D(a, d, f, g, 0); COMPOSE_2( 8, 48);
IDCT_1D(a, d, f, g, 8); COMPOSE_2( 9, 49);
IDCT_1D(a, d, f, g, 16); COMPOSE_2(10, 50);
IDCT_1D(a, d, f, g, 24); COMPOSE_2(11, 51);
/* j = 2 */
IDCT_1D(a, e, -f, b, 0); COMPOSE_2(16, 40);
IDCT_1D(a, e, -f, b, 8); COMPOSE_2(17, 41);
IDCT_1D(a, e, -f, b, 16); COMPOSE_2(18, 42);
IDCT_1D(a, e, -f, b, 24); COMPOSE_2(19, 43);
/* j = 3 */
IDCT_1D(a, g, -c, e, 0); COMPOSE_2(24, 32);
IDCT_1D(a, g, -c, e, 8); COMPOSE_2(25, 33);
IDCT_1D(a, g, -c, e, 16); COMPOSE_2(26, 34);
IDCT_1D(a, g, -c, e, 24); COMPOSE_2(27, 35);
#undef IDCT_1D
#undef COMPOSE_1
#undef COMPOSE_2
/*****************
**** IDCT 2D ****
*****************/
#define IDCT_2D(c0, c1, c2, c3, in) \
do { \
tmp = temp[in]*(c0) + temp[(in)+1]*(c1) \
+ temp[(in)+2]*(c2) + temp[(in)+3]*(c3); \
} while (0)
#define STORE(i) \
do { \
tmp = tmp >> 15; \
tmp = tmp + 128; \
if (tmp > 255) tmp = 255; \
if (tmp < 0) tmp = 0; \
pOut[i] = (unsigned char) tmp; \
} while (0)
#define IDCT_2D_ROW(in) \
do { \
IDCT_2D(a, b, c, d, in); STORE(0+out_idx); \
IDCT_2D(a, d, f, -g, in); STORE(1+out_idx); \
IDCT_2D(a, e, -f, -b, in); STORE(2+out_idx); \
IDCT_2D(a, g, -c, -e, in); STORE(3+out_idx); \
IDCT_2D(a, -g, -c, e, in); STORE(4+out_idx); \
IDCT_2D(a, -e, -f, b, in); STORE(5+out_idx); \
IDCT_2D(a, -d, f, g, in); STORE(6+out_idx); \
IDCT_2D(a, -b, c, -d, in); STORE(7+out_idx); \
} while (0)
#define IDCT_2D_FAST(c0, c1, c2, c3, in) \
do { \
tmp1=((c0)*temp[in])+((c2)*temp[(in)+2]); \
tmp2=(c1)*temp[(in)+1]; \
tmp3=(c3)*temp[(in)+3]; \
} while (0)
#define STORE_FAST_1(out1, out2) \
do { \
tmp=tmp1+tmp2+tmp3; \
STORE((out1)+out_idx); \
tmp=tmp1-tmp2-tmp3; \
STORE((out2)+out_idx); \
} while (0)
#define STORE_FAST_2(out1, out2) \
do { \
tmp=tmp1+tmp2-tmp3; \
STORE((out1)+out_idx); \
tmp=tmp1-tmp2+tmp3; \
STORE((out2)+out_idx); \
} while (0)
#define IDCT_2D_FAST_ROW(in) \
do { \
IDCT_2D_FAST(a, b, c, d, in); STORE_FAST_1(0, 7); \
IDCT_2D_FAST(a, d, f, g, in); STORE_FAST_2(1, 6); \
IDCT_2D_FAST(a, e, -f, b, in); STORE_FAST_2(2, 5); \
IDCT_2D_FAST(a, g, -c, e, in); STORE_FAST_2(3, 4); \
} while (0)
out_idx = out_pos;
IDCT_2D_ROW(0); out_idx += w;
IDCT_2D_ROW(8); out_idx += w;
IDCT_2D_ROW(16); out_idx += w;
IDCT_2D_ROW(24); out_idx += w;
IDCT_2D_ROW(32); out_idx += w;
IDCT_2D_ROW(40); out_idx += w;
IDCT_2D_FAST_ROW(48); out_idx += w;
IDCT_2D_FAST_ROW(56);
*iIn = in_pos;
*iOut = out_pos + 8;
}
#define DECOMP_Y() DecompressYHI(pIn, pY, &iIn, &iY, w, 1)
#define DECOMP_U() DecompressYHI(pIn, pU, &iIn, &iU, w/2, 2)
#define DECOMP_V() DecompressYHI(pIn, pV, &iIn, &iV, w/2, 2)
inline static int
Decompress400HiNoMMX(unsigned char *pIn,
unsigned char *pOut,
const int w,
const int h,
const int inSize)
{
unsigned char *pY = pOut;
int x, y, iIn, iY;
iIn = 0;
for (y = 0; y < h; y += 8) {
iY = w*y;
for (x = 0; x < w; x += 8)
DECOMP_Y();
}
return 0;
}
inline static int
Decompress420HiNoMMX(unsigned char *pIn,
unsigned char *pOut,
const int w,
const int h,
const int inSize)
{
unsigned char *pY = pOut;
unsigned char *pU = pY + w*h;
unsigned char *pV = pU + w*h/4;
int xY, xUV, iY, iU, iV, iIn, count;
const int nBlocks = (w*h) / (32*8);
iIn = 0;
iY = iU = iV = 0;
xY = xUV = 0;
for (count = 0; count < nBlocks; count++) {
DECOMP_U();
DECOMP_V(); xUV += 16;
if (xUV >= w) {
iU += (w*7)/2;
iV += (w*7)/2;
xUV = 0;
}
DECOMP_Y(); xY += 8;
DECOMP_Y(); xY += 8;
if (xY >= w) {
iY += w*7;
xY = 0;
}
DECOMP_Y(); xY += 8;
DECOMP_Y(); xY += 8;
if (xY >= w) {
iY += w*7;
xY = 0;
}
}
return 0;
}
/* Input format is raw isoc. data (with header and packet
* number stripped, and all-zero blocks removed).
* Output format is YUV400
* Returns uncompressed data length if success, or zero if error
*/
static int
Decompress400(unsigned char *pIn,
unsigned char *pOut,
unsigned char *pTmp,
int w,
int h,
int inSize)
{
int numpix = w * h;
int rc;
PDEBUG(4, "%dx%d pIn=%p pOut=%p inSize=%d", w, h, pIn, pOut, inSize);
rc = Decompress400HiNoMMX(pIn, pOut, w, h, inSize);
if (rc)
return 0;
return numpix;
}
/* Input format is raw isoc. data (with header and packet
* number stripped, and all-zero blocks removed).
* Output format is planar YUV420
* Returns uncompressed data length if success, or zero if error
*/
static int
Decompress420(unsigned char *pIn,
unsigned char *pOut,
unsigned char *pTmp,
int w,
int h,
int inSize)
{
int numpix = w * h;
int rc;
PDEBUG(4, "%dx%d pIn=%p pOut=%p inSize=%d", w, h, pIn, pOut, inSize);
rc = Decompress420HiNoMMX(pIn, pOut, w, h, inSize);
if (rc)
return 0;
/* Disabled by Mark */
#if 0
/* For color saturation 8/22/00 */
{
long u , v;
unsigned char *pU = pOut + numpix;
unsigned char *pV = pU + numpix/4;
for (int i = 0; i < numpix/4; i++) {
u = (long)*pU;
v = (long)*pV;
u -= 128;
v -= 128;
u = (u * 577) >> 10;
v = (v * 730) >> 10;
u += 128;
v += 128;
*pU++ = (unsigned char)u;
*pV++ = (unsigned char)v;
/* u=0.564 */
/* v=0.713 */
}
}
#endif
return (numpix * 3 / 2);
}
/******************************************************************************
* Module Functions
******************************************************************************/
static struct ov51x_decomp_ops decomp_ops = {
.decomp_400 = Decompress400,
.decomp_420 = Decompress420,
.owner = THIS_MODULE,
};
static int __init
decomp_init(void)
{
int rc;
EXPORT_NO_SYMBOLS;
rc = ov511_register_decomp_module(DECOMP_INTERFACE_VER, &decomp_ops,
ov518, mmx);
if (rc) {
err("Could not register with ov511 (rc=%d)", rc);
return -1;
}
info(DRIVER_VERSION " : " DRIVER_DESC);
return 0;
}
static void __exit
decomp_exit(void)
{
ov511_deregister_decomp_module(ov518, mmx);
info("deregistered\n");
}
module_init(decomp_init);
module_exit(decomp_exit);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -