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

📄 png_decoder.c

📁 最新MTK手机软件源码
💻 C
📖 第 1 页 / 共 4 页
字号:
/*****************************************************************************
*  Copyright Statement:
*  --------------------
*  This software is protected by Copyright and the information contained
*  herein is confidential. The software may not be copied and the information
*  contained herein may not be used or disclosed except with the written
*  permission of MediaTek Inc. (C) 2005
*
*  BY OPENING THIS FILE, BUYER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
*  THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
*  RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO BUYER ON
*  AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES,
*  EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF
*  MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT.
*  NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE
*  SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR
*  SUPPLIED WITH THE MEDIATEK SOFTWARE, AND BUYER AGREES TO LOOK ONLY TO SUCH
*  THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. MEDIATEK SHALL ALSO
*  NOT BE RESPONSIBLE FOR ANY MEDIATEK SOFTWARE RELEASES MADE TO BUYER'S
*  SPECIFICATION OR TO CONFORM TO A PARTICULAR STANDARD OR OPEN FORUM.
*
*  BUYER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND CUMULATIVE
*  LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL BE,
*  AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT ISSUE,
*  OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY BUYER TO
*  MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE. 
*
*  THE TRANSACTION CONTEMPLATED HEREUNDER SHALL BE CONSTRUED IN ACCORDANCE
*  WITH THE LAWS OF THE STATE OF CALIFORNIA, USA, EXCLUDING ITS CONFLICT OF
*  LAWS PRINCIPLES.  ANY DISPUTES, CONTROVERSIES OR CLAIMS ARISING THEREOF AND
*  RELATED THERETO SHALL BE SETTLED BY ARBITRATION IN SAN FRANCISCO, CA, UNDER
*  THE RULES OF THE INTERNATIONAL CHAMBER OF COMMERCE (ICC).
*
*****************************************************************************/
/*******************************************************************************
 * Filename:
 * ---------
 *	 png_decoder.c
 *
 * Project:
 * --------
 *  MAUI
 *
 * Description:
 * ------------
 *  Driver of the png decoder .
 *
 * Author:
 * -------
 * -------
 *
 *==============================================================================
 * 				HISTORY
 * Below this line, this part is controlled by PVCS VM. DO NOT MODIFY!! 
 *------------------------------------------------------------------------------
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 *
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 * removed!
 *------------------------------------------------------------------------------
 * Upper this line, this part is controlled by PVCS VM. DO NOT MODIFY!! 
 *==============================================================================
 *******************************************************************************/
 // include header files
#include "kal_release.h"
#include "reg_base.h"
#include "intrCtrl.h"
#include "drv_comm.h"
#include "gpt_sw.h"
#include "visual_comm.h"
#include "drm_gprot.h"
#include "fat_fs.h"
#include	"bytestream_hw.h"
#include "png_decoder.h"
#include "2d_engine.h"
#include "visualhisr.h"

// #define USE_HW_PNG_DECODER
#if defined(USE_HW_PNG_DECODER_V1)
static png_dcb_struct png_dcb;
static png_state_enum png_state;
static VISUAL_HISR_ID png_hisr;				
static kal_uint8 png_gpt_handle;	

// constant
#define PNG_IDAT_BUF_LEN		8*1024

static kal_uint8 png_signature[8] = {137, 80, 78, 71, 13, 10, 26, 10};
static const kal_uint8 png_IHDR[5] = { 73,  72,  68,  82, '\0'};
static const kal_uint8 png_IDAT[5] = { 73,  68,  65,  84, '\0'};
static const kal_uint8 png_IEND[5] = { 73,  69,  78,  68, '\0'};
static const kal_uint8 png_PLTE[5] = { 80,  76,  84,  69, '\0'};
static const kal_uint8 png_tRNS[5] = {116,  82,  78,  83, '\0'};
static const kal_uint8 png_bKGD[5] = { 98,  75,  71,  68, '\0'};
#define DONT_CARE	1
static const kal_uint8 png_type_channel[] = {1,DONT_CARE,3,1,2,DONT_CARE,4};
static kal_uint32 png_idat_buf[PNG_IDAT_BUF_LEN/4+1];
static kal_uint32 idat_buf_len = PNG_IDAT_BUF_LEN;

/*************************************************************************
* FUNCTION
*  png_assemble_idat
*
* DESCRIPTION
*	1. assemle the IDAT chunk into png_idat_buf
*	2. check if the last IDAT is reached
*  3. there are two special case: a. only one data chunk and less than 4 bytes
*		b. the last remaining bytes are less than 4 bytes
* PARAMETERS
*	
* RETURNS
*   
* GLOBALS AFFECTED
*	png_dcb.my_idat_remain
*
*************************************************************************/
static void png_assemble_idat(void)
{
	kal_uint32 remain,len,size;
	kal_uint8 *ptr = (kal_uint8*)png_idat_buf;
	kal_uint8 buf[4];

	remain = png_dcb.my_idat_remain ;
	size = idat_buf_len; 
	while(1)
	{				
		if(remain)
		{
			len = remain;
			goto no_header;
		}
		else
		{
			// encounter a new IDAT chunk
			len = PNG_GET_U32();		
			if(len > 0x1000000)
				PNG_RAISE(1);
			PNG_GET_ARRAY(buf, 4);
		}
		if(!kal_mem_cmp(buf,png_IDAT,4) && len!=0)
		{
no_header:				
			if(size >= len)
			{
				// read entire IDAT chunk into buffer
				PNG_GET_ARRAY(ptr, len);
				PNG_FLUSH(4);// crc 					
				size -= len;
				ptr += len;
				remain = 0;
			}
			else if(size > 0)
			{
				// fill the idat buffer and record the remaining IDAT bytes
				PNG_GET_ARRAY(ptr, size);
				remain  = len -size;
				png_dcb.my_idat_remain = remain;
				break;
			}
			else if (size == 0)
			{
				png_dcb.my_idat_remain = len;
				break;
			}
		}
		else
		{
			// all IDAT is finished
			png_dcb.z_count = ptr - (kal_uint8*)png_idat_buf;
			png_dcb.is_IEND = KAL_TRUE;
			break;
		}			
	}
}
/*************************************************************************
* FUNCTION
*  png_remove_srckey_color
*
* DESCRIPTION
*	modify the same color with the transparent index
*
* PARAMETERS
*	index: transparent index	
*	
* RETURNS
*   
* GLOBALS AFFECTED
*	
*************************************************************************/
/*static void png_remove_srckey_color( kal_uint32 index)
{
	kal_uint32 i,count;
	kal_uint32 src_key;
	kal_uint32 *ct = png_dcb.cfg->color_table;	

	src_key = ct[index];
	count = png_dcb.info.num_plte;
	for(i=0;i<=count;i++)
	{
		if(src_key == ct[i])
		{
			// modify the blue 
			ct[i] ^= 1;
		}
	}
	ct[index]= src_key;	
}*/
/*************************************************************************
* FUNCTION
*  png_timeout_hander
*
* DESCRIPTION
*	call back function of the GPT timer ot handle the decoding timeout.
*
* PARAMETERS
*	
* RETURNS
*   
* GLOBALS AFFECTED
*	
*************************************************************************/
static void png_timeout_hander(void* p)
{
	png_dcb.is_timeout = KAL_TRUE;
	kal_print("hw png decode timeout");
	DRV_WriteReg32(PNG_IRQ_EN, 0);
	PNG_RESET();
	png_state = PNG_STATE_READY;
	DRVPDN_Enable(DRVPDN_CON3,DRVPDN_CON3_PNG,PDN_PNG);
	if(png_dcb.cb  != NULL)
		png_dcb.cb(PNG_DECODE_TIMEOUT);
}
/*************************************************************************
* FUNCTION
*  png_resz_ratio
*
* DESCRIPTION
*	calculate the resizing ratio according to the real size and expected one
*
* PARAMETERS
*	real: actual image width or height
*	expect: expected image width or height
*	
* RETURNS
* 	The resizing ratio  
*
* GLOBALS AFFECTED
*	
*************************************************************************/
#if 0
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
#endif
/*************************************************************************
* FUNCTION
*  png_g2d_bitblt
*
* DESCRIPTION
*	bitblit the png_work_buffer onto the destination LCD frame buffer.
*
* PARAMETERS
*	
* RETURNS
*
* GLOBALS AFFECTED
*	
*************************************************************************/
#if 0
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
/* under construction !*/
#endif

/*************************************************************************
* FUNCTION
*  png_get_gray_scale
*
* DESCRIPTION
*	1. Transform the gray value from low bit depth into 8 bit depth
*	2. Transfrom the 16-bepth gray value into 8-bit depth.
* PARAMETERS
*	bit_depth: original bit depth of the gray value
*	gray: gray value to be transformed.
*
* RETURNS
*   The transformed 8-bit gray value.
*
* GLOBALS AFFECTED
*	
*************************************************************************/
kal_uint32 png_get_gray_scale(kal_uint32 bit_depth, kal_uint32 gray)
{
	kal_uint32 loop,value;

	ASSERT(gray <= ((1<<bit_depth)-1));
	if(gray == ((1<<bit_depth)-1))
		return 0xff;
	if(gray == 0)
		return gray;
	
	if(bit_depth < 8)
	{
		value = gray;
		loop = (8/bit_depth) -1 ;
		while(loop--)
		{
			value = (value << bit_depth);
			value |= gray;			
		}	
		return value;
	}
	else if(bit_depth == 8)
	{
		return gray;
	}
	else
	{
		return gray >> 8;
	}
}
/*************************************************************************
* FUNCTION
*  png_decode_hw
*
* DESCRIPTION
*	1. start to decode the specific PNG image (first time of a image)
*	2. input all of the registers of png decoder
*	3. trigger the decoding process
*
* PARAMETERS
*	z_len: length of IDAT count
*
* RETURNS
*   
* GLOBALS AFFECTED
*	
*************************************************************************/
// len: length of IDAT count
static void png_decode_hw(kal_uint32 z_len)
{	
	register png_config_struct *cfg = png_dcb.cfg;
	png_inform_struct *info = &png_dcb.info;
	kal_uint32 reg,out_format;
	kal_uint8 resz_w=0, resz_h=0;
	
	DRVPDN_Disable(DRVPDN_CON3,DRVPDN_CON3_PNG,PDN_PNG);	
	DRV_WriteReg32(PNG_IRQ_EN, 0);
	PNG_RESET();

	png_dcb.my_idat_remain = z_len;
	png_assemble_idat();
	DRV_WriteReg32(PNG_IN_START, png_idat_buf);
	DRV_WriteReg32(PNG_IN_COUNT, idat_buf_len+4);
	if(png_dcb.z_count >= 4)
	{
		DRV_WriteReg32(PNG_IDAT_COUNT, png_dcb.z_count);
	}
	else if(png_dcb.z_count > 0)
	{
		kal_uint32 reg,i;
		kal_uint8 *ptr = (kal_uint8*)png_idat_buf;
		
		for(reg=0,i=0; i<png_dcb.z_count; i++)
		{
			 reg |= (ptr[i] << (8*i));
		}
		DRV_WriteReg32(PNG_IDAT_BUFFER, reg);
		DRV_WriteReg32(PNG_IDAT_COUNT, png_dcb.z_count);
	}	
	else
		DRV_WriteReg32(PNG_IDAT_COUNT, idat_buf_len);
		
	// configure the buffers 
	#if defined(PNG_NEW_BUFFER_INTERFACE)
	{
		register kal_uint32 buf_index;
		
		buf_index = (kal_uint32)cfg->color_table_t;
		buf_index += CT_LEN*4;
		DRV_WriteReg32(PNG_HCLEN_START, buf_index);
		buf_index += HCLEN_LEN;	
		DRV_WriteReg32(PNG_HLEN_START, buf_index);
		buf_index += HLEN_LEN;
		DRV_WriteReg32(PNG_HLIT_START, buf_index);
		buf_index += HLIT_LEN;
		DRV_WriteReg32(PNG_HDIST_START, buf_index);
		buf_index += HDIST_LEN;
		DRV_WriteReg32(PNG_BUFF0_START, buf_index);
		buf_index += BUFF0_LEN;
		DRV_WriteReg32(PNG_BUFF1_START, buf_index);
		buf_index += BUFF1_LEN;
		DRV_WriteReg32(PNG_LZ77_START, buf_index);
	}
	#else
	DRV_WriteReg32(PNG_HCLEN_START, cfg->hclen);
	DRV_WriteReg32(PNG_HLEN_START, cfg->hlen);
	DRV_WriteReg32(PNG_HLIT_START, cfg->hlit);
	DRV_WriteReg32(PNG_HDIST_START, cfg->hdist);
	DRV_WriteReg32(PNG_BUFF0_START, cfg->buff0);
	DRV_WriteReg32(PNG_BUFF1_START, cfg->buff1);
	DRV_WriteReg32(PNG_LZ77_START, cfg->LZ77);
	#endif
	DRV_WriteReg32(PNG_CT_START, cfg->color_table);
	DRV_WriteReg32(PNG_TRAN_TABLE, cfg->color_table_t);
	
	reg = (info->bit_depth << 3)|(info->color_type);
	DRV_WriteReg8(PNG_COLOR_TYPE, reg);
	DRV_WriteReg8(PNG_INTERLACE_EN, info->interlaced);
	DRV_WriteReg32(PNG_IMG_WH, (info->img_w << 16) | info->img_h);

	// partial input have to be enabled always
	out_format = cfg->out_format|PNG_OUT_FORMAT_PATRIAL;
	// use software to remove MMI's source key 
	if((info->color_type == COLOR_TYPE_RGB || info->color_type == COLOR_TYPE_RGB_A)
		&&(cfg->out_format == RGB565|| cfg->out_format == RGB888))
		info->use_work_buf = KAL_TRUE;

	// calculate resz_w , resz_h
	{
		kal_uint32 bytes_per_pixel;
		
		switch(cfg->out_format)
		{
		case RGB565: bytes_per_pixel=2;break;
		case RGB888: bytes_per_pixel=3;break;
		case ARGB8888: bytes_per_pixel=4;break;
		default: bytes_per_pixel=1;break;
		}
		if(cfg->expect_w==0) cfg->expect_w = info->img_w;
		if(cfg->expect_h==0) cfg->expect_h = info->img_h;

		cfg->cal_work_buffer_info_func(
						&resz_w,
						&info->wb_dest_x,&info->wb_dest_y,
						&info->wb_width,&info->wb_height,
						cfg->work_buffer_size / bytes_per_pixel,
						info->img_w,info->img_h,
						cfg->dest_x,cfg->dest_y,
						cfg->expect_w,cfg->expect_h,
						cfg->clip_x1,cfg->clip_y1,cfg->clip_x2,cfg->clip_y2);
		resz_h = resz_w;
	}
	
	info->use_work_buf = KAL_FALSE;
	info->resz_w = resz_w;
	info->resz_h = resz_h;
	
	// configure the resizing
	if((info->img_w>>resz_w) != cfg->expect_w
	||(info->img_h>>resz_h)!= cfg->expect_h)
	{
		// use 2D engine to perform transparent
		info->use_work_buf = KAL_TRUE;
	}

	if(resz_w || resz_h)
	{	// use software resizer to perform fine resizing	
		png_dcb.resz_en = KAL_TRUE;
		png_dcb.resz_w = resz_w;
		png_dcb.resz_h = resz_h;
		reg = (resz_w << 8)|(resz_h << 4)|1;
		DRV_WriteReg32(PNG_RESIZE_CTRL, reg);		
	}
	else
	{
		DRV_WriteReg32(PNG_RESIZE_CTRL, 0);

⌨️ 快捷键说明

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