⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 decode.c

📁 jpeg快速算法,用于TI和philips的DSP开发
💻 C
字号:
/*
 *********************************************************************
 * File name: decode.c
 * Version: 5.0(release v1.0)    Date: Jan 12, 2006
 * Author:  xiezm                Email: xiezm@wxintech.cn
 * Company: Wuxi Intech co., ltd.
 *
 * Project: Jpeg Decoder for Trio
 *********************************************************************
 */
#define  DECODE_GLOBALS

#include "cf6_chess.h"

#include "djpg.h"
#include "bitstream.h"

#define DC 0
#define AC 1

//#define INT_P362 362
//#define INT_P473 473
//#define INT_P277 277
//#define INT_M669 (-669)


const int natural_order[DCT_SIZE2] =
{
	 0,  1,  8, 16,  9,  2,  3, 10,
	17, 24, 32, 25, 18, 11,  4,  5,
	12, 19, 26, 33, 40, 48, 41, 34,
	27, 20, 13,  6,  7, 14, 21, 28,
	35, 42, 49, 56, 57, 50, 43,	36,
	29, 22, 15, 23, 30, 37, 44, 51,
	58, 59, 52, 45, 38, 31, 39, 46,
	53,	60, 61, 54, 47, 55, 62, 63
};

int errorHuffman=0;

void decode_initial(void)
{
	int i;

	decode_bitstream_initial();

	for(i=0;i<MAX_COMPS;i++)
	{
		PreDC[i] = 0;
	}

	for(i=1;i<16;i++)
	{
		shift_std[i] = 1<<(i-1);
		shift_offset[i] = (((-1) << i) + 1);
	}

#if 0
	for(i=0;i<32;i++)
	{
		cellingR_tab[i] = 0;
		cellingG_tab[i] = 0;
		cellingB_tab[i] = 0;
	}
	for(i=0;i<64;i++)
	{
		cellingR_tab[i+32] = ((i>>1)<<11);
		cellingG_tab[i+32] = (i<<5);
		cellingB_tab[i+32] = (i>>1);
	}
	for(i=0;i<32;i++)
	{
		cellingR_tab[i+96] = 0x00F800;
		cellingG_tab[i+96] = 0x0007E0;
		cellingB_tab[i+96] = 0x00001F;
	}

	cellingR = &cellingR_tab[32];
	cellingG = &cellingG_tab[32];
	cellingB = &cellingB_tab[32];
#else 
	for(i=0;i<128;i++)
	{
		cellingR_tab1[i] = 0;
		cellingG_tab1[i] = 0;
		cellingB_tab1[i] = 0;
	}
	for(i=0;i<256;i++)
	{
		cellingR_tab1[i+128] = ((i>>3)<<11);
		cellingG_tab1[i+128] = ((i>>2)<<5);
		cellingB_tab1[i+128] = (i>>3);
	}
	for(i=0;i<128;i++)
	{
		cellingR_tab1[i+384] = 0x00F800;
		cellingG_tab1[i+384] = 0x0007E0;
		cellingB_tab1[i+384] = 0x00001F;
	}

	cellingR = &cellingR_tab1[128];
	cellingG = &cellingG_tab1[128];
	cellingB = &cellingB_tab1[128];

#endif



	restart_marker = 0;	
	
	INT_P454 = 454;
	INT_M88 = -88;
	INT_M183 = -183;
	INT_P359 = 359;
	
	INT_P362 = 362;
	INT_P473 = 473;
	INT_P277 = 277;
	INT_M669 = -669;
}

unsigned int de_huffman_cal()
{
	int l = 9;
	int code;

	code = get_bits(l);
	while (code > htbl->maxcode[l])
	{
		code <<= 1;
		code |= get_bits(1);
		l++;
	}

	if (l > 16)
	{
		errorHuffman = 15;
		return 0;//error(15);
		l = 16;			/* fake the result */
	}
	return (htbl->symbol[(unsigned int) (code + htbl->valoffset[l])]);
}

#if 1   //yover_optimize_0822
unsigned int de_huffman(void)
{
	unsigned int peek, nb;

	peek = peek_byte();
  	if ((nb = htbl->look_nbits[peek]) != 0) 
	{
		drop_bits(nb);
		return(htbl->look_sym[peek]);
	}
    return de_huffman_cal();
}
#else
#define de_huffman(dhfm)						\
{												\
	unsigned int peek, nb;						\
	peek = peek_byte();							\
  	if ((nb = htbl->look_nbits[peek]) != 0)		\
	{											\
		drop_bits(nb);							\
		dhfm = (htbl->look_sym[peek]);			\
	}											\
	else										\
		dhfm = de_huffman_cal();				\
}
#endif

void restart_decode(void)
{
	drop_bits(bits_left%8);		//sync
	if((0x00ff!=get_bits(8)) || ((get_bits(8) - RST0) != restart_marker))
	{
		error(17);
	}
	restart_marker++;
	restart_marker %= 8;
	PreDC[0] = 0;
	PreDC[1] = 0;
	PreDC[2] = 0;
}

void fast_IDCT(int rec_idx);

int decode_data_unit(int comp, int rec_idx)
{
	unsigned int bits;
	unsigned int RS;
	unsigned int SSSS;
	unsigned int RRRR;
	unsigned int K;
	int Diff;
	int iRet = 0;

	int chess_storage(YMEM) *qtbl;

	int *inptr;
	int *wsptr;
	int *outptr;
	
	int tmp0, tmp1, tmp2, tmp3, tmp4, tmp5, tmp6, tmp7;
	int tmp10, tmp11, tmp12, tmp13;
	int z5, z10, z11, z12, z13;

	
	/* decode DC */
	//cal Diff
	htbl = &dc_huff_tbl[Tdi[comp]];
	//yover_optimize_0822, de_huffman(bits);
	bits = de_huffman();//yover_optimize_0822, 
	if(errorHuffman==15)
	{
		return 15;
	}


	if(bits)
	{
		Diff = get_bits(bits);
		Diff = (Diff < shift_std[bits] ? (Diff + shift_offset[bits]) : Diff);
	}
	else
	{
		Diff = 0;
	}
	ZZ[0] = (PreDC[comp] += Diff);
	
	/* decode ACs */
	htbl = &ac_huff_tbl[Tai[comp]];
	for(K=1;K<DCT_SIZE2;K++)
	{
		ZZ[K] = 0;			//can use memset
	}
	K=1;
	do{
		int ac_tmp;
		//yover_optimize_0822, de_huffman(RS);
		RS = de_huffman();//yover_optimize_0822, 
		if(errorHuffman==15)
		{
			return 15;
		}

		SSSS = RS & 0x0f;
		RRRR = RS >> 4;
		if(SSSS)
		{
			K += RRRR;
			//Decode_zz[k]
			ac_tmp = get_bits(SSSS);
			ZZ[K] = (ac_tmp < shift_std[SSSS] ? ac_tmp + shift_offset[SSSS] : ac_tmp);
		}
		else
		{
			if(15 == RRRR)
			{
				K += 16;
				continue;
			}
			else
			{
				K=64;
				break;
			}
		}
		K++;
	}while(K < 64);/*while(64 == K);*/
	if(64 != K)
	{
		error(16);
	}

	//de-quantiz
	qtbl = (int chess_storage(YMEM) *)quant_tbl[Tqi[comp]];
	inptr = reconstruc_buffer[rec_idx];
	for(K=0;K<DCT_SIZE2;K++)
	{
		inptr[natural_order[K]] = (ZZ[K] * qtbl[K])  >> 10;
	}
	
  	wsptr = ZZ;
	for(K=DCT_SIZE; K>0; K--)
	{
		tmp0 = inptr[0];
		tmp4 = inptr[8];
	    tmp1 = inptr[16];
	    tmp5 = inptr[24];
    	tmp2 = inptr[32];
    	tmp6 = inptr[40];
    	tmp3 = inptr[48];
	    tmp7 = inptr[56];
    	
    	tmp10 = tmp0 + tmp2;
    	tmp11 = tmp0 - tmp2;
    	
    	tmp13 = tmp1 + tmp3;
    	tmp12 = ((INT_P362*(tmp1 - tmp3))>>8) - tmp13;
    	
    	tmp0 = tmp10 + tmp13;
    	tmp3 = tmp10 - tmp13;
    	tmp1 = tmp11 + tmp12;
    	tmp2 = tmp11 - tmp12;
    
		z13 = tmp6 + tmp5;
		z10 = tmp6 - tmp5;
		z11 = tmp4 + tmp7;
		z12 = tmp4 - tmp7;

		tmp7 = z11 + z13;
		tmp11 = (INT_P362*(z11 - z13))>>8;
		z5 =    ((z10 + z12)*INT_P473);
		tmp10 = ((INT_P277*z12 - z5)>>8);
		tmp12 = ((INT_M669*z10 + z5)>>8);

		tmp6 = tmp12 - tmp7;
		tmp5 = tmp11 - tmp6;
		tmp4 = tmp10 + tmp5;

		wsptr[0]  =  (tmp0 + tmp7);
		wsptr[8]  =  (tmp1 + tmp6);
		wsptr[16] =  (tmp2 + tmp5);
		wsptr[24] =  (tmp3 - tmp4);
		wsptr[32] =  (tmp3 + tmp4);
		wsptr[40] =  (tmp2 - tmp5);
		wsptr[48] =  (tmp1 - tmp6);
		wsptr[56] =  (tmp0 - tmp7);

		inptr++;
		wsptr++;
	}

	/* pass 2 */
	wsptr = ZZ;
	outptr = reconstruc_buffer[rec_idx];
	for(K=DCT_SIZE; K>0; K--)
	{
		tmp10 = (wsptr[0] + wsptr[4]);
		tmp11 = (wsptr[0] - wsptr[4]);

		tmp13 = (wsptr[2] + wsptr[6]);
		tmp12 = ((INT_P362*(wsptr[2] - wsptr[6]))>>8) - tmp13;

		tmp0 = tmp10 + tmp13;
		tmp3 = tmp10 - tmp13;
		tmp1 = tmp11 + tmp12;
		tmp2 = tmp11 - tmp12;

		z13 = wsptr[5] + wsptr[3];
		z10 = wsptr[5] - wsptr[3];
		z11 = wsptr[1] + wsptr[7];
		z12 = wsptr[1] - wsptr[7];

		tmp7 = z11 + z13;
		tmp11 = (INT_P362*(z11 - z13))>>8;

		z5 = (z10 + z12)*INT_P473;
		tmp10 = ((INT_P277*z12 - z5)>>8);
		tmp12 = ((INT_M669*z10 + z5)>>8);

		tmp6 = tmp12 - tmp7;
		tmp5 = tmp11 - tmp6;
		tmp4 = tmp10 + tmp5;

		*outptr++ = ((tmp0 + tmp7)>>5);
		*outptr++ = ((tmp1 + tmp6)>>5);
		*outptr++ = ((tmp2 + tmp5)>>5);
		*outptr++ = ((tmp3 - tmp4)>>5);
		*outptr++ = ((tmp3 + tmp4)>>5);
		*outptr++ = ((tmp2 - tmp5)>>5);
		*outptr++ = ((tmp1 - tmp6)>>5);
		*outptr++ = ((tmp0 - tmp7)>>5);
		wsptr += DCT_SIZE;
	}
	return iRet;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -