jdecode.c
来自「是一个手机功能的模拟程序」· C语言 代码 · 共 911 行 · 第 1/2 页
C
911 行
//===========================================================================
// JDECODE.C
// This file contains JPEG functions implemented for the JPEG library to
// implement JPEG prvoding via Epson JPEG Codec.
//---------------------------------------------------------------------------
// Copyright (c) 2003 Epson Research and Development, Inc.
// All Rights Reserved.
//===========================================================================
//-----------------------------------------------------------------------------
// Include Files
//-----------------------------------------------------------------------------
#include <stdio.h>
#include "chiplib.h"
#include "hal.h"
#include "hal_regs.h"
#include "jpeg.h"
#include "jpegcomm.h"
#include "multiframe.h"
//extern unsigned long tmpjpg[12*1024*100/4];
//------------------------------------------------------------------------------
// Local Type Defintions
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
// Local Function Prototypes
//------------------------------------------------------------------------------
static Boolean prvCalcScaleHeight( JPEGINFO* pJpegInfo, int displayHeight );
static Boolean prvCalcScaleWidth( JPEGINFO* pJpegInfo, int displayWidth );
static Boolean prvIsFifoFull( void );
static Boolean prvLoadJpeg( JPEGINFO* pJpegInfo );
static Boolean prvLoadMJpeg( JPEGINFO* pJpegInfo ,UInt8 * pHeader,Int32 HeaderSize);
static Boolean prvLoadYUV( JPEGINFO* pJpegInfo );
static Boolean prvReadMarker( JPEGINFO* pJpegInfo, prvJpegFlag jpegStatus );
static Boolean prvInitDecodeCodec( JPEGINFO* pJpegInfo );
static Boolean prvInitDecodeResizer( JPEGINFO* pJpegInfo );
static Boolean prvInitNextDecode( JPEGINFO* pJpegInfo, Boolean fSuccess );
//------------------------------------------------------------------------------
// jpegDecode - Decodes existing JPEG image from memory into hardware to be
// displayed
//
// Input: pJpegInfo pointer to JPEGINFO object
//
// Output: TRUE means success
// FALSE means NOT success
//
//------------------------------------------------------------------------------
Boolean jpegDecode( JPEGINFO *pJpegInfo )
{
Boolean fMulit;
Boolean fMjpeg;
UInt8 * pBuf;
Boolean fSuccess = pJpegInfo->m_MemEnc || jpegValidateBuf(pJpegInfo);
if ( fSuccess )
{
// 13.3 Resizer Restricts
// The dimensions specified by the resizer X/Y Start/End Positions registers
// must be a multiple of two.
fSuccess = (pJpegInfo->m_XStart & 1) ? FALSE : TRUE;
if ( !fSuccess )
{
jpegSetLastError( JPEG_ERR_DIM_RESTRICT );
}
else
{
fSuccess = (pJpegInfo->m_YStart & 1) ? FALSE : TRUE;
if ( !fSuccess )
{
jpegSetLastError( JPEG_ERR_DIM_RESTRICT );
}
else
{
// prvWorld world;
// SAVE/RESTORE is a good idea, but the problem right now is that the save is done here after registers have already been changed by program!
// So, I'm removing SAVE/RESTORE for now until we figure out a better way of doing this. [Roc]
// prvSaveWorld( &world );
fMulit=mfValidateMultiFrame((JPEGMULTIFRAME *)pJpegInfo->m_pBuf);
if(fMulit)
{
JPEGMULTIFRAME* pJpegMultiFrame;
pBuf=pJpegInfo->m_pBuf+pJpegInfo->m_EncSize;
while(pJpegInfo->m_pBuf<pBuf)
{
fMulit=mfValidateMultiFrame((JPEGMULTIFRAME *)pJpegInfo->m_pBuf);
if(!fMulit)
break;
pJpegMultiFrame = (JPEGMULTIFRAME*)(pJpegInfo->m_pBuf);
pJpegInfo->m_pBuf=pJpegInfo->m_pBuf+sizeof(JPEGMULTIFRAME);
pJpegInfo->m_EncSize=pJpegMultiFrame->ResultSize;
fSuccess = prvInitDecodeCodec( pJpegInfo );
if ( fSuccess )
{
if ( pJpegInfo->m_IsYUVfile )
fSuccess = prvLoadYUV( pJpegInfo );
else
fSuccess = prvLoadJpeg( pJpegInfo );
fSuccess = prvInitNextDecode( pJpegInfo, fSuccess );
}
pJpegInfo->m_pBuf=pJpegInfo->m_pBuf+pJpegMultiFrame->PaddedSize;
}
}
else
{
fSuccess = prvInitDecodeCodec( pJpegInfo );
if ( fSuccess )
{
if ( pJpegInfo->m_IsYUVfile )
fSuccess = prvLoadYUV( pJpegInfo );
else
fSuccess = prvLoadJpeg( pJpegInfo );
fSuccess = prvInitNextDecode( pJpegInfo, fSuccess );
}
}
// fSuccess = prvRestoreWorld(pJpegInfo,&world) && fSuccess;
}
}
}
return ( fSuccess );
}
//------------------------------------------------------------------------------
// jpegMDecode - Decodes existing MJPEG image from memory into hardware to be
// displayed
//
// Input: pJpegInfo pointer to JPEGINFO object
//
// Output: TRUE means success
// FALSE means NOT success
//
//------------------------------------------------------------------------------
Boolean jpegMDecode( JPEGINFO *pJpegInfo )
{
Boolean fMulit;
Boolean fMjpeg;
UInt8 * pBuf;
Boolean fSuccess = pJpegInfo->m_MemEnc || jpegValidateBuf(pJpegInfo);
pJpegInfo->m_FrameCount=0;
if ( fSuccess )
{
// 13.3 Resizer Restricts
// The dimensions specified by the resizer X/Y Start/End Positions registers
// must be a multiple of two.
fSuccess = (pJpegInfo->m_XStart & 1) ? FALSE : TRUE;
if ( !fSuccess )
{
jpegSetLastError( JPEG_ERR_DIM_RESTRICT );
}
else
{
fSuccess = (pJpegInfo->m_YStart & 1) ? FALSE : TRUE;
if ( !fSuccess )
{
jpegSetLastError( JPEG_ERR_DIM_RESTRICT );
}
else
{
UInt8 * pHeader;
JPEGMULTIFRAME* pJpegMultiFrame;
pHeader=pJpegInfo->m_pBuf+sizeof(JPEGMULTIFRAME);
pBuf=pJpegInfo->m_pBuf+pJpegInfo->m_EncSize;
// prvSaveWorld( &world );
fMulit=mfValidateMultiFrame((JPEGMULTIFRAME *)pJpegInfo->m_pBuf);
if(!fMulit)
return;
pJpegMultiFrame = (JPEGMULTIFRAME*)(pJpegInfo->m_pBuf);
pJpegInfo->m_pBuf=pJpegInfo->m_pBuf+sizeof(JPEGMULTIFRAME);
pJpegInfo->m_EncSize=pJpegMultiFrame->ResultSize;
fSuccess = prvInitDecodeCodec( pJpegInfo );
if ( fSuccess )
{
fSuccess = prvLoadJpeg(pJpegInfo);
fSuccess = prvInitNextDecode( pJpegInfo, fSuccess );
}
if ( fSuccess )
{
pJpegInfo->m_pBuf=pJpegInfo->m_pBuf+pJpegMultiFrame->PaddedSize;
pJpegInfo->m_FrameCount++;
}
else
{
return FALSE;
}
halDelayUS(pJpegInfo->m_Delay);
while(pJpegInfo->m_pBuf<pBuf)
{
#define HEADERSIZE 595
fMulit=mfValidateMultiFrame((JPEGMULTIFRAME *)pJpegInfo->m_pBuf);
if(!fMulit)
break;
pJpegMultiFrame = (JPEGMULTIFRAME*)(pJpegInfo->m_pBuf);
pJpegInfo->m_pBuf=pJpegInfo->m_pBuf+sizeof(JPEGMULTIFRAME);
pJpegInfo->m_EncSize=pJpegMultiFrame->ResultSize-2+HEADERSIZE;
fSuccess = prvInitDecodeCodec( pJpegInfo );
if ( fSuccess )
{
fSuccess = prvLoadMJpeg(pJpegInfo, pHeader, HEADERSIZE);
}
else
{
prvInitNextDecode( pJpegInfo, fSuccess );
return FALSE;
}
if ( fSuccess )
{
fSuccess = prvInitNextDecode( pJpegInfo, fSuccess );
}
else
{
return FALSE;
}
if ( fSuccess )
{
pJpegInfo->m_pBuf=pJpegInfo->m_pBuf+pJpegMultiFrame->PaddedSize;
pJpegInfo->m_FrameCount++;
}
else
{
return FALSE;
}
//pJpegInfo->m_pBuf=pJpegInfo->m_pBuf+pJpegMultiFrame->PaddedSize;
halDelayUS(pJpegInfo->m_Delay);
}
// fSuccess = prvRestoreWorld(pJpegInfo,&world) && fSuccess;
}
}
}
return ( fSuccess );
}
//------------------------------------------------------------------------------
// prvIsFifoFull - determines if FIFO flag is set or not
//
// Input: n/a
//
// Output: TRUE means FIFO is full
// FALSE means FIFO is NOT full
//
//------------------------------------------------------------------------------
Boolean prvIsFifoFull( void )
{
UInt8 irqStatus = halReadReg8( REG0300_IRQSTATUS0 );
Boolean fFifoFull = (irqStatus & 0x20) ? TRUE : FALSE;
return ( fFifoFull );
}
//------------------------------------------------------------------------------
// prvLoadJpeg - loads JPEG data into FIFO
//
// Input: pJpegInfo pointer to JPEGINFO object
//
// Output: TRUE means success
// FALSE means NOT success
//
//------------------------------------------------------------------------------
static Boolean prvLoadJpeg( JPEGINFO* pJpegInfo )
{
Boolean fSuccess = TRUE;
UInt8 fifoSize = 32;
UInt32 jpegDataSize = pJpegInfo->m_EncSize;
UInt8* pData = pJpegInfo->m_pBuf;
UInt8 irqEnable;
//UInt16 prevStatus = 0;
// If decoding from memory, don't load anything, just wait until decoding is done.
if ( pJpegInfo->m_MemEnc )
{
while ( (halReadReg8(REG0802_JPEGSTATUS0)&0x02) == 0 )
continue;
if ( pJpegInfo->m_fPause )
{
//printf( "Pause right after JPEG decode is complete. Press any key to continue..." );
//getch();
//printf( "\n" );
}
return TRUE;
}
#ifndef MV850E
//jpegFindTimeOut( pJpegInfo );
#endif
if ( !pJpegInfo->m_fFastCpu )
{
irqEnable = halReadReg8( REG0302_IRQENABLE0 );
//76543210b
//|||||||+--I2C Interrupt Enable
//||||||+---LCD Interface Busy Interrupt Enable
//|||||+----Camera Error Interrupt Enable
//||||+-----JPEG Interrupt Enable
//|||+------Camera Data Capture Interrupt Enable
//||+-------JPEG FIFO Full Interrupt Enable
//|+--------JPEG FIFO Empty Interrupt Enable
//+---------JPEG FIFO Overflow Interrupt Enable
halWriteReg8( REG0302_IRQENABLE0, (UInt8)(irqEnable | 0x20) );
}
while ( fSuccess && jpegDataSize )
{
if ( pJpegInfo->m_fFastCpu )
{
if ( pJpegInfo->m_fAFAP )
{
for ( ; jpegDataSize; --jpegDataSize, ++pData )
halWriteReg8( REG081A_JPEGFIFOWRITE, *pData );
}
else
{
for ( ; fifoSize && jpegDataSize; --fifoSize, --jpegDataSize, ++pData )
halWriteReg8( REG081A_JPEGFIFOWRITE, *pData );
fifoSize = 32 - (halReadReg8(REG0808_JPEGRAWSTATUS1)&0x3F);
}
}
else
{
Boolean fFifoFull;
do
{
fFifoFull = prvIsFifoFull();
#ifndef MV850E
if ( !fFifoFull )
{
//fSuccess = jpegNoTimeOut( pJpegInfo );
}
#endif
}
while ( fSuccess && (!fFifoFull) );
if ( fSuccess )
{
for ( ; (!fFifoFull) && jpegDataSize; ++pData, --jpegDataSize )
{
halWriteReg8( REG081A_JPEGFIFOWRITE, *pData );
fFifoFull = prvIsFifoFull();
}
}
}
if ( fSuccess )
{
prvJpegFlag jpegStatus = prvGetJpegStatus();
/*if ( pJpegInfo->m_fVerbose )
{
if ( jpegStatus != prevStatus )
{
if ( jpegStatus & JpegCodec )
//printf( "JpegCodec " );
if ( jpegStatus & LnBufOverflow )
//printf( "LnBufOverflow " );
if ( jpegStatus & JpegDecMarkerRd )
//printf( "DecodeMarkerRead " );
if ( jpegStatus & JpegDecComplete )
//printf( "JpegComplete" );
//printf( "\n" );
prevStatus = jpegStatus;
}
}*/
// Decode Marker Read
if ( jpegStatus & JpegDecMarkerRd )
{
fSuccess = prvReadMarker( pJpegInfo, jpegStatus );
}
#ifndef MV850E
else
{
//fSuccess = jpegNoTimeOut( pJpegInfo );
}
#endif
}
}
if ( pJpegInfo->m_fPause )
{
//printf( "Pause right after JPEG decode is complete. Press any key to continue..." );
//getch();
//printf( "\n" );
}
if ( !pJpegInfo->m_fFastCpu )
{
halWriteReg8( REG0302_IRQENABLE0, irqEnable );
}
return ( fSuccess );
}
static Boolean prvLoadMJpeg( JPEGINFO* pJpegInfo ,UInt8 * pHeader,Int32 HeaderSize)
{
Boolean fSuccess = TRUE;
Boolean fLoadHeader=FALSE;
UInt8 fifoSize = 32;
Int32 jpegDataSize = pJpegInfo->m_EncSize-HeaderSize;
UInt8* pData = pJpegInfo->m_pBuf;
UInt8 irqEnable;
//UInt16 prevStatus = 0;
// If decoding from memory, don't load anything, just wait until decoding is done.
if ( pJpegInfo->m_MemEnc )
{
while ( (halReadReg8(REG0802_JPEGSTATUS0)&0x02) == 0 )
continue;
if ( pJpegInfo->m_fPause )
{
//printf( "Pause right after JPEG decode is complete. Press any key to continue..." );
//getch();
//printf( "\n" );
}
return TRUE;
}
#ifndef MV850E
//jpegFindTimeOut( pJpegInfo );
#endif
if ( !pJpegInfo->m_fFastCpu )
{
irqEnable = halReadReg8( REG0302_IRQENABLE0 );
//76543210b
//|||||||+--I2C Interrupt Enable
//||||||+---LCD Interface Busy Interrupt Enable
//|||||+----Camera Error Interrupt Enable
//||||+-----JPEG Interrupt Enable
//|||+------Camera Data Capture Interrupt Enable
//||+-------JPEG FIFO Full Interrupt Enable
//|+--------JPEG FIFO Empty Interrupt Enable
//+---------JPEG FIFO Overflow Interrupt Enable
halWriteReg8( REG0302_IRQENABLE0, (UInt8)(irqEnable | 0x20) );
}
/*
while ( fSuccess && HeaderSize)
{
if ( pJpegInfo->m_fFastCpu )
{
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?