Initial community commit
This commit is contained in:
@@ -0,0 +1,315 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : OptFunctions.c
|
||||
*
|
||||
* Description : MMX or otherwise processor specific
|
||||
* optimised versions of functions
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.08 JBB 13 Jun 01 VP4 Code Clean Out
|
||||
* 1.07 JBB 26/01/01 Removed unused function
|
||||
* 1.06 YWX 23/05/00 Remove the clamping in MmxReconPostProcess()
|
||||
* 1.05 YWX 15/05/00 Added MmxReconPostProcess()
|
||||
* 1.04 SJL 03/14/00 Added in Tim's versions of MmxReconInter and MmxReconInterHalfPixel2.
|
||||
* 1.03 PGW 12/10/99 Changes to reduce uneccessary dependancies.
|
||||
* 1.02 PGW 30/08/99 Minor changes to MmxReconInterHalfPixel2().
|
||||
* 1.01 PGW 13/07/99 Changes to keep reconstruction data to 16 bit
|
||||
* 1.00 PGW 14/06/99 Configuration baseline
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/*
|
||||
Use Tim's optimized version.
|
||||
*/
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT // Strict type checking.
|
||||
|
||||
#include "codec_common.h"
|
||||
|
||||
#include "pbdll.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Imports.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
extern INT32 * XX_LUT;
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Module Statics
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
INT16 Ones[4] = {1,1,1,1};
|
||||
INT16 OneTwoEight[4] = {128,128,128,128};
|
||||
UINT8 Eight128s[8] = {128,128,128,128,128,128,128,128};
|
||||
|
||||
#pragma warning( disable : 4799 ) // Disable no emms instruction warning!
|
||||
|
||||
/****************************************************************************
|
||||
* Forward References
|
||||
*****************************************************************************
|
||||
*/
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : ClearSysState()
|
||||
*
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : DoesNothing
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void ClearSysStateC(void)
|
||||
{
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : ClearMmx()
|
||||
*
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Clears down the MMX state
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void ClearMmx(void)
|
||||
{
|
||||
__asm
|
||||
{
|
||||
emms ; Clear the MMX state.
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : MMXReconIntra
|
||||
*
|
||||
* INPUTS : INT16 * idct
|
||||
* Pointer to the output from the idct for this block
|
||||
*
|
||||
* UINT32 stride
|
||||
* Line Length in pixels in recon and reference images
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : UINT8 * dest
|
||||
* The reconstruction buffer
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Reconstructs an intra block - MMX version
|
||||
*
|
||||
* SPECIAL NOTES : Tim Murphy's optimized version
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void MMXReconIntra( PB_INSTANCE *pbi, UINT8 * dest, INT16 * idct, INT32 stride )
|
||||
{
|
||||
__asm
|
||||
{
|
||||
// u pipe
|
||||
// v pipe
|
||||
mov eax,[idct] ; Signed 16 bit inputs
|
||||
mov edx,[dest] ; Signed 8 bit outputs
|
||||
movq mm0,[Eight128s] ; Set mm0 to 0x8080808080808080
|
||||
;
|
||||
mov ebx,[stride] ; Line stride in output buffer
|
||||
lea ecx,[eax+128] ; Endpoint in input buffer
|
||||
loop_label: ;
|
||||
movq mm2,[eax] ; First four input values
|
||||
;
|
||||
packsswb mm2,[eax+8] ; pack with next(high) four values
|
||||
por mm0,mm0 ; stall
|
||||
pxor mm2,mm0 ; Convert result to unsigned (same as add 128)
|
||||
lea eax,[eax + 16] ; Step source buffer
|
||||
cmp eax,ecx ; are we done
|
||||
;
|
||||
movq [edx],mm2 ; store results
|
||||
;
|
||||
lea edx,[edx+ebx] ; Step output buffer
|
||||
jc loop_label ; Loop back if we are not done
|
||||
}
|
||||
// 6c/8 elts = 9c/8 = 1.125 c/pix
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : MmxReconInter
|
||||
*
|
||||
* INPUTS : UINT8 * RefPtr
|
||||
* The last frame reference
|
||||
*
|
||||
* INT16 * ChangePtr
|
||||
* Pointer to the change data
|
||||
*
|
||||
* UINT32 LineStep
|
||||
* Line Length in pixels in recon and ref images
|
||||
*
|
||||
* OUTPUTS : UINT8 * ReconPtr
|
||||
* The reconstruction
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Reconstructs data from last data and change
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void MmxReconInter( PB_INSTANCE *pbi, UINT8 * ReconPtr, UINT8 * RefPtr, INT16 * ChangePtr, UINT32 LineStep )
|
||||
{
|
||||
(void) pbi;
|
||||
|
||||
_asm {
|
||||
push edi
|
||||
;; mov ebx, [ref]
|
||||
;; mov ecx, [diff]
|
||||
;; mov eax, [dest]
|
||||
;; mov edx, [stride]
|
||||
mov ebx, [RefPtr]
|
||||
mov ecx, [ChangePtr]
|
||||
mov eax, [ReconPtr]
|
||||
mov edx, [LineStep]
|
||||
pxor mm0, mm0
|
||||
lea edi, [ecx + 128]
|
||||
;
|
||||
L:
|
||||
movq mm2, [ebx] ; (+3 misaligned) 8 reference pixels
|
||||
;
|
||||
movq mm4, [ecx] ; first 4 changes
|
||||
movq mm3, mm2
|
||||
movq mm5, [ecx + 8] ; last 4 changes
|
||||
punpcklbw mm2, mm0 ; turn first 4 refs into positive 16-bit #s
|
||||
paddsw mm2, mm4 ; add in first 4 changes
|
||||
punpckhbw mm3, mm0 ; turn last 4 refs into positive 16-bit #s
|
||||
paddsw mm3, mm5 ; add in last 4 changes
|
||||
add ebx, edx ; next row of reference pixels
|
||||
packuswb mm2, mm3 ; pack result to unsigned 8-bit values
|
||||
lea ecx, [ecx + 16] ; next row of changes
|
||||
cmp ecx, edi ; are we done?
|
||||
;
|
||||
movq [eax], mm2 ; store result
|
||||
;
|
||||
lea eax, [eax+edx] ; next row of output
|
||||
jc L ; 12c / 8 elts = 18c / 8 pixels = 2.25 c/pix
|
||||
|
||||
pop edi
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : CopyBlockUsingMMX
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Copies a block from source to destination
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void CopyBlockMMX(unsigned char *src, unsigned char *dest, unsigned int srcstride)
|
||||
{
|
||||
unsigned char *s = src;
|
||||
unsigned char *d = dest;
|
||||
unsigned int stride = srcstride;
|
||||
// recon copy
|
||||
_asm
|
||||
{
|
||||
mov ecx, [stride]
|
||||
mov eax, [s]
|
||||
mov ebx, [d]
|
||||
lea edx, [ecx + ecx * 2]
|
||||
|
||||
movq mm0, [eax]
|
||||
movq mm1, [eax + ecx]
|
||||
movq mm2, [eax + ecx*2]
|
||||
movq mm3, [eax + edx]
|
||||
|
||||
lea eax, [eax + ecx*4]
|
||||
|
||||
movq [ebx], mm0
|
||||
movq [ebx + ecx], mm1
|
||||
movq [ebx + ecx*2], mm2
|
||||
movq [ebx + edx], mm3
|
||||
|
||||
lea ebx, [ebx + ecx * 4]
|
||||
|
||||
movq mm0, [eax]
|
||||
movq mm1, [eax + ecx]
|
||||
movq mm2, [eax + ecx*2]
|
||||
movq mm3, [eax + edx]
|
||||
|
||||
movq [ebx], mm0
|
||||
movq [ebx + ecx], mm1
|
||||
movq [ebx + ecx*2], mm2
|
||||
movq [ebx + edx], mm3
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,204 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : WmtOptFunctions.c
|
||||
*
|
||||
* Description : willamette processor specific
|
||||
* optimised versions of functions
|
||||
*
|
||||
* AUTHOR : Yaowu Xu
|
||||
*
|
||||
* Special Note:
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
*
|
||||
* 1.04 JBB 13 Jun 01 VP4 Code Clean Out
|
||||
* 1.03 YWX 07-Dec-00 Removed constants and functions that are not in use
|
||||
* Added push and pop ebx in WmtReconIntra
|
||||
* 1.02 YWX 30 Aug 00 changed to be compatible with Microsoft compiler
|
||||
* 1.01 YWX 13 JUL 00 New Willamette Optimized Functions
|
||||
* 1.00 YWX 14/06/00 Configuration baseline from OptFunctions.c
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/*
|
||||
Use Tim's optimized version.
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT // Strict type checking.
|
||||
|
||||
#include "codec_common.h"
|
||||
|
||||
#include "pbdll.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Imports.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Module Statics
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
|
||||
_declspec(align(16)) static UINT8 Eight128s[8] = {128,128,128,128,128,128,128,128};
|
||||
|
||||
#pragma warning( disable : 4799 ) // Disable no emms instruction warning!
|
||||
|
||||
/****************************************************************************
|
||||
* Forward References
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : WmtReconIntra
|
||||
*
|
||||
* INPUTS : INT16 * idct
|
||||
* Pointer to the output from the idct for this block
|
||||
*
|
||||
* UINT32 stride
|
||||
* Line Length in pixels in recon and reference images
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : UINT8 * dest
|
||||
* The reconstruction buffer
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Reconstructs an intra block - wmt version
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void WmtReconIntra( PB_INSTANCE *pbi, UINT8 * dest, INT16 * idct, INT32 stride )
|
||||
{
|
||||
__asm
|
||||
{
|
||||
|
||||
push ebx
|
||||
|
||||
mov eax,[idct] ; Signed 16 bit inputs
|
||||
mov edx,[dest] ; Unsigned 8 bit outputs
|
||||
|
||||
movq xmm0,QWORD PTR [Eight128s] ; Set xmm0 to 0x000000000000008080808080808080
|
||||
pxor xmm3, xmm3 ; set xmm3 to 0
|
||||
;
|
||||
mov ebx,[stride] ; Line stride in output buffer
|
||||
lea ecx,[eax+128] ; Endpoint in input buffer
|
||||
|
||||
loop_label:
|
||||
|
||||
movdqa xmm2,XMMWORD PTR [eax] ; Read the eight inputs
|
||||
packsswb xmm2,xmm3 ;
|
||||
|
||||
pxor xmm2,xmm0 ; Convert result to unsigned (same as add 128)
|
||||
lea eax,[eax + 16] ; Step source buffer
|
||||
|
||||
cmp eax,ecx ; are we done
|
||||
movq QWORD PTR [edx],xmm2 ; store results
|
||||
|
||||
lea edx,[edx+ebx] ; Step output buffer
|
||||
jc loop_label ; Loop back if we are not done
|
||||
|
||||
pop ebx
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : WmtReconInter
|
||||
*
|
||||
* INPUTS : UINT8 * RefPtr
|
||||
* The last frame reference
|
||||
*
|
||||
* INT16 * ChangePtr
|
||||
* Pointer to the change data
|
||||
*
|
||||
* UINT32 LineStep
|
||||
* Line Length in pixels in recon and ref images
|
||||
*
|
||||
* OUTPUTS : UINT8 * ReconPtr
|
||||
* The reconstruction
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Reconstructs data from last data and change
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void WmtReconInter( PB_INSTANCE *pbi, UINT8 * ReconPtr, UINT8 * RefPtr, INT16 * ChangePtr, UINT32 LineStep )
|
||||
{
|
||||
(void) pbi;
|
||||
|
||||
_asm {
|
||||
push edi
|
||||
|
||||
mov ebx, [RefPtr]
|
||||
mov ecx, [ChangePtr]
|
||||
|
||||
mov eax, [ReconPtr]
|
||||
mov edx, [LineStep]
|
||||
|
||||
pxor xmm0, xmm0
|
||||
lea edi, [ecx + 128]
|
||||
L:
|
||||
movq xmm2, QWORD ptr [ebx] ; (+3 misaligned) 8 reference pixels
|
||||
movdqa xmm4, XMMWORD ptr [ecx] ; 8 changes
|
||||
|
||||
punpcklbw xmm2, xmm0 ;
|
||||
|
||||
add ebx, edx ; next row of reference pixels
|
||||
paddsw xmm2, xmm4 ; add in first 4 changes
|
||||
|
||||
lea ecx, [ecx + 16] ; next row of changes
|
||||
packuswb xmm2, xmm0 ; pack result to unsigned 8-bit values
|
||||
|
||||
cmp ecx, edi ; are we done?
|
||||
movq QWORD PTR [eax], xmm2 ; store result
|
||||
|
||||
lea eax, [eax+edx] ; next row of output
|
||||
jc L ; 12c / 8 elts = 18c / 8 pixels = 2.25 c/pix
|
||||
|
||||
pop edi
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,369 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : SystemDependant.c
|
||||
*
|
||||
* Description : Miscellaneous system dependant functions
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.19 YWX 15-Jun-01 added function pointer setups for new deblocking filter
|
||||
* 1.18 YWX 26-Apr-01 Fixed the cpu frequency detection bug caused by Sleep()
|
||||
* 1.17 JBX 22-Mar-01 Merged with new vp4-mapca bitstream
|
||||
* 1.16 JBB 26-Jan-01 Cleaned out unused function
|
||||
* 1.15 YWX 08-dec-00 Added WMT PostProcessor and
|
||||
* moved function declarations into _head files
|
||||
* 1.14 JBB 30 NOV 00 Version number changes
|
||||
* 1.13 YWX 03-Nov-00 Optimized postprocessor filters
|
||||
* 1.12 YWX 02-Nov-00 Added new loopfilter function pointers
|
||||
* 1.11 YWX 19-Oct-00 Added 1-2 Scaling functions pointers
|
||||
* 1.10 jbb 16 oct 00 added ifdefs to insure version code
|
||||
* 1.09 YWX 04-Oct-00 Added function pointers for scaling
|
||||
* 1.08 YWX 06 Sep 00 Added function pointers for new deringing filter
|
||||
* using frag baseed Q Value.
|
||||
* 1.07 JBB 21 Aug 00 New More Blurry in high variance area deringer
|
||||
* 1.06 YWX 2 Aug 00 Added function pointers for postprocess
|
||||
* 1.05 YWX 15/05/00 Added functions to check processor frequency
|
||||
* and more function pointers for postprocessor
|
||||
* 1.04 YWX 08/05/00 Added function pointers setup for postprocess
|
||||
* 1.03 SJL 20/04/00 Added ability to enable the new dequant code.
|
||||
* 1.02 SJL 22/03/00 Function pointers for the loop filter.
|
||||
* 1.01 JBB 21/03/00 More Function Pointers for optimized playback
|
||||
* 1.00 PGW 12/10/99 Configuration baseline
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#include "pbdll.h"
|
||||
#pragma warning(disable:4115)
|
||||
#include <windows.h>
|
||||
|
||||
extern void GetProcessorFlags(INT32 *MmxEnabled, INT32 *XmmEnabled, INT32 *WmtEnabled);
|
||||
|
||||
//extern void ReadTokens_c(PB_INSTANCE *pbi, INT32 * HuffIndices );
|
||||
extern void (*VP5_BuildQuantIndex)( QUANTIZER * pbi);
|
||||
|
||||
extern void UnPackVideo_C(PB_INSTANCE *pbi);
|
||||
extern void UnPackVideo2(PB_INSTANCE *pbi);
|
||||
|
||||
extern void VP5_BuildQuantIndex_Generic(QUANTIZER *pbi);
|
||||
extern void VP5_BuildQuantIndex_ForMMX(QUANTIZER *pbi);
|
||||
extern void VP5_BuildQuantIndex_ForWMT(QUANTIZER *pbi);
|
||||
|
||||
|
||||
//extern void ReadTokens_mmx(PB_INSTANCE *pbi, INT32 * HuffIndices );
|
||||
extern void UnPackVideoMMX_LL (PB_INSTANCE *pbi);
|
||||
extern void ClearMmx(void);
|
||||
extern void CopyBlockMMX(unsigned char *src, unsigned char *dest, unsigned int srcstride);
|
||||
//extern void ReadTokensPredict_c( PB_INSTANCE *pbi, UINT32 BlockSize, UINT32 Hpos );
|
||||
|
||||
/****************************************************************************
|
||||
* Explicit imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
extern unsigned int CPUFrequency;
|
||||
|
||||
//extern MmxEnabled; // Is MMX enabled flag
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Module statics.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : readTSC
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : read the cpu time stamp counter
|
||||
*
|
||||
* SPECIAL NOTES : Since this function uses RDTSC instruction, which is
|
||||
* introduced in Pentium processor, so this routine is
|
||||
* expected to work on Pentium and above.
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void VP5_readTSC(unsigned long *tsc)
|
||||
{
|
||||
int time;
|
||||
|
||||
__asm
|
||||
{
|
||||
pushad
|
||||
cpuid
|
||||
rdtsc
|
||||
mov time,eax
|
||||
popad
|
||||
}
|
||||
|
||||
*tsc=time;
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_GetProcessorFrequency()
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
*
|
||||
* OUTPUTS : The Frequency in MHZ
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Check the Processor's working freqency
|
||||
*
|
||||
* SPECIAL NOTES : This function should only be used here. Limited tests
|
||||
* has verified it works till 166MHz Pentium with MMX.
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
unsigned long VP5_GetProcessorFrequency()
|
||||
{
|
||||
|
||||
LARGE_INTEGER pf; //Performance Counter Frequencey
|
||||
LARGE_INTEGER startcount, endcount;
|
||||
unsigned long tsc1, tsc2;
|
||||
|
||||
//If the cpu does not support the high resolution counter, return 0
|
||||
unsigned long time1, time2;
|
||||
unsigned long cpufreq=0;
|
||||
unsigned long Nearest66Mhz, Nearest50Mhz;
|
||||
unsigned long Delta66, Delta50;
|
||||
|
||||
if( QueryPerformanceFrequency(&pf))
|
||||
{
|
||||
|
||||
// read the counter and TSC at start
|
||||
QueryPerformanceCounter(&startcount);
|
||||
VP5_readTSC(&tsc1);
|
||||
// delay for 10 ms to get enough accuracy
|
||||
time1 = timeGetTime();
|
||||
time2 = time1;
|
||||
|
||||
while( time2 < time1+5 )
|
||||
time2 = timeGetTime();
|
||||
|
||||
//read the counter and TSC at end
|
||||
QueryPerformanceCounter(&endcount);
|
||||
VP5_readTSC(&tsc2);
|
||||
|
||||
//calculate the frequency
|
||||
cpufreq = (unsigned long )((double)( tsc2 - tsc1 )
|
||||
* (double)pf.LowPart
|
||||
/ (double) ( endcount.LowPart - startcount.LowPart )
|
||||
/ 1000000);
|
||||
|
||||
}
|
||||
|
||||
Nearest66Mhz = ((cpufreq * 3 + 100)/200 * 200) / 3;
|
||||
Delta66 = abs(Nearest66Mhz - cpufreq);
|
||||
Nearest50Mhz = ((cpufreq + 25)/50 *50);
|
||||
Delta50 = abs(Nearest50Mhz - cpufreq);
|
||||
|
||||
if(Delta50 < Delta66)
|
||||
cpufreq = Nearest50Mhz;
|
||||
else
|
||||
{
|
||||
|
||||
cpufreq = Nearest66Mhz;
|
||||
if(cpufreq == 666)
|
||||
cpufreq = 667;
|
||||
}
|
||||
return cpufreq;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : MachineSpecificConfig
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Checks for machine specifc features such as MMX support
|
||||
* sets approipriate flags and function pointers.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
#define MMX_ENABLED 1
|
||||
void VP5_DMachineSpecificConfig(void)
|
||||
{
|
||||
INT32 MmxEnabled;
|
||||
INT32 XmmEnabled;
|
||||
INT32 WmtEnabled;
|
||||
|
||||
GetProcessorFlags( &MmxEnabled,&XmmEnabled,&WmtEnabled);
|
||||
|
||||
|
||||
// If MMX supported then set to use MMX versions of functions else
|
||||
// use original 'C' versions.
|
||||
|
||||
if(WmtEnabled) //Willamette
|
||||
{
|
||||
VP5_BuildQuantIndex = VP5_BuildQuantIndex_ForWMT;
|
||||
}
|
||||
else if ( MmxEnabled )
|
||||
{
|
||||
VP5_BuildQuantIndex = VP5_BuildQuantIndex_ForMMX;
|
||||
}
|
||||
else
|
||||
{
|
||||
VP5_BuildQuantIndex = VP5_BuildQuantIndex_Generic;
|
||||
}
|
||||
|
||||
// ReadTokens = ReadTokensPredict_c;
|
||||
|
||||
}
|
||||
|
||||
// Issues a warning message
|
||||
void VP5_IssueWarning( char * WarningMessage )
|
||||
{
|
||||
// Issue the warning messge
|
||||
MessageBox(NULL, WarningMessage, NULL, MB_ICONEXCLAMATION | MB_TASKMODAL );
|
||||
}
|
||||
|
||||
// Pause/Sleep for a X milliseconds
|
||||
void VP5_PauseProcess( unsigned int SleepMs )
|
||||
{
|
||||
Sleep( SleepMs );
|
||||
}
|
||||
|
||||
char * VP5_SytemGlobalAlloc( unsigned int Size )
|
||||
{
|
||||
return GlobalAlloc( GPTR, Size );
|
||||
}
|
||||
|
||||
void VP5_SystemGlobalFree( char * MemPtr )
|
||||
{
|
||||
GlobalFree( (HGLOBAL) MemPtr );
|
||||
}
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_SetPbParam
|
||||
*
|
||||
* INPUTS : PB_COMMAND_TYPE Command
|
||||
* char * Parameter
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Generalised command interface to decoder.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void CCONV VP5_SetPbParam( PB_INSTANCE *pbi, PB_COMMAND_TYPE Command, UINT32 Parameter )
|
||||
{
|
||||
|
||||
#if defined(POSTPROCESS)
|
||||
switch ( Command )
|
||||
{
|
||||
case PBC_SET_CPUFREE:
|
||||
{
|
||||
|
||||
double Pixels = pbi->Configuration.VideoFrameWidth * pbi->Configuration.VideoFrameHeight;
|
||||
double FreeMhz = pbi->ProcessorFrequency * Parameter / 100;
|
||||
double PixelsPerMhz = 100 * sqrt(1.0*Pixels) / FreeMhz;
|
||||
pbi->CPUFree = Parameter;
|
||||
|
||||
if( PixelsPerMhz > 150 )
|
||||
pbi->PostProcessingLevel = 0;
|
||||
else if( PixelsPerMhz > 100 )
|
||||
pbi->PostProcessingLevel = 8;
|
||||
else if( PixelsPerMhz > 90 )
|
||||
pbi->PostProcessingLevel = 4;
|
||||
else if( PixelsPerMhz > 80 )
|
||||
pbi->PostProcessingLevel = 5;
|
||||
else
|
||||
pbi->PostProcessingLevel = 6;
|
||||
break;
|
||||
|
||||
}
|
||||
case PBC_SET_REFERENCEFRAME:
|
||||
CopyFrame( pbi->postproc, (YUV_BUFFER_CONFIG *) Parameter, pbi->LastFrameRecon);
|
||||
CopyFrame( pbi->postproc, (YUV_BUFFER_CONFIG *) Parameter, pbi->GoldenFrame);
|
||||
break;
|
||||
|
||||
case PBC_SET_POSTPROC:
|
||||
if( Parameter == 9 )
|
||||
{
|
||||
VP5_SetPbParam( pbi, PBC_SET_CPUFREE, 70);
|
||||
}
|
||||
else
|
||||
|
||||
{
|
||||
pbi->CPUFree = 0;
|
||||
pbi->PostProcessingLevel = Parameter;
|
||||
}
|
||||
break;
|
||||
|
||||
case PBC_SET_DEINTERLACEMODE:
|
||||
pbi->DeInterlaceMode = Parameter;
|
||||
break;
|
||||
|
||||
case PBC_SET_BLACKCLAMP:
|
||||
pbi->BlackClamp = Parameter;
|
||||
break;
|
||||
|
||||
case PBC_SET_WHITECLAMP:
|
||||
pbi->WhiteClamp = Parameter;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
@@ -0,0 +1,377 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : quantindexmmx.c
|
||||
*
|
||||
* Description :
|
||||
*
|
||||
* AUTHOR :
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.03 JBB 15Nov00 Removed unnecessary ifdefs
|
||||
* 1.02 JBB 26Jul00 Removed unnecessary macro
|
||||
* 1.01 YWX 26 JUL 00 Bug Fixing, used WMT TI(x) for MMX processors
|
||||
* 1.00 SJL 14/04/00
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Frames
|
||||
*****************************************************************************
|
||||
*/
|
||||
#define STRICT /* Strict type checking. */
|
||||
#include "codec_common.h"
|
||||
#include "quantize.h"
|
||||
#define MIN16 ((1<<16)-1)
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Imported Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Imported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Foreward References
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Module Statics
|
||||
*****************************************************************************
|
||||
*/
|
||||
static UINT32 dequant_index[64] =
|
||||
{ 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
|
||||
};
|
||||
|
||||
static UINT32 dequant_indexMMX[64] =
|
||||
{
|
||||
0, 1, 5, 6, 14, 15, 27, 28,
|
||||
2, 4, 7, 13, 16, 26, 29, 42,
|
||||
3, 8, 12, 17, 25, 30, 41, 43,
|
||||
9, 11, 18, 24, 31, 40, 44, 53,
|
||||
10, 19, 23, 32, 39, 45, 52, 54,
|
||||
20, 22, 33, 38, 46, 51, 55, 60,
|
||||
21, 34, 37, 47, 50, 56, 59, 61,
|
||||
35, 36, 48, 49, 57, 58, 62, 63
|
||||
};
|
||||
/*
|
||||
used to unravel the coeffs in the proper order required by MMX_idct
|
||||
see mmxidct.cxx
|
||||
*/
|
||||
static UINT32 transIndexMMX[64] =
|
||||
{
|
||||
0, 8, 1, 2, 9, 16, 24, 17,
|
||||
10, 3, 32, 11, 18, 25, 4, 12,
|
||||
5, 26, 19, 40, 33, 34, 41, 48,
|
||||
27, 6, 13, 20, 28, 21, 14, 7,
|
||||
|
||||
56, 49, 42, 35, 43, 50, 57, 36,
|
||||
15, 22, 29, 30, 23, 44, 37, 58,
|
||||
51, 59, 38, 45, 52, 31, 60, 53,
|
||||
46, 39, 47, 54, 61, 62, 55, 63
|
||||
};
|
||||
|
||||
static UINT32 transIndexWMT[64] =
|
||||
{
|
||||
0, 8, 1, 2, 9, 16, 24, 17,
|
||||
10, 3, 4, 11, 18, 25, 32, 40,
|
||||
33, 26, 19, 12, 5, 6, 13, 20,
|
||||
27, 34, 41, 48, 56, 49, 42, 35,
|
||||
28, 21, 14, 7, 15, 22, 29, 36,
|
||||
43, 50, 57, 58, 51, 44, 37, 30,
|
||||
23, 31, 38, 45, 52, 59, 60, 53,
|
||||
46, 39, 47, 54, 61, 62, 55, 63
|
||||
};
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : BuildQuantIndex_ForMMX
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Builds the quant_index table in a transposed order.
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_BuildQuantIndex_ForMMX(QUANTIZER *pbi)
|
||||
{
|
||||
INT32 i,j;
|
||||
|
||||
pbi->transIndex = transIndexMMX;
|
||||
|
||||
// invert the dequant index into the quant index
|
||||
for ( i = 0; i < BLOCK_SIZE; i++ )
|
||||
{
|
||||
j = transIndexMMX[ dequant_indexMMX[i] ];
|
||||
pbi->quant_index[j] = i;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : BuildQuantIndex_ForWMT
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Builds the quant_index table in a transposed order.
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void VP5_BuildQuantIndex_ForWMT(QUANTIZER *pbi)
|
||||
{
|
||||
INT32 i,j;
|
||||
|
||||
pbi->transIndex = transIndexWMT;
|
||||
|
||||
// invert the dequant index into the quant index
|
||||
for ( i = 0; i < BLOCK_SIZE; i++ )
|
||||
{
|
||||
j = transIndexWMT[ dequant_indexMMX[i] ];
|
||||
pbi->quant_index[j] = i;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_quantize_wmt
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Builds the quant_index table in a transposed order.
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_quantize_wmt( QUANTIZER *pbi, INT16 * DCT_block, Q_LIST_ENTRY * quantized_list, UINT8 bp )
|
||||
{
|
||||
UINT32 i, j;
|
||||
|
||||
INT32 * QuantRoundPtr = pbi->QuantRound[QTableSelect[bp]];
|
||||
INT32 * QuantCoeffsPtr = pbi->QuantCoeffs[QTableSelect[bp]];
|
||||
INT32 * ZBinPtr = pbi->ZeroBinSize[QTableSelect[bp]];
|
||||
|
||||
INT16 * DCT_blockPtr = DCT_block;
|
||||
INT32 temp;
|
||||
INT32 NonZeroACs = 0;
|
||||
INT16 *round = &pbi->round[0];
|
||||
INT16 *mult = &pbi->mult[0];
|
||||
INT16 *zbin = &pbi->zbin[0];
|
||||
|
||||
// DC quantization
|
||||
temp = 0;
|
||||
if ( DCT_blockPtr[0] >= QuantRoundPtr[0] )
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] + QuantRoundPtr[0] ) ;
|
||||
else if ( DCT_blockPtr[0] <= -QuantRoundPtr[0] )
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] - QuantRoundPtr[0] ) + MIN16;
|
||||
quantized_list[0] = (Q_LIST_ENTRY) (temp>>16);
|
||||
|
||||
// this quantizer stores its results back in the source!!
|
||||
__asm
|
||||
{
|
||||
|
||||
// setup and collect registers
|
||||
mov esi, DCT_block
|
||||
xor ecx, ecx // index ptr
|
||||
mov edi, round
|
||||
movdqu xmm2, [edi] // get the round values
|
||||
mov edi, mult
|
||||
movdqu xmm3, [edi] // get the quantizer values
|
||||
mov edi, zbin
|
||||
movdqu xmm4, [edi] // get the zerobin values
|
||||
|
||||
// 8 coefficients at a time loop
|
||||
next8:
|
||||
movdqa xmm0, [esi+ecx] // get source values
|
||||
movdqa xmm1, xmm0 // sign bits of the abs values
|
||||
psraw xmm1, 15 // negative all 1's postive all 0's
|
||||
|
||||
// get the absolute value of the input values
|
||||
pxor xmm0, xmm1 // one's complement of negatives
|
||||
psubw xmm0, xmm1 // xmm0 = abs coeffs
|
||||
|
||||
// zero bin coefficients
|
||||
movdqa xmm5, xmm0
|
||||
pcmpgtw xmm5, xmm4 // ZBin > Coeffs
|
||||
pand xmm0, xmm5 // zerobined coefficients
|
||||
|
||||
// calculate & round quantizer
|
||||
paddw xmm0, xmm2 // Coeff + Quant Round
|
||||
pmulhuw xmm0, xmm3 // *QuantCoeffs >> 16
|
||||
|
||||
|
||||
// get back the sign bit
|
||||
pxor xmm0, xmm1 // ones complement of negatives
|
||||
psubw xmm0, xmm1 // negatives are back as negative
|
||||
|
||||
// output the results
|
||||
movdqa [esi+ecx], xmm0
|
||||
|
||||
// loop back to the next set
|
||||
add ecx, 16
|
||||
cmp ecx, 128
|
||||
jl next8
|
||||
}
|
||||
|
||||
// zigzagify
|
||||
for( i = 1; i < 64; i++)
|
||||
{
|
||||
// Zig Zag order
|
||||
j = dequant_index[i];
|
||||
quantized_list[i] = DCT_block[j];
|
||||
}
|
||||
|
||||
}
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_quantize_mmx
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Builds the quant_index table in a transposed order.
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_quantize_mmx( QUANTIZER *pbi, INT16 * DCT_block, Q_LIST_ENTRY * quantized_list, UINT8 bp )
|
||||
{
|
||||
UINT32 i, j;
|
||||
|
||||
INT32 * QuantRoundPtr = pbi->QuantRound[QTableSelect[bp]];
|
||||
INT32 * QuantCoeffsPtr = pbi->QuantCoeffs[QTableSelect[bp]];
|
||||
INT32 * ZBinPtr = pbi->ZeroBinSize[QTableSelect[bp]];
|
||||
|
||||
INT16 * DCT_blockPtr = DCT_block;
|
||||
INT32 temp;
|
||||
INT32 NonZeroACs = 0;
|
||||
INT16 *round = &pbi->round[0];
|
||||
INT16 *mult = &pbi->mult[0];
|
||||
INT16 *zbin = &pbi->zbin[0];
|
||||
|
||||
// DC quantization
|
||||
temp = 0;
|
||||
if ( DCT_blockPtr[0] >= QuantRoundPtr[0] )
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] + QuantRoundPtr[0] ) ;
|
||||
else if ( DCT_blockPtr[0] <= -QuantRoundPtr[0] )
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] - QuantRoundPtr[0] ) + MIN16;
|
||||
quantized_list[0] = (Q_LIST_ENTRY) (temp>>16);
|
||||
|
||||
// this quantizer stores its results back in the source!!
|
||||
__asm
|
||||
{
|
||||
|
||||
// setup and collect registers
|
||||
mov esi, DCT_block
|
||||
xor ecx, ecx // index ptr
|
||||
mov edi, round
|
||||
movq mm2, [edi] // get the round values
|
||||
mov edi, mult
|
||||
movq mm3, [edi] // get the quantizer values
|
||||
mov edi, zbin
|
||||
movq mm4, [edi] // get the zerobin values
|
||||
|
||||
// 8 coefficients at a time loop
|
||||
next4:
|
||||
movq mm0, [esi+ecx] // get source values
|
||||
movq mm1, mm0 // sign bits of the abs values
|
||||
psraw mm1, 15 // negative all 1's postive all 0's
|
||||
|
||||
// get the absolute value of the input values
|
||||
pxor mm0, mm1 // one's complement of negatives
|
||||
psubw mm0, mm1 // mm0 = abs coeffs
|
||||
|
||||
// zero bin coefficients
|
||||
movq mm5, mm0
|
||||
pcmpgtw mm5, mm4 // ZBin > Coeffs
|
||||
pand mm0, mm5 // zerobined coefficients
|
||||
|
||||
// calculate & round quantizer
|
||||
paddw mm0, mm2 // Coeff + Quant Round
|
||||
pmulhuw mm0, mm3 // *QuantCoeffs >> 16
|
||||
|
||||
|
||||
// get back the sign bit
|
||||
pxor mm0, mm1 // ones complement of negatives
|
||||
psubw mm0, mm1 // negatives are back as negative
|
||||
|
||||
// output the results
|
||||
movq [esi+ecx], mm0
|
||||
|
||||
// loop back to the next set
|
||||
add ecx, 8
|
||||
cmp ecx, 128
|
||||
jl next4
|
||||
}
|
||||
|
||||
// zigzagify
|
||||
for( i = 1; i < 64; i++)
|
||||
{
|
||||
// Zig Zag order
|
||||
j = dequant_index[i];
|
||||
quantized_list[i] = DCT_block[j];
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,147 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : Timer.C
|
||||
*
|
||||
* Description : Video CODEC timer module
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.01 PGW 09/07/99 Added code to support profile timing
|
||||
* 1.00 PGW 14/06/99 Configuration baseline
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
#define INC_WIN_HEADER 1
|
||||
#include <windows.h>
|
||||
|
||||
#include "type_aliases.h"
|
||||
#include <mmsystem.h>
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Module Static Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
// Used for calculation of elapsed time
|
||||
UINT32 LastCPUTime;
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : MyInitTimer
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Initialises the timer mechanism.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void MyInitTimer( void )
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : MyGetTime
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : Time in ms since startup.
|
||||
*
|
||||
* FUNCTION : Provides a model independant interface for getting times.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
UINT32 MyGetTime( void )
|
||||
{
|
||||
/* Use different timing mechanisms for win32 and win16.
|
||||
* The win16 method is accurate to 1ms whilst the Win32 is not garauteed to better than 16ms
|
||||
*/
|
||||
return timeGetTime();
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : MyGetElapsedCpuTime
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : CPU cycles since last call
|
||||
*
|
||||
* FUNCTION : Calculate the CPU cycles elapsed since the last call
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
UINT32 MyGetElapsedCpuTime( void )
|
||||
{
|
||||
UINT32 CurrCPUTime[2]; // Full 64 bit CPU time
|
||||
UINT32 CurrentCpuTime; // modified 32 bit current time
|
||||
UINT32 ElapsedTime;
|
||||
|
||||
__asm
|
||||
{
|
||||
rdtsc ; Get CPU time into EDX:EAX
|
||||
|
||||
mov dword ptr [CurrCPUTime], eax ; Save to a global
|
||||
mov dword ptr [CurrCPUTime+4], edx
|
||||
}
|
||||
|
||||
// Save CurrCPUTime to LastCPUTime
|
||||
CurrCPUTime[0] = (CurrCPUTime[0] >> 8);
|
||||
CurrCPUTime[1] = (CurrCPUTime[1] & 0x000000FF) << 24;
|
||||
CurrentCpuTime = CurrCPUTime[0] | CurrCPUTime[1];
|
||||
|
||||
// Check for wrapp around
|
||||
if ( CurrentCpuTime >= LastCPUTime )
|
||||
{
|
||||
ElapsedTime = CurrentCpuTime - LastCPUTime;
|
||||
}
|
||||
else
|
||||
{
|
||||
ElapsedTime = (LastCPUTime - CurrentCpuTime) + 0xFFFF;
|
||||
}
|
||||
LastCPUTime = CurrentCpuTime;
|
||||
|
||||
return ElapsedTime;
|
||||
}
|
||||
@@ -0,0 +1,380 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : DFrameR.C
|
||||
*
|
||||
* Description : Functions to read
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.18 YWX 17/dec/02 Added DeInterlacedMode setup
|
||||
* 1.17 YWX 05/08/02 Added initialization of postprocessor 's interlaced flag
|
||||
* 1.16 JBB 13 Jun 01 VP4 Code Clean Out
|
||||
* 1.15 AWG 08-Jun-01 Added support for DCT16
|
||||
* 1.14 JBB 04 May 01 Added set of ReadTokens Function for VP5
|
||||
* 1.13 JBB 04 Dec 00 Added new Center vs Scale Bits
|
||||
* 1.12 JBB 30 NOV 00 Version number changes
|
||||
* 1.11 JBB 14 Oct 00 Added ifdefs around version specific code
|
||||
* 1.10 PGW 06 Oct 00 QThreshTable[] made instance specific.
|
||||
* Changes to LoadFrameHeader() to call InitQTables().
|
||||
* 1.09 YWX 25 Aug 00 Added version number check
|
||||
* 1.08 JBB 22 Aug 00 Ansi C conversion
|
||||
* 1.07 JBB 27 Jul 00 Malloc checks
|
||||
* 1.06 PGW 20/03/00 Removed InterIntra mode flag.
|
||||
* 1.05 JBB 27/01/99 Globals Removed, use of PB_INSTANCE, Bit Management Functions
|
||||
* 1.04 PGW 17/12/99 Changes to Synch code to reflect the fact that 0 length
|
||||
* frames are no longer legal (simply not transmittedd)
|
||||
* Note that this change is only relevant to the live version
|
||||
* of the codec
|
||||
* 1.03 PGW 15/11/99 Added support for VP3 version ID.
|
||||
* 1.02 PGW 30/08/99 Use bit functions to read header data.
|
||||
* Changes to way bytes are read.
|
||||
* 1.01 PGW 16/08/99 Header changes for VFW version and key frames.
|
||||
* 1.00 PGW 22/06/99 pbi->Configuration baseline
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Frames
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
#include "pbdll.h"
|
||||
#include "duck_mem.h"
|
||||
#include "boolhuff.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define START_SIZE 0
|
||||
#define END_SIZE 1
|
||||
|
||||
#define READ_BUFFER_EMPTY_WAIT 20
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Module Statics
|
||||
***** ************************************************************************
|
||||
*/
|
||||
#ifndef MAPCA
|
||||
static const UINT32 loMaskTbl_VP31[] = { 0,
|
||||
1, 3, 7, 15,
|
||||
31, 63, 127, 255,
|
||||
0x1ff, 0x3ff, 0x7ff, 0xfff,
|
||||
0x1fff, 0x3fff, 0x7fff, 0xffff,
|
||||
0x1FFFF, 0x3FFFF, 0x7FFFF, 0xfFFFF,
|
||||
0x1fFFFF, 0x3fFFFF, 0x7fFFFF, 0xffFFFF,
|
||||
0x1ffFFFF, 0x3ffFFFF, 0x7ffFFFF, 0xfffFFFF,
|
||||
0x1fffFFFF, 0x3fffFFFF, 0x7fffFFFF, 0xffffFFFF
|
||||
};
|
||||
|
||||
static const UINT32 hiMaskTbl_VP31[] = { 0,
|
||||
0x80000000, 0xC0000000, 0xE0000000, 0xF0000000,
|
||||
0xF8000000, 0xFC000000, 0xFE000000, 0xFF000000,
|
||||
0xFF800000, 0xFFC00000, 0xFFE00000, 0xFFF00000,
|
||||
0xFFF80000, 0xFFFC0000, 0xFFFE0000, 0xFFFF0000,
|
||||
0xFFFF8000, 0xFFFFC000, 0xFFFFE000, 0xFFFFF000,
|
||||
0xFFFFF800, 0xFFFFFC00, 0xFFFFFE00, 0xFFFFFF00,
|
||||
0xFFFFFF80, 0xFFFFFFC0, 0xFFFFFFE0, 0xFFFFFFF0,
|
||||
0xFFFFFFF8, 0xFFFFFFFC, 0xFFFFFFFE, 0xFFFFFFFF
|
||||
};
|
||||
|
||||
#endif
|
||||
/****************************************************************************
|
||||
* Forward References.
|
||||
*****************************************************************************
|
||||
*/
|
||||
static BOOL LoadFrameHeader(PB_INSTANCE *pbi);
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : LoadFrame
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : FALSE if an Error is detected or the frame is empty else TRUE.
|
||||
*
|
||||
* FUNCTION : Loads a frame and decodes the fragment arrays.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
BOOL VP5_LoadFrame(PB_INSTANCE *pbi)
|
||||
{
|
||||
BOOL RetVal = TRUE;
|
||||
|
||||
// Initialise the bit extractor.
|
||||
//ExtractInit(pbi);
|
||||
|
||||
// Load the frame header (including the frame size).
|
||||
if ( !LoadFrameHeader(pbi) )
|
||||
{
|
||||
RetVal = FALSE;
|
||||
}
|
||||
|
||||
return RetVal;
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : LoadFrameHeader
|
||||
*
|
||||
* INPUTS : fptr - The file pointer for the data file.
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : FALSE if and Error is detected else TRUE.
|
||||
*
|
||||
* FUNCTION : Loads and interprets the frame header.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
// VFW codec version
|
||||
#define ROUNDUP32(X) ( ( ( (unsigned long) X ) + 31 )&( 0xFFFFFFE0 ) )
|
||||
static BOOL LoadFrameHeader(PB_INSTANCE *pbi)
|
||||
{
|
||||
UINT8 VersionByte0; // Must be 0 for VP30b and later
|
||||
UINT8 DctQMask;
|
||||
UINT8 SpareBits; // Spare cfg bits
|
||||
UINT8 Unused;
|
||||
|
||||
BOOL RetVal = TRUE;
|
||||
|
||||
// Is the frame and inter frame or a key frame
|
||||
pbi->FrameType = DecodeBool(&pbi->br, 128);
|
||||
|
||||
// unused bit
|
||||
Unused = DecodeBool(&pbi->br, 128);
|
||||
|
||||
// Quality (Q) index
|
||||
DctQMask = (UINT8)VP5_bitread( &pbi->br, 6 );
|
||||
|
||||
|
||||
// If the frame was a base frame then read the frame dimensions and build a bitmap structure.
|
||||
if ( (pbi->FrameType == BASE_FRAME) )
|
||||
{
|
||||
// Read the frame dimensions bytes (0,0 indicates vp31 or later)
|
||||
VersionByte0 = (UINT8)VP5_bitread( &pbi->br, 8 );
|
||||
pbi->Vp3VersionNo = (UINT8)VP5_bitread( &pbi->br, 5 );
|
||||
|
||||
if(pbi->Vp3VersionNo > CURRENT_DECODE_VERSION)
|
||||
{
|
||||
RetVal = FALSE;
|
||||
return RetVal;
|
||||
}
|
||||
// Initialise version specific quantiser values
|
||||
VP5_InitQTables( pbi->quantizer, pbi->Vp3VersionNo );
|
||||
|
||||
// Read the type / coding method for the key frame.
|
||||
pbi->KeyFrameType = (UINT8)DecodeBool(&pbi->br, 128);
|
||||
|
||||
SpareBits = (UINT8)DecodeBool(&pbi->br, 128);
|
||||
|
||||
// is this keyframe section of the file interlaced
|
||||
pbi->Configuration.Interlaced = (UINT32)DecodeBool(&pbi->br, 128);
|
||||
#ifndef MAPCA
|
||||
SetPPInterlacedMode(pbi->postproc, pbi->Configuration.Interlaced);
|
||||
if(pbi->Configuration.Interlaced)
|
||||
{
|
||||
SetDeInterlaceMode(pbi->postproc, pbi->DeInterlaceMode);
|
||||
}
|
||||
#endif
|
||||
// Spare config bits
|
||||
{
|
||||
UINT32 HFragments;
|
||||
UINT32 VFragments;
|
||||
UINT32 HOldScaled;
|
||||
UINT32 VOldScaled;
|
||||
UINT32 HNewScaled;
|
||||
UINT32 VNewScaled;
|
||||
UINT32 OutputHFragments;
|
||||
UINT32 OutputVFragments;
|
||||
|
||||
VFragments = 2 * ((UINT8)VP5_bitread( &pbi->br, 8 ));
|
||||
HFragments = 2 * ((UINT8)VP5_bitread( &pbi->br, 8 ));
|
||||
|
||||
OutputVFragments = 2 * ((UINT8)VP5_bitread( &pbi->br, 8 ));
|
||||
OutputHFragments = 2 * ((UINT8)VP5_bitread( &pbi->br, 8 ));
|
||||
|
||||
if(pbi->Configuration.HRatio == 0)
|
||||
pbi->Configuration.HRatio = 1;
|
||||
|
||||
if(pbi->Configuration.VRatio == 0)
|
||||
pbi->Configuration.VRatio = 1;
|
||||
|
||||
HOldScaled = pbi->Configuration.HScale * pbi->HFragments * 8 / pbi->Configuration.HRatio;
|
||||
VOldScaled = pbi->Configuration.VScale * pbi->VFragments * 8 / pbi->Configuration.VRatio;
|
||||
|
||||
pbi->Configuration.ExpandedFrameWidth = OutputHFragments * 8;
|
||||
pbi->Configuration.ExpandedFrameHeight = OutputVFragments * 8;
|
||||
|
||||
if(VFragments >= OutputVFragments)
|
||||
{
|
||||
pbi->Configuration.VScale = 1;
|
||||
pbi->Configuration.VRatio = 1;
|
||||
}
|
||||
else if (5*VFragments >= 4*OutputVFragments)
|
||||
{
|
||||
pbi->Configuration.VScale = 5;
|
||||
pbi->Configuration.VRatio = 4;
|
||||
}
|
||||
else if (5*VFragments >= 3*OutputVFragments)
|
||||
{
|
||||
pbi->Configuration.VScale = 5;
|
||||
pbi->Configuration.VRatio = 3;
|
||||
}
|
||||
else
|
||||
{
|
||||
pbi->Configuration.VScale = 2;
|
||||
pbi->Configuration.VRatio = 1;
|
||||
}
|
||||
|
||||
if(HFragments >= OutputHFragments)
|
||||
{
|
||||
pbi->Configuration.HScale = 1;
|
||||
pbi->Configuration.HRatio = 1;
|
||||
}
|
||||
else if (5*HFragments >= 4*OutputHFragments)
|
||||
{
|
||||
pbi->Configuration.HScale = 5;
|
||||
pbi->Configuration.HRatio = 4;
|
||||
}
|
||||
else if (5*HFragments >= 3*OutputHFragments)
|
||||
{
|
||||
pbi->Configuration.HScale = 5;
|
||||
pbi->Configuration.HRatio = 3;
|
||||
}
|
||||
else
|
||||
{
|
||||
pbi->Configuration.HScale = 2;
|
||||
pbi->Configuration.HRatio = 1;
|
||||
}
|
||||
|
||||
HNewScaled = pbi->Configuration.HScale * HFragments * 8 / pbi->Configuration.HRatio;
|
||||
VNewScaled = pbi->Configuration.VScale * VFragments * 8 / pbi->Configuration.VRatio;
|
||||
|
||||
pbi->ScaleWidth = HNewScaled;
|
||||
pbi->ScaleHeight = VNewScaled;
|
||||
|
||||
pbi->Configuration.ScalingMode = ((UINT32)VP5_bitread( &pbi->br, 2 ));
|
||||
|
||||
// we have a new input size
|
||||
if( VFragments != pbi->VFragments ||
|
||||
HFragments != pbi->HFragments)
|
||||
{
|
||||
// Validate the combination of height and width.
|
||||
pbi->Configuration.VideoFrameWidth = HFragments*8;
|
||||
pbi->Configuration.VideoFrameHeight = VFragments*8;
|
||||
VP5_InitFrameDetails(pbi);
|
||||
}
|
||||
|
||||
|
||||
// we have a new intermediate buffer clean the screen
|
||||
if( pbi->ScaleBuffer != 0 &&
|
||||
(HOldScaled != HNewScaled ||
|
||||
VOldScaled != VNewScaled ) )
|
||||
{
|
||||
// turn the screen black!!
|
||||
memset(pbi->ScaleBuffer, 0x0, (pbi->OutputWidth+32) * (pbi->OutputHeight+32) );
|
||||
memset(pbi->ScaleBuffer + (pbi->OutputWidth+32) * (pbi->OutputHeight+32),
|
||||
0x80, (pbi->OutputWidth+32) * (pbi->OutputHeight+32) / 2 );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Set this frame quality value from Q Index
|
||||
pbi->quantizer->FrameQIndex = DctQMask;
|
||||
#ifdef MAPCA
|
||||
SetFLimit(DctQMask);
|
||||
SetSimpleDeblockFlimit(DctQMask);
|
||||
#endif
|
||||
pbi->quantizer->ThisFrameQuantizerValue = pbi->quantizer->QThreshTable[DctQMask];
|
||||
VP5_UpdateQ( pbi->quantizer, pbi->Vp3VersionNo );
|
||||
|
||||
return RetVal;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_SetFrameType
|
||||
*
|
||||
* INPUTS : A Frame type.
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Sets the current frame type.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_SetFrameType( PB_INSTANCE *pbi,UINT8 FrType )
|
||||
{
|
||||
/* Set the appropriate frame type according to the request. */
|
||||
switch ( FrType )
|
||||
{
|
||||
|
||||
case BASE_FRAME:
|
||||
pbi->FrameType = FrType;
|
||||
break;
|
||||
|
||||
default:
|
||||
pbi->FrameType = FrType;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_GetFrameType
|
||||
*
|
||||
* INPUTS : None.
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : The current frame type.
|
||||
*
|
||||
* FUNCTION : Gets the current frame type.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
UINT8 VP5_GetFrameType(PB_INSTANCE *pbi)
|
||||
{
|
||||
return pbi->FrameType;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,198 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : SystemDependant.c
|
||||
*
|
||||
* Description : Miscellaneous system dependant functions
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.20 YWX 06-Nov-01 Configuration Baseline for C only version
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#include "pbdll.h"
|
||||
|
||||
extern void GetProcessorFlags(INT32 *MmxEnabled, INT32 *XmmEnabled, INT32 *WmtEnabled);
|
||||
|
||||
//extern void ReadTokens_c(PB_INSTANCE *pbi, INT32 * HuffIndices );
|
||||
extern void (*VP5_BuildQuantIndex)( QUANTIZER * pbi);
|
||||
|
||||
extern void UnPackVideo_C(PB_INSTANCE *pbi);
|
||||
extern void UnPackVideo2(PB_INSTANCE *pbi);
|
||||
|
||||
extern void VP5_BuildQuantIndex_Generic(QUANTIZER *pbi);
|
||||
|
||||
/****************************************************************************
|
||||
* Explicit imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
extern unsigned int CPUFrequency;
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Module statics.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : GetProcessorFrequency()
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
*
|
||||
* OUTPUTS : The Frequency in MHZ
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Check the Processor's working freqency
|
||||
*
|
||||
* SPECIAL NOTES : This function should only be used here. Limited tests
|
||||
* has verified it works till 166MHz Pentium with MMX.
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
unsigned long VP5_GetProcessorFrequency()
|
||||
{
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : MachineSpecificConfig
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Checks for machine specifc features such as MMX support
|
||||
* sets approipriate flags and function pointers.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_DMachineSpecificConfig(void)
|
||||
{
|
||||
VP5_BuildQuantIndex = VP5_BuildQuantIndex_Generic;
|
||||
}
|
||||
|
||||
// Issues a warning message
|
||||
void VP5_IssueWarning( char * WarningMessage )
|
||||
{
|
||||
(void) WarningMessage;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_SetPbParam
|
||||
*
|
||||
* INPUTS : PB_COMMAND_TYPE Command
|
||||
* char * Parameter
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Generalised command interface to decoder.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void CCONV VP5_SetPbParam( PB_INSTANCE *pbi, PB_COMMAND_TYPE Command, UINT32 Parameter )
|
||||
{
|
||||
|
||||
#if defined(POSTPROCESS)
|
||||
switch ( Command )
|
||||
{
|
||||
case PBC_SET_CPUFREE:
|
||||
{
|
||||
|
||||
double PixelsPerMhz = 100 *10;
|
||||
pbi->CPUFree = Parameter;
|
||||
|
||||
if( PixelsPerMhz > 150 )
|
||||
pbi->PostProcessingLevel = 0;
|
||||
else if( PixelsPerMhz > 100 )
|
||||
pbi->PostProcessingLevel = 8;
|
||||
else if( PixelsPerMhz > 90 )
|
||||
pbi->PostProcessingLevel = 4;
|
||||
else if( PixelsPerMhz > 80 )
|
||||
pbi->PostProcessingLevel = 5;
|
||||
else
|
||||
pbi->PostProcessingLevel = 6;
|
||||
break;
|
||||
|
||||
}
|
||||
case PBC_SET_REFERENCEFRAME:
|
||||
break;
|
||||
|
||||
case PBC_SET_POSTPROC:
|
||||
if( Parameter == 9 )
|
||||
{
|
||||
VP5_SetPbParam( pbi, PBC_SET_CPUFREE, 70);
|
||||
}
|
||||
else
|
||||
|
||||
{
|
||||
pbi->CPUFree = 0;
|
||||
pbi->PostProcessingLevel = Parameter;
|
||||
}
|
||||
break;
|
||||
|
||||
case PBC_SET_DEINTERLACEMODE:
|
||||
pbi->DeInterlaceMode = Parameter;
|
||||
break;
|
||||
|
||||
case PBC_SET_BLACKCLAMP:
|
||||
pbi->BlackClamp = Parameter;
|
||||
break;
|
||||
|
||||
case PBC_SET_WHITECLAMP:
|
||||
pbi->WhiteClamp = Parameter;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
@@ -0,0 +1,484 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : FrameIni.c
|
||||
*
|
||||
* Description : Video CODEC playback module
|
||||
*
|
||||
* AUTHOR : JimBankoski
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.21 YWX 06-Nov-01 Changed to align the MB coeffs buffer memory
|
||||
* 1.20 JBB 13-Jun-01 VP4 Code Clean Out
|
||||
* 1.19 AWG 11-Jun-01 Added support for DCT16
|
||||
* 1.18 JBB 24-May-01 Fixed Memory Allocation problem and frame recon prob
|
||||
* 1.17 JBB 09-Apr-01 CPUFree persistence
|
||||
* 1.16 SJL 05-Apr-01 Fixed MAC compile errors.
|
||||
* 1.15 JBB 23-Mar-01 New DC prediction
|
||||
* 1.14 JBX 22-Mar-01 Merged with vp4-mapca bitstream
|
||||
* 1.13 JBB 30 NOV 00 Version number changes
|
||||
* 1.12 JBB 15-NOV-00 cleaned out ifdefs
|
||||
* 1.11 JBB 17-oct-00 Ifdefs around version information
|
||||
* 1.10 YWX 17-Oct-00 Added Initialization of block coordinates for
|
||||
* new loop filtering strategy
|
||||
* 1.09 YWX 11-Oct-00 Added LastFrameNoMvRecon and LastFrameNoMvReconAlloc
|
||||
* 1.08 SJL 25 Aug 00 Fixed Mac compile error
|
||||
* 1.08 JBB 24 Aug 00 Removed extraneous definition of load and decode
|
||||
* 1.07 SJL 16 Aug 00 Fixed Mac compile error
|
||||
* 1.06 JBB 28 jul 00 Added fragment variance array for post processor
|
||||
* 1.05 JBB 27Jul00 Added checks on Mallocs
|
||||
* 1.04 SJL 24Jul00 Changed Frees to DUCK_FREE for Mac utilization
|
||||
* 1.03 YWX 08/05/00 Added #if defined(POSTPROCESS) for postprocess
|
||||
* 1.02 JBB 05/05/00 Added Post Processing Buffer & Block Quality Buffers
|
||||
* 1.01 YWX 06/04/00 Alligned more buffers for speed
|
||||
* 1.00 JBB 27/01/99 Globals Removed, use of PB_INSTANCE, common between
|
||||
* compressor and decompressor
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#include "pbdll.h"
|
||||
#include "stdlib.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Module Static Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
static const struct
|
||||
{
|
||||
INT32 row;
|
||||
INT32 col;
|
||||
} NearMacroBlocks[12] =
|
||||
{
|
||||
{ -1, 0 },
|
||||
{ 0, -1 },
|
||||
{ -1, -1 },
|
||||
{ -1, 1 },
|
||||
{ -2, 0 },
|
||||
{ 0, -2 },
|
||||
{ -1, -2 },
|
||||
{ -2, -1 },
|
||||
{ -2, 1 },
|
||||
{ -1, 2 },
|
||||
{ -2, -2 },
|
||||
{ -2, 2 }
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
* Forward References
|
||||
*****************************************************************************
|
||||
*/
|
||||
void InitializeFragCoordinates(PB_INSTANCE *pbi);
|
||||
/****************************************************************************
|
||||
* Explicit Imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
#include "duck_mem.h"
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DeleteFragmentInfo
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_DeleteFragmentInfo(PB_INSTANCE * pbi)
|
||||
{
|
||||
|
||||
// free prior allocs if present
|
||||
#ifndef MAPCA
|
||||
if( pbi->mbi.CoeffsAlloc)
|
||||
duck_free(pbi->mbi.CoeffsAlloc);
|
||||
pbi->mbi.CoeffsAlloc = 0;
|
||||
pbi->mbi.Coeffs=0;
|
||||
#endif
|
||||
|
||||
if( pbi->FragInfoAlloc)
|
||||
duck_free(pbi->FragInfoAlloc);
|
||||
pbi->FragInfoAlloc = 0;
|
||||
pbi->FragInfo = 0;
|
||||
|
||||
if( pbi->fc.AboveYAlloc)
|
||||
duck_free(pbi->fc.AboveYAlloc);
|
||||
pbi->fc.AboveYAlloc = 0;
|
||||
pbi->fc.AboveY = 0;
|
||||
|
||||
if( pbi->fc.AboveUAlloc)
|
||||
duck_free(pbi->fc.AboveUAlloc);
|
||||
pbi->fc.AboveUAlloc = 0;
|
||||
pbi->fc.AboveU = 0;
|
||||
|
||||
if( pbi->fc.AboveVAlloc)
|
||||
duck_free(pbi->fc.AboveVAlloc);
|
||||
pbi->fc.AboveVAlloc = 0;
|
||||
pbi->fc.AboveV = 0;
|
||||
|
||||
if( pbi->MBInterlacedAlloc)
|
||||
duck_free(pbi->MBInterlacedAlloc);
|
||||
pbi->MBInterlacedAlloc = 0;
|
||||
pbi->MBInterlaced = 0;
|
||||
|
||||
if( pbi->MBMotionVectorAlloc)
|
||||
duck_free(pbi->MBMotionVectorAlloc);
|
||||
pbi->MBMotionVectorAlloc = 0;
|
||||
pbi->MBMotionVector = 0;
|
||||
|
||||
if( pbi->predictionModeAlloc)
|
||||
duck_free(pbi->predictionModeAlloc);
|
||||
pbi->predictionModeAlloc = 0;
|
||||
pbi->predictionMode = 0;
|
||||
|
||||
#ifdef MAPCA
|
||||
if(pbi->ReferenceBlocksAlloc)
|
||||
duck_free(pbi->ReferenceBlocksAlloc);
|
||||
pbi->ReferenceBlocksAlloc = 0;
|
||||
pbi->ReferenceBlocks = 0;
|
||||
|
||||
if(pbi->ReconstructedMBsAlloc)
|
||||
duck_free(pbi->ReconstructedMBsAlloc);
|
||||
pbi->ReconstructedMBsAlloc=0;
|
||||
pbi->ReconstructedMBs =0;
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : AllocateFragmentInfo
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
#define ROUNDUP32(X) ( ( ( (unsigned long) X ) + 31 )&( 0xFFFFFFE0 ) )
|
||||
BOOL VP5_AllocateFragmentInfo(PB_INSTANCE * pbi)
|
||||
{
|
||||
|
||||
// clear any existing info
|
||||
VP5_DeleteFragmentInfo(pbi);
|
||||
#ifndef MAPCA
|
||||
pbi->mbi.CoeffsAlloc = (Q_LIST_ENTRY(*)[72]) duck_malloc(32 + sizeof(Q_LIST_ENTRY)*72*6, DMEM_GENERAL);
|
||||
if(!pbi->mbi.CoeffsAlloc) {VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->mbi.Coeffs = (Q_LIST_ENTRY(*)[72])ROUNDUP32(pbi->mbi.CoeffsAlloc);
|
||||
#endif
|
||||
// context allocations
|
||||
pbi->fc.AboveYAlloc = (BLOCK_CONTEXTA *) duck_malloc(32 + (8+pbi->HFragments) * sizeof(BLOCK_CONTEXT), DMEM_GENERAL);
|
||||
if(!pbi->fc.AboveYAlloc) { VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->fc.AboveY = (BLOCK_CONTEXTA *) ROUNDUP32(pbi->fc.AboveYAlloc);
|
||||
|
||||
pbi->fc.AboveUAlloc = (BLOCK_CONTEXTA *) duck_malloc(32 + (8+pbi->HFragments / 2) * sizeof(BLOCK_CONTEXT), DMEM_GENERAL);
|
||||
if(!pbi->fc.AboveUAlloc) { VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->fc.AboveU = (BLOCK_CONTEXTA *) ROUNDUP32(pbi->fc.AboveUAlloc);
|
||||
|
||||
pbi->fc.AboveVAlloc = (BLOCK_CONTEXTA *) duck_malloc(32 + (8+pbi->HFragments / 2) * sizeof(BLOCK_CONTEXT), DMEM_GENERAL);
|
||||
if(!pbi->fc.AboveVAlloc) { VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->fc.AboveV = (BLOCK_CONTEXTA *) ROUNDUP32(pbi->fc.AboveVAlloc);
|
||||
|
||||
|
||||
// the encoder is the only thing using this move it to compdll
|
||||
pbi->MBInterlacedAlloc = (char *) duck_malloc(32+pbi->MacroBlocks * sizeof(char), DMEM_GENERAL);
|
||||
if(!pbi->MBInterlacedAlloc) { VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->MBInterlaced = (char *) ROUNDUP32(pbi->MBInterlacedAlloc );
|
||||
|
||||
pbi->predictionModeAlloc = (char *) duck_malloc(32+pbi->MacroBlocks * sizeof(char), DMEM_GENERAL);
|
||||
if(!pbi->predictionModeAlloc) { VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->predictionMode = (char *) ROUNDUP32(pbi->predictionModeAlloc );
|
||||
|
||||
pbi->MBMotionVectorAlloc = (MOTION_VECTORA *) duck_malloc(32+pbi->MacroBlocks * sizeof(MOTION_VECTORA ), DMEM_GENERAL);
|
||||
if(!pbi->MBMotionVectorAlloc) { VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->MBMotionVector = (MOTION_VECTORA *) ROUNDUP32(pbi->MBMotionVectorAlloc );
|
||||
|
||||
|
||||
// the encoder is the only thing using this move it to compdll
|
||||
pbi->FragInfoAlloc = (FRAG_INFO *) duck_malloc(32+pbi->UnitFragments * sizeof(FRAG_INFO), DMEM_GENERAL);
|
||||
if(!pbi->FragInfoAlloc) { VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->FragInfo = (FRAG_INFO *) ROUNDUP32(pbi->FragInfoAlloc );
|
||||
|
||||
|
||||
#ifdef MAPCA
|
||||
pbi->ReferenceBlocksAlloc=(UINT8(*)[192])duck_malloc(32 + 6*192, DMEM_GENERAL);
|
||||
if(!pbi->ReferenceBlocksAlloc){ VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->ReferenceBlocks = (UINT8(*)[192])ROUNDUP32(pbi->ReferenceBlocksAlloc);
|
||||
|
||||
pbi->ReconstructedMBsAlloc = (UINT8*) duck_malloc(32 + 768, DMEM_GENERAL);
|
||||
if(!pbi->ReconstructedMBsAlloc){ VP5_DeleteFragmentInfo(pbi); return FALSE;}
|
||||
pbi->ReconstructedMBs = (UINT8*) ROUNDUP32(pbi->ReconstructedMBsAlloc);
|
||||
#endif
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DeleteFrameInfo
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_DeleteFrameInfo(PB_INSTANCE * pbi)
|
||||
{
|
||||
if(pbi->ThisFrameReconAlloc )
|
||||
duck_free(pbi->ThisFrameReconAlloc );
|
||||
if(pbi->GoldenFrameAlloc)
|
||||
duck_free(pbi->GoldenFrameAlloc);
|
||||
if(pbi->LastFrameReconAlloc)
|
||||
duck_free(pbi->LastFrameReconAlloc);
|
||||
if(pbi->PostProcessBufferAlloc)
|
||||
duck_free(pbi->PostProcessBufferAlloc);
|
||||
|
||||
pbi->ThisFrameReconAlloc = 0;
|
||||
pbi->GoldenFrameAlloc = 0;
|
||||
pbi->LastFrameReconAlloc = 0;
|
||||
pbi->PostProcessBufferAlloc = 0;
|
||||
|
||||
pbi->ThisFrameRecon = 0;
|
||||
pbi->GoldenFrame = 0;
|
||||
pbi->LastFrameRecon = 0;
|
||||
pbi->PostProcessBufferAlloc = 0;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : AllocateFrameInfo
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
BOOL VP5_AllocateFrameInfo(PB_INSTANCE * pbi, unsigned int FrameSize)
|
||||
{
|
||||
|
||||
// clear any existing info
|
||||
VP5_DeleteFrameInfo(pbi);
|
||||
|
||||
// allocate frames
|
||||
|
||||
// (JBB+YX ) Added 2 extra lines to framebuffer so that copy12x12
|
||||
// doesn't fail when we have a large motion vector in V
|
||||
// on the last v block. Note : We never use these pixels
|
||||
// anyway so this doesn't hurt anything
|
||||
|
||||
pbi->ThisFrameReconAlloc = (UINT8 *)duck_malloc(32+pbi->Configuration.YStride+FrameSize*sizeof(YUV_BUFFER_ENTRY), DMEM_GENERAL);
|
||||
if(!pbi->ThisFrameReconAlloc) { VP5_DeleteFrameInfo(pbi); return FALSE;}
|
||||
|
||||
pbi->GoldenFrameAlloc = (UINT8 *)duck_malloc(32+pbi->Configuration.YStride+FrameSize*sizeof(YUV_BUFFER_ENTRY ), DMEM_GENERAL);
|
||||
if(!pbi->GoldenFrameAlloc) { VP5_DeleteFrameInfo(pbi); return FALSE;}
|
||||
|
||||
pbi->LastFrameReconAlloc = (UINT8 *)duck_malloc(32+pbi->Configuration.YStride+FrameSize*sizeof(YUV_BUFFER_ENTRY), DMEM_GENERAL);
|
||||
if(!pbi->LastFrameReconAlloc) { VP5_DeleteFrameInfo(pbi); return FALSE;}
|
||||
|
||||
pbi->PostProcessBufferAlloc = (UINT8 *)duck_malloc(32+pbi->Configuration.YStride+FrameSize*sizeof(YUV_BUFFER_ENTRY), DMEM_GENERAL);
|
||||
if(!pbi->PostProcessBufferAlloc) { VP5_DeleteFrameInfo(pbi); return FALSE;}
|
||||
|
||||
|
||||
// adjust up to the next 32 byte boundary
|
||||
pbi->ThisFrameRecon = (unsigned char *) ROUNDUP32(pbi->ThisFrameReconAlloc );
|
||||
pbi->GoldenFrame = (unsigned char *) ROUNDUP32(pbi->GoldenFrameAlloc );
|
||||
pbi->LastFrameRecon = (unsigned char *) ROUNDUP32(pbi->LastFrameReconAlloc );
|
||||
pbi->PostProcessBuffer = (unsigned char *) ROUNDUP32( pbi->PostProcessBufferAlloc );
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_InitFrameDetails
|
||||
*
|
||||
* INPUTS : Nonex.
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Initialises the frame details.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
BOOL VP5_InitFrameDetails(PB_INSTANCE *pbi)
|
||||
{
|
||||
int FrameSize;
|
||||
UINT32 i;
|
||||
|
||||
if(pbi->CPUFree > 0 )
|
||||
VP5_SetPbParam( pbi, PBC_SET_CPUFREE, pbi->CPUFree );
|
||||
|
||||
/* Set the frame size etc. */
|
||||
pbi->YPlaneSize = pbi->Configuration.VideoFrameWidth * pbi->Configuration.VideoFrameHeight;
|
||||
pbi->UVPlaneSize = pbi->YPlaneSize / 4;
|
||||
pbi->HFragments = pbi->Configuration.VideoFrameWidth / pbi->Configuration.HFragPixels;
|
||||
pbi->VFragments = pbi->Configuration.VideoFrameHeight / pbi->Configuration.VFragPixels;
|
||||
pbi->UnitFragments = ((pbi->VFragments * pbi->HFragments)*3)/2;
|
||||
pbi->YPlaneFragments = pbi->HFragments * pbi->VFragments;
|
||||
pbi->UVPlaneFragments = pbi->YPlaneFragments / 4;
|
||||
|
||||
pbi->Configuration.YStride = (pbi->Configuration.VideoFrameWidth + STRIDE_EXTRA);
|
||||
pbi->Configuration.UVStride = pbi->Configuration.YStride / 2;
|
||||
pbi->ReconYPlaneSize = pbi->Configuration.YStride * (pbi->Configuration.VideoFrameHeight + STRIDE_EXTRA);
|
||||
pbi->ReconUVPlaneSize = pbi->ReconYPlaneSize / 4;
|
||||
FrameSize = pbi->ReconYPlaneSize + 2 * pbi->ReconUVPlaneSize;
|
||||
|
||||
pbi->YDataOffset = 0;
|
||||
pbi->UDataOffset = pbi->YPlaneSize;
|
||||
pbi->VDataOffset = pbi->YPlaneSize + pbi->UVPlaneSize;
|
||||
pbi->ReconYDataOffset = 0;//(pbi->Configuration.YStride * UMV_BORDER) + UMV_BORDER;
|
||||
pbi->ReconUDataOffset = pbi->ReconYPlaneSize;// + (pbi->Configuration.UVStride * (UMV_BORDER/2)) + (UMV_BORDER/2);
|
||||
pbi->ReconVDataOffset = pbi->ReconYPlaneSize + pbi->ReconUVPlaneSize;// + (pbi->Configuration.UVStride * (UMV_BORDER/2)) + (UMV_BORDER/2);
|
||||
|
||||
// Image dimensions in Macro-Blocks
|
||||
pbi->MBRows = 4+(pbi->Configuration.VideoFrameHeight/16) + ( pbi->Configuration.VideoFrameHeight%16 ? 1 : 0 );
|
||||
pbi->MBCols = 4+(pbi->Configuration.VideoFrameWidth/16) + ( pbi->Configuration.VideoFrameWidth%16 ? 1 : 0 );
|
||||
pbi->MacroBlocks = pbi->MBRows * pbi->MBCols;
|
||||
|
||||
|
||||
for(i=0;i<12;i++)
|
||||
{
|
||||
pbi->mvNearOffset[i] = MBOffset(NearMacroBlocks[i].row, NearMacroBlocks[i].col);
|
||||
}
|
||||
#ifndef MAPCA
|
||||
ChangePostProcConfiguration(pbi->postproc, &pbi->Configuration);
|
||||
#endif
|
||||
if(!VP5_AllocateFragmentInfo(pbi))
|
||||
return FALSE;
|
||||
|
||||
if(!VP5_AllocateFrameInfo(pbi, FrameSize))
|
||||
{
|
||||
VP5_DeleteFragmentInfo(pbi);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// We have a differently output size than our scaling provides
|
||||
if( pbi->ScaleBuffer == 0 && pbi->OutputWidth &&
|
||||
(pbi->Configuration.VideoFrameWidth != pbi->OutputWidth ||
|
||||
pbi->Configuration.VideoFrameHeight != pbi->OutputHeight ) )
|
||||
{
|
||||
// we add 32 to outputwidth to insure that we have enough to overscale (ie scale to a size that's bigger
|
||||
// than our output size) we do this now even though we don't use it so that we don't have to check border conditions
|
||||
pbi->ScaleBufferAlloc = (UINT8 *)
|
||||
duck_malloc(32 + 3 *
|
||||
(pbi->OutputWidth + 32) *
|
||||
(pbi->OutputHeight + 32)*
|
||||
sizeof(YUV_BUFFER_ENTRY) / 2, DMEM_GENERAL);
|
||||
|
||||
pbi->ScaleBuffer = (UINT8 *) ROUNDUP32(pbi->ScaleBufferAlloc );
|
||||
}
|
||||
|
||||
// this is just so the post processor will work !!
|
||||
for(i=0;i<pbi->UnitFragments;i++)
|
||||
pbi->FragInfo[i].DisplayFragment = 1;
|
||||
|
||||
|
||||
return TRUE;
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : InitialiseConfiguration
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Sets up the default starting pbi->Configuration.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_InitialiseConfiguration(PB_INSTANCE *pbi)
|
||||
{
|
||||
|
||||
// IDCT table initialisation
|
||||
//InitDctTables();
|
||||
|
||||
pbi->Configuration.HFragPixels = 8;
|
||||
pbi->Configuration.VFragPixels = 8;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,285 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : Huffman.c
|
||||
*
|
||||
* Description : Video CODEC
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.13 YWX 06-Nov-01 Changed for compatibility with Equator C compiler
|
||||
* 1.12 JBB 13-Jun-01 VP4 Code Clean Out
|
||||
* 1.11 SJL 22-Mar-01 Fixed MAC compile errors
|
||||
* 1.10 JBX 22-Mar-01 Changed size of SORT_NODE array to 1024;
|
||||
* 1.09 JBB 26 Jan 00 Reworked Huffman to remove dynamic allocation and
|
||||
* to condense tree storage.
|
||||
* 1.08 PGW 11 Oct 00 Changes to support different entropy tables for
|
||||
* different encoder versions.
|
||||
* 1.07 PGW 17/03/00 Further Entropy changes.
|
||||
* 1.06 PGW 15/03/00 Updated entropy tables.
|
||||
* 1.05 JBB 27/01/99 Globals Removed, use of PB_INSTANCE, Bit Management
|
||||
* 1.04 PGW 05/11/99 Changes to support AC range entropy tables.
|
||||
* 1.03 PGW 12/10/99 Changes to reduce uneccessary dependancies.
|
||||
* 1.02 PGW 19/07/99 Deleted the funtion DecodeHuffToken().
|
||||
* 1.01 PGW 15/07/99 Added inline bit extraction to DecodeHuffToken().
|
||||
* 1.00 PGW 07/07/99 Configuration baseline
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#include "systemdependant.h"
|
||||
#include "huffman.h"
|
||||
#include "pbdll.h"
|
||||
#include "boolhuff.h"
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Forward references.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
void VP5_BuildHuffTree(
|
||||
HUFF_NODE *hn,
|
||||
unsigned int *counts,
|
||||
int values );
|
||||
|
||||
void VP5_CreateCodeArray( HUFF_NODE *hn,
|
||||
int node,
|
||||
unsigned int *codearray,
|
||||
unsigned char *lengtharray,
|
||||
int codevalue,
|
||||
int codelength );
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
typedef struct _SORT_NODE
|
||||
{
|
||||
int next;
|
||||
int freq;
|
||||
unsigned char value;
|
||||
} SORT_NODE;
|
||||
|
||||
/****************************************************************************
|
||||
* Module Static Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
//***********************************************************
|
||||
// Jim's version of Eric's condensed huffman trees!
|
||||
|
||||
|
||||
typedef struct _sortnode
|
||||
{
|
||||
int next;
|
||||
int freq;
|
||||
tokenorptr value;
|
||||
} sortnode;
|
||||
|
||||
|
||||
// inserts a node into a sorted linklist
|
||||
static void InsertSorted(
|
||||
sortnode *sn,
|
||||
int node,
|
||||
int *startnode )
|
||||
{
|
||||
int which = *startnode;
|
||||
int prior = *startnode;
|
||||
|
||||
// find the position at which to insert the node
|
||||
while( which != -1 && sn[node].freq > sn[which].freq )
|
||||
{
|
||||
prior = which;
|
||||
which = sn[which].next;
|
||||
}
|
||||
|
||||
if(which == *startnode)
|
||||
{
|
||||
*startnode = node;
|
||||
sn[node].next = which;
|
||||
}
|
||||
else
|
||||
{
|
||||
sn[prior].next = node;
|
||||
sn[node].next = which;
|
||||
}
|
||||
}
|
||||
|
||||
// returns a pointer to the condensed huffman root node
|
||||
void VP5_BuildHuffTree(
|
||||
HUFF_NODE *hn,
|
||||
unsigned int *counts,
|
||||
int values )
|
||||
{
|
||||
int i;
|
||||
sortnode sn[256];
|
||||
int sncount=0;
|
||||
int startnode=0;
|
||||
|
||||
// note we are creating the huffman tree in
|
||||
// reverse order so that the root will always be 0
|
||||
int huffptr=values-1;
|
||||
|
||||
// set up our sorted linked list of values
|
||||
// or pointers into the huffman tree
|
||||
for(i=0;i<values;i++)
|
||||
{
|
||||
sn[i].value.selector = 1;
|
||||
sn[i].value.value = i;
|
||||
if(counts[i] == 0)
|
||||
counts[i] = 1;
|
||||
sn[i].freq = counts[i];
|
||||
sn[i].next = -1;
|
||||
}
|
||||
sncount=values;
|
||||
|
||||
// connected the above list into a linked list
|
||||
for(i=1;i<values;i++)
|
||||
{
|
||||
InsertSorted(sn,i,&startnode);
|
||||
}
|
||||
|
||||
// while there is more than one node in our linked list
|
||||
while(sn[startnode].next!=-1)
|
||||
{
|
||||
int first = startnode;
|
||||
int second = sn[startnode].next;
|
||||
int sumfreq = sn[first].freq + sn[second].freq;
|
||||
|
||||
// setup new merged huffman node
|
||||
--huffptr;
|
||||
hn[huffptr].leftunion.left = sn[first].value;
|
||||
hn[huffptr].rightunion.right = sn[second].value;
|
||||
hn[huffptr].freq = 256 * sn[first].freq / sumfreq;
|
||||
|
||||
// set up new merged sort node pointing to our huffnode
|
||||
sn[sncount].value.selector = 0;
|
||||
sn[sncount].value.value = huffptr;
|
||||
sn[sncount].freq = sumfreq;
|
||||
sn[sncount].next = -1;
|
||||
|
||||
// remove the two nodes we just merged from the linked list
|
||||
startnode = sn[second].next;
|
||||
|
||||
// insert the new sort node into the proper location
|
||||
InsertSorted(sn, sncount, &startnode);
|
||||
|
||||
// account for new nodes
|
||||
sncount++;
|
||||
|
||||
}
|
||||
return ;
|
||||
}
|
||||
|
||||
void VP5_CreateCodeArray( HUFF_NODE *hn,
|
||||
int node,
|
||||
unsigned int *codearray,
|
||||
unsigned char *lengtharray,
|
||||
int codevalue,
|
||||
int codelength )
|
||||
{
|
||||
|
||||
/* If we are at a leaf then fill in a code array entry. */
|
||||
/* Recursive calls to scan down the tree. */
|
||||
if( hn[node].leftunion.left.selector )
|
||||
{
|
||||
codearray[hn[node].leftunion.left.value] = (codevalue<<1)+0;
|
||||
lengtharray[hn[node].leftunion.left.value] = codelength+1;
|
||||
}
|
||||
else
|
||||
{
|
||||
VP5_CreateCodeArray(
|
||||
hn,
|
||||
hn[node].leftunion.left.value,
|
||||
codearray,
|
||||
lengtharray,
|
||||
((codevalue << 1) + 0),
|
||||
(codelength + 1)
|
||||
);
|
||||
}
|
||||
|
||||
if( hn[node].rightunion.right.selector )
|
||||
{
|
||||
codearray[hn[node].rightunion.right.value] = (codevalue<<1)+1;
|
||||
lengtharray[hn[node].rightunion.right.value] = codelength+1;
|
||||
}
|
||||
else
|
||||
{
|
||||
VP5_CreateCodeArray(
|
||||
hn,
|
||||
hn[node].rightunion.right.value,
|
||||
codearray,
|
||||
lengtharray,
|
||||
((codevalue << 1) + 1),
|
||||
(codelength + 1)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
int VP5_DecodeValue(
|
||||
BOOL_CODER *bc,
|
||||
HUFF_NODE *hn
|
||||
)
|
||||
{
|
||||
tokenorptr torp;
|
||||
torp.value=0;
|
||||
torp.selector=0;
|
||||
// Loop searches down through tree based upon bits read from the bitstream
|
||||
// until it hits a leaf at which point we have decoded a token
|
||||
|
||||
do
|
||||
{
|
||||
if(DecodeBool(bc, hn[torp.value].freq))
|
||||
{
|
||||
torp = hn[torp.value].rightunion.right;
|
||||
}
|
||||
else
|
||||
{
|
||||
torp = hn[torp.value].leftunion.left;
|
||||
}
|
||||
}
|
||||
while ( !(torp.selector));
|
||||
|
||||
return torp.value;
|
||||
}
|
||||
|
||||
void VP5_EncodeValue(
|
||||
BOOL_CODER *bc,
|
||||
HUFF_NODE *hn,
|
||||
int value,
|
||||
int length)
|
||||
{
|
||||
int i;
|
||||
int node = 0;
|
||||
for(i=length-1;i>=0;i--)
|
||||
{
|
||||
int v= (value>>i) & 1;
|
||||
|
||||
if ( bc->MeasureCost )
|
||||
EncodeBool2(bc,(BOOL) v , hn[node].freq);
|
||||
else
|
||||
EncodeBool(bc,(BOOL) v , hn[node].freq);
|
||||
|
||||
if(v)
|
||||
{
|
||||
node=hn[node].rightunion.right.value;
|
||||
}
|
||||
else
|
||||
{
|
||||
node=hn[node].leftunion.left.value;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,710 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : MvEntropy.c
|
||||
*
|
||||
* Description : Video CODEC: Motion vector entropy module.
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.03 YWX 06-Nov-01 Changed for compatibility with Equator C compiler
|
||||
* 1.02 JBB 13 Jun 01 VP4 Code Clean Out
|
||||
* 1.01 PGW 23 Jan 01 Module created.
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Header Frames
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#include "type_aliases.h"
|
||||
#include "systemdependant.h"
|
||||
#include "codec_common.h"
|
||||
#include "codec_common_interface.h"
|
||||
#include "huffman.h"
|
||||
#include "pbdll.h"
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Explicit Imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Constants
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Types
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Data structures
|
||||
*****************************************************************************
|
||||
*/
|
||||
// VP5 MV coding tables
|
||||
UINT8 VP5_MvTableIndex[MV_ENTROPY_TOKENS] =
|
||||
{ 15, 15, 14, 14, 13, 13, 13, 13,
|
||||
12, 12, 12, 12, 11, 11, 11, 11,
|
||||
10, 10, 9, 9, 8, 8, 7, 7,
|
||||
6, 6, 5, 4, 3, 2, 1,
|
||||
0,
|
||||
1, 2, 3, 4, 5, 6, 6,
|
||||
7, 7, 8, 8, 9, 9, 10, 10,
|
||||
11, 11, 11, 11, 12, 12, 12, 12,
|
||||
13, 13, 13, 13, 14, 14, 15, 15
|
||||
};
|
||||
|
||||
HUFF_NODE XMvHuffTables[MV_ENTROPY_TABLES][MV_ENTROPY_TOKENS-1];
|
||||
UINT32 XMvPatternTables[MV_ENTROPY_TABLES][MV_ENTROPY_TOKENS];
|
||||
UINT8 XMvBitsTables[MV_ENTROPY_TABLES][MV_ENTROPY_TOKENS];
|
||||
|
||||
static UINT32 VP5_XMvFrequencyCounts[MV_ENTROPY_TABLES][MV_ENTROPY_TOKENS] =
|
||||
{
|
||||
67 , 15 , 32 , 4 , 21 , 8 , 33 , 2 , 32 , 6 , 29 , 4 , 25 , 5 , 83 , 16 , 58 , 3 , 59 , 7 , 75 , 11 ,129 , 19 ,126 , 22 ,159 , 29 ,207 , 88 ,636 ,388 ,579 ,125 ,269 , 66 ,223 , 33 ,177 , 15 ,118 , 14 ,130 , 14 , 81 , 10 , 91 , 25 ,106 , 10 , 68 , 12 , 51 , 10 , 61 , 13 , 46 , 8 , 55 , 6 , 63 , 29 ,207 ,
|
||||
77 , 6 , 23 , 1 , 19 , 1 , 25 , 4 , 38 , 2 , 39 , 6 , 48 , 6 ,116 , 25 ,110 , 16 ,105 , 16 ,125 , 26 ,223 , 28 ,279 , 56 ,407 , 98 ,509 ,238 ,921 ,461 ,1260 ,628 ,857 ,173 ,543 , 74 ,368 , 31 ,284 , 28 ,207 , 21 ,159 , 21 ,180 , 38 ,166 , 14 , 56 , 5 , 42 , 8 , 48 , 5 , 35 , 4 , 29 , 8 , 37 , 10 , 84 ,
|
||||
7 , 3 , 3 , 1 , 4 , 0 , 3 , 1 , 4 , 0 , 4 , 0 , 10 , 0 , 13 , 7 , 18 , 1 , 17 , 2 , 22 , 5 , 36 , 5 , 52 , 15 , 83 , 15 ,116 , 35 ,220 ,144 ,391 ,262 ,282 ,178 ,235 , 52 ,150 , 23 , 83 , 12 , 74 , 4 , 44 , 8 , 46 , 9 , 36 , 1 , 18 , 1 , 10 , 1 , 7 , 3 , 8 , 0 , 6 , 2 , 6 , 0 , 15 ,
|
||||
25 , 3 , 17 , 3 , 5 , 2 , 9 , 1 , 23 , 0 , 21 , 5 , 17 , 6 , 51 , 7 , 61 , 9 , 48 , 5 , 76 , 7 , 93 , 11 ,125 , 26 ,190 , 54 ,271 , 98 ,502 ,194 ,604 ,221 ,606 ,258 ,639 ,296 ,527 , 56 ,282 , 32 ,195 , 17 ,138 , 11 ,135 , 18 ,132 , 3 , 50 , 1 , 31 , 6 , 34 , 3 , 23 , 3 , 17 , 1 , 20 , 3 , 49 ,
|
||||
10 , 0 , 3 , 1 , 4 , 0 , 2 , 1 , 3 , 1 , 2 , 1 , 4 , 0 , 7 , 7 , 11 , 0 , 12 , 2 , 16 , 2 , 21 , 2 , 31 , 10 , 40 , 10 , 46 , 20 ,115 , 59 ,140 ,106 ,222 ,106 ,225 , 76 ,199 , 82 ,126 , 9 , 67 , 4 , 38 , 2 , 36 , 12 , 34 , 0 , 8 , 0 , 7 , 1 , 9 , 0 , 7 , 3 , 8 , 2 , 12 , 0 , 17 ,
|
||||
28 , 5 , 11 , 1 , 12 , 2 , 8 , 1 , 14 , 2 , 19 , 2 , 19 , 2 , 38 , 8 , 38 , 2 , 47 , 4 , 54 , 5 , 81 , 11 ,103 , 16 ,124 , 23 ,183 , 56 ,376 ,178 ,451 ,142 ,487 ,125 ,549 ,185 ,552 , 89 ,443 ,170 ,358 , 34 ,180 , 16 ,167 , 31 ,152 , 12 , 49 , 7 , 39 , 5 , 37 , 5 , 33 , 4 , 20 , 4 , 25 , 10 , 59 ,
|
||||
22 , 3 , 18 , 0 , 6 , 2 , 8 , 1 , 15 , 0 , 10 , 0 , 17 , 6 , 40 , 6 , 48 , 6 , 50 , 3 , 55 , 7 , 83 , 14 ,100 , 11 , 99 , 14 ,151 , 39 ,309 ,159 ,370 ,124 ,487 ,176 ,686 ,188 ,704 ,121 ,606 , 79 ,385 , 68 ,368 ,126 ,331 , 62 ,200 , 16 ,101 , 5 , 74 , 6 , 79 , 5 , 57 , 9 , 47 , 6 , 47 , 6 , 75 ,
|
||||
15 , 2 , 10 , 0 , 5 , 2 , 7 , 3 , 11 , 3 , 13 , 0 , 15 , 0 , 25 , 1 , 27 , 2 , 35 , 3 , 46 , 7 , 48 , 7 , 62 , 15 , 77 , 13 ,112 , 32 ,220 ,104 ,251 , 64 ,242 , 72 ,347 , 95 ,525 , 79 ,699 , 65 ,533 , 41 ,240 , 13 ,254 , 77 ,264 , 72 ,179 , 8 , 89 , 7 , 65 , 3 , 61 , 3 , 45 , 2 , 49 , 8 , 68 ,
|
||||
14 , 3 , 7 , 0 , 7 , 1 , 7 , 0 , 8 , 3 , 10 , 0 , 7 , 0 , 21 , 4 , 28 , 2 , 17 , 0 , 33 , 7 , 26 , 2 , 40 , 4 , 48 , 9 , 70 , 13 ,147 , 84 ,160 , 41 ,167 , 41 ,202 , 42 ,301 , 32 ,475 , 29 ,410 , 38 ,333 , 17 ,265 , 31 ,171 , 10 ,117 , 16 ,156 , 72 ,146 , 6 , 64 , 5 , 48 , 2 , 49 , 12 , 80 ,
|
||||
14 , 2 , 6 , 0 , 2 , 0 , 3 , 1 , 2 , 0 , 6 , 1 , 4 , 1 , 14 , 5 , 12 , 0 , 13 , 1 , 24 , 2 , 20 , 5 , 20 , 3 , 32 , 7 , 43 , 11 , 93 , 46 , 96 , 25 , 96 , 18 ,117 , 22 ,137 , 14 ,140 , 17 ,256 , 14 ,388 , 13 ,330 , 20 ,112 , 4 , 81 , 7 , 63 , 6 , 68 , 16 , 79 , 43 , 71 , 7 , 43 , 10 , 80 ,
|
||||
19 , 2 , 3 , 0 , 6 , 0 , 3 , 0 , 11 , 1 , 8 , 2 , 7 , 0 , 18 , 4 , 11 , 1 , 17 , 3 , 20 , 3 , 15 , 2 , 33 , 9 , 33 , 11 , 51 , 14 ,127 , 64 ,148 , 35 ,106 , 16 ,107 , 21 ,119 , 11 ,133 , 18 ,195 , 19 ,287 , 11 ,267 , 15 ,200 , 3 ,101 , 7 , 86 , 7 , 56 , 3 , 49 , 8 , 65 , 11 ,100 , 63 ,163 ,
|
||||
25 , 5 , 12 , 0 , 8 , 0 , 7 , 0 , 8 , 1 , 18 , 0 , 21 , 0 , 42 , 5 , 33 , 1 , 22 , 5 , 23 , 5 , 29 , 4 , 51 , 17 , 47 , 14 , 69 , 28 ,189 ,104 ,200 , 15 ,131 , 33 ,121 , 18 ,146 , 26 ,162 , 18 ,155 , 12 ,175 , 12 ,278 , 21 ,331 , 13 ,240 , 7 ,148 , 9 ,104 , 11 , 84 , 15 , 83 , 8 ,163 , 71 ,339 ,
|
||||
17 , 4 , 8 , 0 , 5 , 0 , 6 , 0 , 5 , 0 , 13 , 0 , 3 , 1 , 12 , 4 , 14 , 1 , 8 , 2 , 14 , 1 , 20 , 0 , 16 , 0 , 23 , 7 , 34 , 10 , 63 , 44 , 85 , 19 , 53 , 13 , 66 , 12 , 63 , 10 , 70 , 5 , 66 , 12 , 49 , 5 ,106 , 8 , 93 , 11 , 81 , 6 , 87 , 2 ,101 , 3 , 78 , 3 , 58 , 4 , 93 , 32 ,155 ,
|
||||
13 , 3 , 4 , 1 , 8 , 0 , 3 , 1 , 6 , 1 , 10 , 0 , 8 , 0 , 11 , 3 , 14 , 2 , 9 , 2 , 13 , 4 , 14 , 3 , 13 , 4 , 18 , 6 , 20 , 10 , 66 , 16 , 57 , 10 , 27 , 9 , 44 , 10 , 35 , 4 , 30 , 7 , 42 , 5 , 38 , 1 , 42 , 9 , 48 , 2 , 42 , 1 , 41 , 6 , 52 , 2 , 70 , 2 , 71 , 3 , 77 , 16 ,130 ,
|
||||
3 , 2 , 2 , 1 , 2 , 1 , 1 , 0 , 3 , 0 , 4 , 0 , 2 , 0 , 6 , 4 , 9 , 0 , 6 , 3 , 7 , 1 , 6 , 1 , 8 , 0 , 12 , 2 , 17 , 4 , 50 , 16 , 50 , 3 , 22 , 8 , 24 , 4 , 20 , 3 , 20 , 3 , 27 , 1 , 24 , 2 , 41 , 1 , 31 , 1 , 29 , 1 , 24 , 0 , 30 , 0 , 31 , 2 , 29 , 1 , 36 , 15 , 76 ,
|
||||
35 , 7 , 15 , 1 , 6 , 0 , 3 , 1 , 9 , 1 , 11 , 0 , 10 , 1 , 24 , 4 , 28 , 0 , 9 , 1 , 15 , 6 , 23 , 2 , 29 , 5 , 32 , 3 , 40 , 15 ,121 , 64 ,136 , 17 , 49 , 11 , 49 , 12 , 50 , 10 , 64 , 4 , 53 , 7 , 42 , 9 , 57 , 8 , 75 , 3 , 47 , 3 , 39 , 7 , 38 , 2 , 35 , 7 , 52 , 3 , 87 , 40 ,194 ,
|
||||
|
||||
|
||||
/*
|
||||
95 ,284 , 30 , 82 , 36 ,143 , 37 ,148 , 34 ,174 , 45 ,164 , 56 ,241 ,101 ,690 ,145 ,296 ,101 ,283 ,118 ,313 ,129 ,346 ,136 ,448 ,185 ,543 ,283 ,1035 ,725 ,3842 ,1009 ,1273 ,347 ,757 ,243 ,543 ,225 ,381 ,162 ,362 ,130 ,294 ,124 ,358 ,188 ,722 ,128 ,260 , 90 ,200 , 64 ,200 , 64 ,160 , 50 ,153 , 34 ,129 , 60 ,374 ,171 ,
|
||||
90 ,162 , 21 , 68 , 15 , 76 , 26 , 83 , 25 ,123 , 34 ,119 , 46 ,158 , 80 ,374 , 87 ,232 , 84 ,204 , 90 ,247 ,138 ,283 ,155 ,398 ,217 ,453 ,244 ,771 ,556 ,2108 ,915 ,1372 ,406 ,579 ,239 ,393 ,169 ,273 ,156 ,246 , 88 ,183 , 84 ,197 ,108 ,383 , 72 ,178 , 35 ,105 , 42 ,127 , 31 , 97 , 25 , 68 , 20 , 61 , 23 ,122 , 78 ,
|
||||
88 ,255 , 38 ,112 , 31 ,139 , 47 ,134 , 46 ,215 , 47 ,205 , 78 ,250 ,123 ,672 ,133 ,328 ,117 ,295 ,137 ,344 ,139 ,371 ,197 ,472 ,212 ,620 ,322 ,980 ,694 ,2402 ,1096 ,2773 ,1079 ,1699 ,549 ,971 ,317 ,650 ,277 ,552 ,185 ,381 ,147 ,428 ,206 ,799 ,125 ,293 , 82 ,212 , 64 ,211 , 60 ,151 , 71 ,163 , 29 ,126 , 33 ,280 ,120 ,
|
||||
40 , 78 , 25 , 29 , 19 , 57 , 18 , 53 , 14 , 58 , 33 , 85 , 36 ,100 , 56 ,224 , 52 ,109 , 47 ,133 , 44 ,122 , 70 ,134 , 70 ,200 , 81 ,208 ,142 ,343 ,223 ,827 ,373 ,1018 ,512 ,933 ,314 ,509 ,170 ,300 ,111 ,189 , 80 ,164 , 76 ,143 , 77 ,298 , 78 ,112 , 34 , 85 , 40 , 57 , 20 , 59 , 20 , 47 , 11 , 50 , 22 , 73 , 56 ,
|
||||
65 ,161 , 25 , 59 , 18 ,103 , 37 , 88 , 45 ,106 , 39 ,105 , 51 ,172 , 76 ,492 ,103 ,214 , 59 ,212 , 65 ,246 ,104 ,281 ,126 ,340 ,153 ,381 ,214 ,604 ,357 ,1262 ,444 ,1463 ,679 ,1863 ,785 ,1296 ,449 ,685 ,307 ,517 ,162 ,314 ,161 ,366 ,132 ,606 ,112 ,232 , 68 ,187 , 70 ,161 , 41 ,123 , 38 ,119 , 36 ,112 , 35 ,194 , 99 ,
|
||||
46 , 76 , 18 , 37 , 16 , 52 , 12 , 54 , 7 , 48 , 14 , 69 , 28 ,112 , 38 ,219 , 57 ,116 , 56 , 96 , 37 , 93 , 38 ,121 , 82 ,178 ,107 ,177 , 78 ,259 ,181 ,491 ,214 ,554 ,302 ,717 ,382 ,788 ,306 ,459 ,199 ,311 ,134 ,235 ,120 ,207 , 85 ,308 , 70 ,135 , 45 , 79 , 41 , 80 , 23 , 72 , 12 , 54 , 7 , 56 , 23 ,113 , 59 ,
|
||||
111 ,226 , 21 ,100 , 36 ,125 , 50 ,158 , 62 ,172 , 55 ,177 , 71 ,288 ,113 ,633 ,129 ,326 , 91 ,268 ,113 ,362 ,133 ,321 ,136 ,424 ,156 ,461 ,240 ,643 ,470 ,1336 ,464 ,1271 ,503 ,1739 ,898 ,2410 ,961 ,1777 ,643 ,1105 ,332 ,709 ,304 ,619 ,294 ,973 ,213 ,386 ,123 ,282 , 78 ,254 , 79 ,222 , 54 ,185 , 57 ,160 , 57 ,264 ,153 ,
|
||||
80 ,188 , 28 , 87 , 31 ,117 , 35 ,108 , 38 ,147 , 54 ,184 , 58 ,188 ,121 ,584 ,108 ,312 , 93 ,231 , 89 ,272 ,109 ,303 ,132 ,326 ,146 ,377 ,156 ,496 ,297 ,1039 ,320 ,825 ,281 ,1010 ,459 ,1403 ,696 ,2078 ,895 ,1575 ,441 ,800 ,260 ,567 ,315 ,891 ,239 ,357 ,118 ,240 , 91 ,212 , 93 ,184 , 69 ,174 , 56 ,129 , 52 ,284 ,120 ,
|
||||
89 ,177 , 17 , 70 , 23 , 77 , 39 ,110 , 31 ,147 , 44 ,138 , 64 ,183 , 81 ,461 , 87 ,234 , 79 ,236 , 70 ,253 ,113 ,244 ,125 ,290 ,111 ,241 ,124 ,384 ,221 ,940 ,251 ,599 ,220 ,602 ,320 ,840 ,336 ,1185 ,638 ,1811 ,664 ,1197 ,307 ,751 ,344 ,942 ,213 ,377 ,131 ,259 , 69 ,201 , 66 ,164 , 48 ,171 , 53 ,136 , 36 ,272 ,142 ,
|
||||
91 ,130 , 27 , 69 , 21 , 85 , 23 , 93 , 36 ,142 , 26 ,121 , 30 ,182 , 65 ,427 , 83 ,201 , 59 ,175 , 64 ,211 , 67 ,198 ,100 ,257 ,107 ,245 ,139 ,322 ,184 ,723 ,214 ,430 ,169 ,445 ,208 ,572 ,228 ,650 ,328 ,1034 ,483 ,1618 ,676 ,1115 ,348 ,1025 ,233 ,413 ,137 ,271 , 81 ,227 , 77 ,170 , 45 ,144 , 56 ,111 , 45 ,178 ,115 ,
|
||||
89 ,200 , 30 , 88 , 21 ,110 , 35 ,102 , 39 ,130 , 46 ,148 , 35 ,234 , 95 ,522 ,128 ,236 , 85 ,188 , 81 ,233 , 84 ,251 , 84 ,282 ,117 ,285 ,121 ,370 ,193 ,806 ,217 ,484 ,162 ,469 ,161 ,494 ,205 ,518 ,241 ,622 ,259 ,918 ,594 ,1431 ,675 ,1505 ,338 ,455 ,129 ,273 , 84 ,236 , 82 ,201 , 80 ,142 , 44 ,142 , 31 ,294 ,162 ,
|
||||
237 ,546 , 61 ,167 , 63 ,238 , 85 ,255 , 71 ,357 , 81 ,323 , 97 ,417 ,186 ,1285 ,302 ,588 ,189 ,469 ,174 ,517 ,224 ,561 ,207 ,619 ,234 ,593 ,285 ,800 ,469 ,1935 ,468 ,983 ,329 ,845 ,281 ,927 ,328 ,944 ,378 ,980 ,372 ,1070 ,523 ,1544 ,857 ,3091 ,995 ,1478 ,465 ,811 ,245 ,613 ,188 ,442 ,166 ,445 ,132 ,334 ,123 ,759 ,360 ,
|
||||
86 ,220 , 34 , 85 , 27 , 93 , 35 ,102 , 39 ,113 , 57 ,138 , 45 ,182 , 71 ,489 , 98 ,221 , 84 ,170 , 78 ,230 , 93 ,248 , 81 ,237 ,109 ,255 ,126 ,365 ,188 ,752 ,209 ,422 ,133 ,331 ,163 ,400 ,133 ,401 ,151 ,410 ,155 ,425 ,153 ,468 ,194 ,916 ,246 ,491 ,205 ,413 ,201 ,373 ,153 ,278 , 96 ,197 , 76 ,162 , 72 ,342 ,210 ,
|
||||
68 ,184 , 17 , 52 , 12 , 86 , 35 , 70 , 18 ,100 , 38 ,102 , 35 ,134 , 76 ,373 , 55 ,185 , 48 ,130 , 65 ,200 , 68 ,177 , 77 ,225 , 90 ,186 , 73 ,271 ,128 ,509 ,126 ,343 ,103 ,286 ,103 ,297 ,133 ,252 ,107 ,269 , 87 ,244 ,114 ,289 ,160 ,621 ,145 ,281 ,101 ,270 ,120 ,265 ,132 ,257 ,142 ,320 ,115 ,201 , 58 ,329 ,193 ,
|
||||
52 , 96 , 4 , 25 , 12 , 39 , 9 , 36 , 15 , 45 , 22 , 32 , 22 , 64 , 36 ,154 , 34 , 79 , 23 , 61 , 28 , 92 , 18 , 66 , 30 , 85 , 41 , 90 , 48 ,140 , 55 ,250 , 57 ,112 , 42 ,103 , 38 ,128 , 44 , 99 , 43 ,112 , 45 ,115 , 38 ,131 , 63 ,288 , 57 ,138 , 31 , 99 , 31 , 94 , 37 , 96 , 30 ,131 , 45 ,117 , 52 ,161 , 94 ,
|
||||
147 ,381 , 25 ,105 , 21 ,147 , 37 ,119 , 43 ,177 , 37 ,168 , 49 ,204 ,106 ,620 ,102 ,238 , 65 ,200 , 57 ,231 , 97 ,191 ,101 ,224 , 89 ,222 , 95 ,394 ,199 ,748 ,171 ,384 ,125 ,322 ,100 ,301 ,118 ,289 ,125 ,304 , 92 ,234 ,100 ,331 ,163 ,834 ,175 ,334 , 81 ,274 , 64 ,266 , 85 ,212 ,113 ,285 , 63 ,206 , 96 ,690 ,402 ,
|
||||
{
|
||||
36, 69, 8, 21, 8, 28, 15, 29,
|
||||
11, 32, 14, 33, 15, 41, 25, 109,
|
||||
22, 61, 32, 62, 32, 78, 49, 91,
|
||||
64, 126, 102, 165, 207, 615, 1860, 2163,
|
||||
1514, 598, 254, 180, 105, 131, 75, 70,
|
||||
43, 60, 38, 48, 31, 60, 36, 105,
|
||||
26, 47, 29, 35, 17, 32, 16, 25,
|
||||
7, 29, 8, 21, 7, 49, 49,
|
||||
},
|
||||
{
|
||||
11, 22, 6, 8, 8, 11, 5, 11,
|
||||
1, 14, 5, 16, 13, 23, 14, 32,
|
||||
18, 29, 25, 32, 26, 37, 32, 52,
|
||||
55, 83, 94, 145, 201, 458, 1233, 2600,
|
||||
1790, 1313, 420, 221, 125, 126, 94, 71,
|
||||
38, 41, 30, 40, 26, 29, 22, 47,
|
||||
24, 23, 12, 17, 15, 14, 14, 14,
|
||||
8, 9, 9, 9, 2, 17, 23,
|
||||
},
|
||||
{
|
||||
29, 32, 9, 22, 7, 21, 10, 11,
|
||||
5, 27, 16, 17, 13, 23, 20, 59,
|
||||
14, 35, 14, 32, 25, 41, 43, 53,
|
||||
40, 75, 61, 135, 146, 298, 635, 1241,
|
||||
2473, 1648, 1042, 437, 182, 146, 94, 94,
|
||||
55, 49, 37, 52, 28, 51, 34, 49,
|
||||
22, 26, 13, 22, 15, 23, 10, 20,
|
||||
14, 26, 10, 14, 5, 27, 37,
|
||||
},
|
||||
{
|
||||
18, 18, 10, 10, 16, 20, 6, 22,
|
||||
16, 30, 14, 38, 16, 24, 12, 59,
|
||||
28, 61, 36, 53, 18, 59, 59, 57,
|
||||
43, 86, 100, 137, 178, 291, 560, 1069,
|
||||
1243, 1919, 1102, 866, 346, 270, 153, 137,
|
||||
90, 63, 43, 34, 38, 61, 36, 57,
|
||||
24, 47, 18, 30, 26, 24, 10, 24,
|
||||
14, 36, 8, 12, 4, 34, 34,
|
||||
},
|
||||
{
|
||||
38, 61, 15, 22, 12, 33, 22, 33,
|
||||
17, 35, 10, 33, 12, 27, 15, 86,
|
||||
25, 63, 33, 78, 35, 71, 55, 89,
|
||||
55, 165, 83, 132, 172, 256, 462, 778,
|
||||
671, 989, 1261, 1045, 803, 524, 259, 231,
|
||||
109, 109, 61, 89, 48, 76, 66, 101,
|
||||
55, 58, 20, 45, 20, 33, 27, 40,
|
||||
12, 33, 10, 25, 2, 71, 53,
|
||||
},
|
||||
{
|
||||
39, 35, 7, 39, 10, 31, 24, 21,
|
||||
35, 46, 35, 46, 21, 46, 17, 78,
|
||||
24, 49, 24, 99, 67, 74, 42, 92,
|
||||
56, 127, 95, 202, 191, 414, 475, 613,
|
||||
652, 656, 652, 1042, 680, 769, 574, 333,
|
||||
205, 195, 88, 74, 88, 74, 70, 81,
|
||||
53, 95, 46, 39, 24, 46, 14, 67,
|
||||
24, 17, 7, 28, 14, 63, 28,
|
||||
},
|
||||
{
|
||||
57, 58, 7, 29, 7, 36, 7, 58,
|
||||
27, 47, 22, 58, 23, 53, 33, 91,
|
||||
29, 84, 38, 57, 66, 69, 79, 84,
|
||||
77, 97, 93, 169, 139, 285, 364, 597,
|
||||
480, 388, 448, 636, 774, 995, 691, 551,
|
||||
320, 241, 160, 169, 99, 125, 79, 123,
|
||||
68, 79, 33, 60, 20, 47, 34, 62,
|
||||
22, 62, 25, 51, 27, 84, 77,
|
||||
},
|
||||
{
|
||||
91, 88, 16, 40, 13, 32, 10, 42,
|
||||
16, 53, 21, 50, 13, 66, 53, 107,
|
||||
34, 72, 29, 58, 32, 74, 64, 88,
|
||||
85, 109, 96, 168, 149, 326, 323, 495,
|
||||
374, 425, 364, 471, 412, 554, 589, 787,
|
||||
527, 460, 313, 214, 163, 168, 149, 184,
|
||||
104, 109, 61, 93, 66, 80, 37, 64,
|
||||
29, 40, 40, 29, 13, 72, 66,
|
||||
},
|
||||
{
|
||||
76, 83, 6, 56, 16, 46, 36, 73,
|
||||
26, 69, 36, 69, 53, 66, 56, 103,
|
||||
66, 106, 49, 79, 36, 93, 83, 133,
|
||||
79, 119, 89, 136, 119, 233, 226, 442,
|
||||
319, 306, 236, 312, 266, 409, 372, 532,
|
||||
502, 675, 496, 386, 236, 262, 239, 206,
|
||||
163, 143, 93, 96, 59, 99, 53, 93,
|
||||
53, 59, 33, 53, 36, 99, 123,
|
||||
},
|
||||
{
|
||||
60, 86, 18, 33, 18, 63, 11, 60,
|
||||
18, 105, 30, 48, 56, 90, 33, 82,
|
||||
78, 101, 30, 101, 67, 116, 75, 123,
|
||||
45, 108, 97, 131, 71, 213, 217, 330,
|
||||
292, 255, 180, 210, 243, 371, 258, 390,
|
||||
240, 562, 446, 675, 480, 498, 318, 348,
|
||||
225, 247, 112, 135, 93, 82, 48, 90,
|
||||
67, 90, 52, 45, 22, 90, 97,
|
||||
},
|
||||
{
|
||||
76, 129, 10, 45, 3, 48, 20, 66,
|
||||
20, 73, 17, 59, 17, 76, 31, 125,
|
||||
55, 94, 38, 80, 41, 108, 80, 111,
|
||||
87, 104, 55, 108, 76, 160, 234, 451,
|
||||
290, 248, 199, 223, 139, 297, 150, 318,
|
||||
199, 342, 321, 489, 433, 605, 563, 510,
|
||||
391, 286, 171, 139, 115, 108, 73, 108,
|
||||
59, 115, 48, 31, 20, 139, 132,
|
||||
},
|
||||
{
|
||||
93, 100, 15, 36, 24, 51, 17, 58,
|
||||
26, 58, 15, 68, 20, 58, 55, 201,
|
||||
79, 96, 39, 85, 49, 125, 53, 85,
|
||||
51, 89, 83, 112, 96, 186, 224, 440,
|
||||
224, 190, 115, 178, 100, 193, 114, 250,
|
||||
171, 229, 157, 294, 247, 421, 437, 859,
|
||||
482, 530, 336, 285, 186, 231, 142, 155,
|
||||
77, 112, 76, 74, 47, 125, 144,
|
||||
},
|
||||
{
|
||||
137, 99, 12, 54, 15, 54, 25, 60,
|
||||
25, 76, 25, 70, 44, 54, 76, 127,
|
||||
60, 70, 19, 99, 67, 127, 54, 127,
|
||||
79, 95, 60, 76, 60, 172, 134, 338,
|
||||
213, 213, 89, 150, 137, 210, 111, 182,
|
||||
95, 255, 105, 255, 150, 322, 265, 427,
|
||||
255, 472, 408, 443, 415, 495, 306, 287,
|
||||
178, 175, 134, 111, 83, 185, 252,
|
||||
},
|
||||
{
|
||||
105, 149, 28, 64, 32, 72, 24, 72,
|
||||
12, 64, 24, 64, 12, 64, 48, 157,
|
||||
80, 76, 40, 76, 56, 117, 64, 109,
|
||||
76, 141, 64, 109, 76, 198, 145, 307,
|
||||
133, 137, 109, 125, 93, 226, 80, 153,
|
||||
113, 214, 97, 234, 88, 218, 258, 384,
|
||||
234, 234, 214, 283, 222, 432, 311, 465,
|
||||
384, 343, 258, 283, 190, 323, 404,
|
||||
},
|
||||
{
|
||||
263, 160, 22, 80, 11, 148, 11, 91,
|
||||
34, 137, 22, 91, 80, 137, 34, 171,
|
||||
22, 57, 22, 102, 45, 160, 80, 91,
|
||||
80, 171, 45, 114, 80, 137, 171, 286,
|
||||
57, 148, 80, 286, 125, 160, 125, 171,
|
||||
102, 102, 57, 217, 125, 160, 80, 286,
|
||||
114, 102, 148, 251, 217, 297, 137, 343,
|
||||
251, 514, 228, 400, 331, 526, 675,
|
||||
},
|
||||
{
|
||||
188, 256, 21, 68, 21, 108, 25, 119,
|
||||
32, 101, 21, 54, 10, 83, 61, 151,
|
||||
68, 94, 43, 126, 43, 108, 43, 151,
|
||||
65, 137, 68, 159, 86, 209, 144, 368,
|
||||
159, 188, 72, 155, 83, 188, 97, 137,
|
||||
65, 155, 97, 144, 57, 195, 97, 249,
|
||||
104, 213, 61, 169, 101, 278, 101, 209,
|
||||
144, 365, 173, 285, 216, 824, 1356,
|
||||
}
|
||||
*/
|
||||
};
|
||||
|
||||
|
||||
HUFF_NODE YMvHuffTables[MV_ENTROPY_TABLES][MV_ENTROPY_TOKENS-1];
|
||||
UINT32 YMvPatternTables[MV_ENTROPY_TABLES][MV_ENTROPY_TOKENS];
|
||||
UINT8 YMvBitsTables[MV_ENTROPY_TABLES][MV_ENTROPY_TOKENS];
|
||||
|
||||
static UINT32 VP5_YMvFrequencyCounts[MV_ENTROPY_TABLES][MV_ENTROPY_TOKENS] =
|
||||
{
|
||||
19 , 12 , 31 , 74 , 10 , 11 , 33 , 66 , 10 , 14 , 26 , 82 , 14 , 27 , 22 ,118 , 27 , 28 , 49 ,170 , 32 , 54 , 70 ,313 , 94 ,101 ,190 ,999 ,326 ,643 ,695 ,1793 ,370 ,583 ,290 ,393 ,100 , 72 , 94 ,215 , 48 , 45 , 59 ,122 , 30 , 33 , 29 , 93 , 14 , 21 , 24 , 78 , 6 , 19 , 20 , 43 , 7 , 12 , 15 , 66 , 17 , 8 , 15 ,
|
||||
4 , 5 , 2 , 11 , 3 , 2 , 2 , 10 , 5 , 1 , 4 , 17 , 5 , 8 , 9 , 28 , 6 , 20 , 26 , 68 , 22 , 43 , 51 , 94 , 63 , 75 , 84 ,179 ,203 ,308 ,352 ,1106 ,655 ,1312 ,535 ,643 ,219 ,117 ,108 ,153 , 74 , 53 , 48 , 77 , 31 , 31 , 23 , 39 , 16 , 12 , 6 , 21 , 10 , 15 , 9 , 9 , 5 , 4 , 2 , 17 , 7 , 11 , 6 ,
|
||||
6 , 6 , 2 , 10 , 4 , 9 , 4 , 17 , 5 , 10 , 5 , 16 , 9 , 13 , 11 , 44 , 16 , 31 , 17 , 46 , 24 , 39 , 39 , 89 , 55 , 48 , 62 ,139 ,126 ,276 ,210 ,715 ,742 ,1649 ,361 ,945 ,265 ,242 ,110 ,206 , 93 , 78 , 55 ,101 , 31 , 45 , 23 , 68 , 22 , 25 , 16 , 22 , 6 , 14 , 9 , 23 , 3 , 17 , 9 , 26 , 2 , 10 , 8 ,
|
||||
2 , 5 , 2 , 6 , 3 , 3 , 2 , 11 , 3 , 8 , 3 , 12 , 2 , 12 , 7 , 23 , 11 , 13 , 8 , 28 , 16 , 31 , 30 , 65 , 28 , 43 , 69 ,110 ,120 ,149 ,183 ,502 ,403 ,627 ,370 ,750 ,259 ,180 ,136 ,173 , 71 , 50 , 39 , 67 , 34 , 27 , 23 , 44 , 15 , 13 , 6 , 21 , 9 , 11 , 3 , 12 , 3 , 2 , 2 , 13 , 2 , 9 , 4 ,
|
||||
6 , 5 , 3 , 22 , 3 , 6 , 2 , 15 , 4 , 4 , 3 , 24 , 4 , 8 , 10 , 32 , 13 , 12 , 12 , 48 , 15 , 20 , 26 ,117 , 33 , 45 , 58 ,181 , 87 ,146 ,146 ,891 ,341 ,639 ,524 ,1885 ,524 ,313 ,300 ,1314 ,194 ,108 , 74 ,252 , 48 , 53 , 30 ,140 , 31 , 42 , 14 , 58 , 13 , 15 , 10 , 39 , 5 , 11 , 4 , 31 , 6 , 14 , 7 ,
|
||||
1 , 4 , 1 , 9 , 0 , 0 , 6 , 10 , 2 , 2 , 1 , 9 , 2 , 1 , 8 , 13 , 4 , 7 , 4 , 13 , 10 , 8 , 8 , 32 , 19 , 21 , 24 , 58 , 54 , 52 , 57 ,163 , 87 ,164 ,199 ,599 ,183 ,127 ,168 ,557 ,119 ,104 , 59 ,108 , 49 , 24 , 20 , 53 , 19 , 11 , 7 , 17 , 6 , 3 , 3 , 10 , 7 , 4 , 4 , 6 , 4 , 3 , 0 ,
|
||||
4 , 5 , 1 , 11 , 1 , 3 , 5 , 6 , 2 , 9 , 3 , 8 , 3 , 5 , 4 , 19 , 4 , 9 , 8 , 18 , 6 , 12 , 10 , 35 , 16 , 29 , 26 , 60 , 47 , 82 , 64 ,120 , 70 ,185 ,145 ,335 ,155 ,118 ,104 ,405 ,100 , 85 , 57 ,192 , 49 , 81 , 45 , 83 , 22 , 20 , 16 , 42 , 15 , 17 , 6 , 35 , 7 , 14 , 6 , 22 , 9 , 8 , 5 ,
|
||||
6 , 7 , 1 , 12 , 3 , 8 , 4 , 14 , 7 , 7 , 3 , 23 , 8 , 5 , 8 , 33 , 6 , 15 , 4 , 33 , 13 , 21 , 20 , 69 , 23 , 38 , 40 ,135 , 57 , 91 , 84 ,287 ,133 ,196 ,172 ,730 ,229 ,174 ,234 ,1521 ,194 ,140 ,124 ,895 ,130 ,115 , 87 ,443 , 73 , 77 , 36 ,109 , 32 , 34 , 19 , 82 , 16 , 16 , 6 , 79 , 11 , 19 , 23 ,
|
||||
1 , 2 , 3 , 3 , 2 , 3 , 0 , 3 , 1 , 2 , 3 , 4 , 4 , 3 , 1 , 10 , 2 , 3 , 3 , 11 , 6 , 5 , 5 , 12 , 8 , 12 , 18 , 31 , 24 , 39 , 39 , 68 , 50 , 61 , 45 , 74 , 36 , 43 , 32 ,133 , 25 , 37 , 16 ,101 , 15 , 29 , 20 , 50 , 10 , 26 , 15 , 50 , 12 , 23 , 12 , 21 , 6 , 8 , 4 , 19 , 8 , 7 , 4 ,
|
||||
2 , 3 , 2 , 8 , 2 , 2 , 2 , 9 , 2 , 2 , 2 , 10 , 3 , 4 , 4 , 18 , 2 , 10 , 2 , 31 , 6 , 12 , 9 , 29 , 12 , 22 , 19 , 54 , 37 , 46 , 34 ,131 , 65 , 78 , 64 ,149 , 54 , 65 , 68 ,388 , 46 , 26 , 57 ,620 , 59 , 33 , 31 ,471 , 37 , 37 , 29 ,158 , 21 , 39 , 25 ,171 , 21 , 36 , 8 , 70 , 14 , 12 , 14 ,
|
||||
0 , 3 , 1 , 4 , 1 , 3 , 1 , 5 , 1 , 6 , 2 , 6 , 3 , 2 , 2 , 8 , 2 , 9 , 4 , 6 , 2 , 2 , 3 , 18 , 8 , 4 , 9 , 29 , 19 , 34 , 28 , 38 , 22 , 28 , 19 , 27 , 12 , 18 , 14 , 68 , 13 , 15 , 8 , 36 , 6 , 26 , 3 , 34 , 6 , 22 , 3 , 16 , 4 , 19 , 3 , 11 , 8 , 14 , 4 , 48 , 15 , 23 , 7 ,
|
||||
1 , 3 , 1 , 12 , 1 , 1 , 3 , 12 , 3 , 4 , 7 , 13 , 2 , 5 , 4 , 21 , 5 , 14 , 6 , 20 , 7 , 10 , 14 , 29 , 8 , 25 , 22 , 50 , 27 , 54 , 33 ,115 , 57 , 89 , 43 ,121 , 33 , 56 , 32 ,149 , 19 , 30 , 22 ,295 , 22 , 30 , 26 ,411 , 28 , 21 , 16 ,267 , 25 , 28 , 15 , 99 , 12 , 32 , 17 ,128 , 29 , 61 , 52 ,
|
||||
2 , 4 , 4 , 12 , 1 , 4 , 1 , 7 , 1 , 1 , 3 , 11 , 2 , 7 , 5 , 13 , 2 , 9 , 3 , 19 , 5 , 8 , 9 , 17 , 11 , 8 , 12 , 34 , 24 , 41 , 25 , 55 , 31 , 58 , 29 , 54 , 17 , 26 , 21 , 52 , 14 , 17 , 18 , 68 , 4 , 18 , 13 ,170 , 13 , 22 , 14 ,179 , 18 , 15 , 5 ,120 , 14 , 18 , 12 ,102 , 26 , 49 , 29 ,
|
||||
5 , 3 , 0 , 8 , 2 , 2 , 2 , 4 , 0 , 5 , 0 , 5 , 0 , 2 , 0 , 8 , 0 , 3 , 3 , 12 , 1 , 3 , 3 , 23 , 8 , 16 , 7 , 26 , 13 , 20 , 18 , 45 , 22 , 28 , 22 , 41 , 14 , 16 , 16 , 49 , 11 , 15 , 11 , 73 , 3 , 10 , 7 , 61 , 7 , 9 , 5 , 90 , 12 , 12 , 7 , 63 , 14 , 8 , 4 , 83 , 13 , 19 , 15 ,
|
||||
3 , 4 , 3 , 9 , 0 , 2 , 0 , 3 , 0 , 2 , 3 , 7 , 0 , 3 , 1 , 8 , 2 , 8 , 1 , 5 , 3 , 6 , 2 , 18 , 3 , 12 , 8 , 34 , 15 , 19 , 12 , 47 , 19 , 25 , 21 , 35 , 15 , 16 , 10 , 33 , 6 , 12 , 6 , 39 , 4 , 15 , 2 , 48 , 6 , 10 , 8 , 42 , 3 , 5 , 4 , 73 , 4 , 1 , 5 ,152 , 11 , 15 , 18 ,
|
||||
0 , 2 , 1 , 1 , 0 , 4 , 0 , 3 , 0 , 3 , 0 , 4 , 0 , 4 , 1 , 2 , 1 , 3 , 0 , 5 , 0 , 3 , 0 , 7 , 4 , 7 , 6 , 15 , 9 , 13 , 8 , 20 , 8 , 16 , 10 , 10 , 5 , 6 , 2 , 12 , 2 , 11 , 1 , 10 , 0 , 10 , 2 , 11 , 0 , 2 , 0 , 7 , 3 , 2 , 3 , 9 , 2 , 5 , 0 , 6 , 3 , 10 , 4 ,
|
||||
/*
|
||||
36 , 94 ,136 ,248 , 42 , 90 , 62 ,284 , 73 , 93 , 87 ,430 ,119 ,147 ,180 ,888 ,157 ,216 ,203 ,716 ,131 ,208 ,243 ,1216 ,272 ,346 ,457 ,2737 ,863 ,1978 ,2840 ,8045 ,1609 ,1342 ,538 ,1273 ,316 ,287 ,195 ,794 ,177 ,199 ,134 ,584 ,193 ,198 ,163 ,755 ,145 ,162 , 99 ,370 ,106 , 76 , 49 ,313 , 64 , 71 , 38 ,252 ,165 , 75 , 39 ,
|
||||
23 , 53 , 71 ,150 , 34 , 48 , 45 ,176 , 57 , 65 , 76 ,251 , 75 ,115 ,138 ,556 ,130 ,153 ,128 ,428 , 94 ,122 ,172 ,606 ,188 ,219 ,287 ,917 ,407 ,804 ,1000 ,5395 ,2602 ,2741 ,1082 ,2329 ,428 ,261 ,215 ,727 ,174 ,154 ,128 ,431 ,149 ,138 ,143 ,593 ,155 ,108 , 95 ,263 , 85 , 62 , 46 ,193 , 49 , 60 , 43 ,168 , 81 , 65 , 33 ,
|
||||
37 , 50 , 64 ,112 , 30 , 51 , 35 ,186 , 44 , 69 , 50 ,251 , 58 ,106 ,126 ,484 , 95 ,167 ,105 ,314 , 97 ,115 ,138 ,527 ,131 ,203 ,185 ,621 ,298 ,678 ,761 ,3375 ,2087 ,2890 ,1483 ,2215 ,482 ,432 ,260 ,745 ,180 ,208 ,128 ,411 ,152 ,134 ,136 ,568 ,124 ,152 , 78 ,226 , 72 , 92 , 51 ,181 , 39 , 66 , 28 ,149 ,102 , 71 , 22 ,
|
||||
16 , 30 , 45 , 84 , 14 , 51 , 29 ,100 , 28 , 49 , 38 ,159 , 48 , 78 , 70 ,326 , 81 , 77 , 71 ,243 , 65 , 64 ,100 ,330 ,100 ,135 ,149 ,378 ,210 ,370 ,370 ,1619 ,907 ,1450 ,1128 ,2217 ,513 ,260 ,240 ,710 ,200 ,128 ,118 ,320 ,128 , 94 , 86 ,353 , 92 , 98 , 80 ,147 , 50 , 36 , 31 ,127 , 45 , 27 , 24 , 78 , 63 , 38 , 22 ,
|
||||
30 , 76 ,122 ,219 , 38 , 74 , 58 ,308 , 50 , 97 ,116 ,409 , 89 ,168 ,143 ,810 ,146 ,169 ,189 ,626 ,150 ,194 ,199 ,809 ,177 ,230 ,261 ,1073 ,322 ,567 ,620 ,3684 ,1380 ,1976 ,1723 ,7569 ,1900 ,854 ,742 ,3046 ,468 ,334 ,267 ,990 ,273 ,249 ,215 ,1029 ,273 ,190 ,133 ,524 ,120 ,107 , 58 ,358 , 77 , 84 , 52 ,292 ,139 , 82 , 49 ,
|
||||
7 , 23 , 47 , 61 , 22 , 23 , 21 ,103 , 14 , 22 , 33 ,136 , 54 , 45 , 57 ,229 , 48 , 54 , 62 ,169 , 52 , 63 , 76 ,241 , 68 , 68 ,115 ,272 ,140 ,153 ,185 ,772 ,302 ,420 ,445 ,1755 ,642 ,242 ,319 ,1349 ,276 ,128 ,105 ,421 ,151 , 86 , 83 ,362 , 77 , 57 , 66 ,167 , 64 , 27 , 34 ,134 , 32 , 29 , 14 , 90 , 61 , 38 , 24 ,
|
||||
23 , 17 , 46 , 77 , 18 , 40 , 28 ,109 , 20 , 37 , 34 ,157 , 36 , 72 , 47 ,242 , 50 , 60 , 69 ,205 , 63 , 75 , 77 ,240 , 77 , 98 ,118 ,363 ,181 ,266 ,269 ,889 ,305 ,457 ,344 ,1010 ,388 ,304 ,365 ,1372 ,317 ,167 ,131 ,572 ,191 ,109 ,110 ,438 , 98 , 93 , 75 ,213 , 83 , 58 , 57 ,157 , 45 , 46 , 32 , 96 , 63 , 78 , 31 ,
|
||||
38 , 89 , 80 ,239 , 44 , 71 , 68 ,286 , 59 , 98 , 76 ,355 , 94 ,145 ,134 ,677 ,142 ,149 ,163 ,540 ,135 ,154 ,157 ,706 ,143 ,212 ,239 ,882 ,307 ,403 ,489 ,1903 ,579 ,795 ,614 ,2498 ,984 ,648 ,760 ,5794 ,1295 ,394 ,465 ,2504 ,467 ,394 ,289 ,1266 ,232 ,250 ,164 ,561 ,146 ,128 , 74 ,383 ,129 ,103 , 47 ,265 ,156 , 96 , 58 ,
|
||||
11 , 31 , 34 , 51 , 12 , 19 , 22 , 67 , 14 , 25 , 46 , 78 , 32 , 41 , 44 ,145 , 28 , 37 , 39 ,130 , 26 , 37 , 46 ,159 , 67 , 47 , 61 ,206 ,102 ,138 ,116 ,429 ,131 ,207 ,121 ,325 ,119 , 98 ,106 ,347 ,108 , 77 , 62 ,330 , 83 , 72 , 51 ,242 , 56 , 44 , 28 ,145 , 32 , 34 , 27 , 78 , 31 , 24 , 15 , 81 , 52 , 27 , 15 ,
|
||||
39 , 72 ,103 ,179 , 29 , 52 , 53 ,207 , 40 , 62 , 66 ,258 , 75 , 80 ,114 ,420 , 81 , 89 ,125 ,392 ,105 , 88 ,120 ,488 ,115 ,119 ,184 ,614 ,194 ,321 ,286 ,1271 ,327 ,367 ,316 ,1021 ,303 ,287 ,238 ,1478 ,452 ,159 ,231 ,2465 ,662 ,191 ,265 ,1859 ,292 ,161 ,158 ,523 ,132 , 82 , 76 ,326 ,108 , 82 , 60 ,247 ,182 , 79 , 44 ,
|
||||
15 , 21 , 32 , 40 , 12 , 15 , 15 , 63 , 15 , 16 , 28 , 72 , 24 , 35 , 31 ,154 , 38 , 35 , 44 ,120 , 37 , 27 , 51 ,141 , 46 , 43 , 61 ,227 ,109 ,149 ,128 ,410 ,143 ,176 ,104 ,288 , 73 , 99 , 56 ,259 , 83 , 55 , 47 ,206 , 73 , 51 , 59 ,315 , 64 , 43 , 32 ,146 , 37 , 40 , 23 , 84 , 22 , 23 , 23 , 64 , 48 , 25 , 14 ,
|
||||
34 , 80 , 79 ,191 , 41 , 62 , 73 ,272 , 41 , 73 , 67 ,295 , 64 ,116 ,137 ,579 ,129 ,141 ,166 ,443 ,102 ,132 ,132 ,535 ,151 ,183 ,209 ,800 ,282 ,476 ,461 ,1521 ,406 ,526 ,351 ,1005 ,285 ,248 ,223 ,1036 ,341 ,172 ,215 ,1113 ,427 ,204 ,254 ,2027 ,432 ,172 ,189 ,828 ,198 ,118 , 99 ,437 ,127 ,108 , 89 ,355 ,204 ,114 , 50 ,
|
||||
13 , 70 , 76 ,116 , 28 , 41 , 57 ,139 , 32 , 37 , 48 ,203 , 57 , 66 , 74 ,308 , 60 , 62 ,131 ,273 , 89 , 66 , 83 ,322 , 79 , 81 ,138 ,423 ,180 ,250 ,246 ,760 ,214 ,276 ,174 ,540 ,165 ,102 , 86 ,610 ,155 , 82 ,109 ,509 ,164 , 87 ,121 ,723 ,212 , 81 ,101 ,637 ,168 , 46 , 69 ,296 , 76 , 54 , 61 ,209 ,182 , 78 , 66 ,
|
||||
14 , 36 , 53 ,132 , 17 , 38 , 21 ,121 , 24 , 34 , 40 ,153 , 38 , 39 , 45 ,290 , 39 , 64 , 68 ,185 , 49 , 54 , 61 ,256 , 53 , 88 , 71 ,330 ,135 ,213 ,177 ,577 ,159 ,162 ,164 ,401 ,113 , 96 ,114 ,415 ,138 , 91 , 73 ,369 ,148 , 79 , 75 ,502 ,112 , 69 , 87 ,295 , 97 , 63 , 40 ,274 ,105 , 51 , 34 ,194 ,156 , 70 , 54 ,
|
||||
14 , 46 , 63 , 89 , 14 , 50 , 17 , 97 , 21 , 24 , 30 ,116 , 22 , 41 , 44 ,181 , 35 , 37 , 43 ,185 , 32 , 55 , 62 ,201 , 39 , 47 , 82 ,273 ,112 ,159 ,131 ,512 ,110 ,163 ,117 ,303 ,103 , 67 , 86 ,322 , 90 , 65 , 46 ,304 , 94 , 55 , 88 ,376 , 89 , 50 , 61 ,248 , 89 , 36 , 58 ,234 , 85 , 44 , 40 ,210 ,293 , 73 , 44 ,
|
||||
17 , 16 , 21 , 40 , 8 , 10 , 14 , 45 , 8 , 14 , 7 , 42 , 13 , 13 , 15 , 70 , 17 , 29 , 20 , 64 , 19 , 10 , 29 , 69 , 23 , 16 , 20 , 90 , 25 , 64 , 58 ,167 , 72 , 75 , 41 ,121 , 35 , 29 , 15 ,118 , 25 , 30 , 25 , 90 , 28 , 29 , 20 , 95 , 19 , 25 , 16 , 73 , 17 , 18 , 12 , 54 , 17 , 31 , 14 , 66 , 43 , 27 , 23 ,
|
||||
{
|
||||
25, 61, 10, 20, 8, 25, 9, 24,
|
||||
10, 23, 9, 23, 13, 35, 19, 77,
|
||||
18, 56, 21, 38, 21, 49, 35, 65,
|
||||
45, 86, 80, 141, 197, 521, 1533, 2830,
|
||||
1891, 605, 232, 160, 91, 100, 63, 71,
|
||||
51, 57, 26, 43, 27, 36, 23, 68,
|
||||
22, 39, 13, 25, 14, 25, 10, 21,
|
||||
6, 23, 5, 19, 3, 49, 29,
|
||||
},
|
||||
{
|
||||
17, 14, 2, 15, 4, 10, 3, 16,
|
||||
5, 11, 6, 17, 8, 23, 17, 38,
|
||||
20, 34, 14, 35, 17, 34, 29, 42,
|
||||
47, 75, 83, 115, 145, 372, 910, 2907,
|
||||
2317, 1284, 375, 198, 116, 93, 52, 52,
|
||||
35, 46, 18, 33, 23, 22, 24, 34,
|
||||
10, 23, 9, 16, 9, 15, 8, 10,
|
||||
8, 7, 4, 9, 4, 17, 10,
|
||||
},
|
||||
{
|
||||
12, 34, 9, 24, 2, 26, 6, 15,
|
||||
7, 22, 18, 28, 11, 31, 17, 51,
|
||||
18, 29, 20, 35, 21, 51, 53, 68,
|
||||
53, 85, 68, 120, 151, 310, 525, 1339,
|
||||
2210, 1761, 988, 498, 210, 167, 96, 93,
|
||||
76, 54, 32, 44, 30, 53, 25, 60,
|
||||
26, 40, 24, 30, 6, 34, 13, 22,
|
||||
4, 26, 10, 18, 7, 35, 17,
|
||||
},
|
||||
{
|
||||
27, 33, 5, 15, 6, 15, 5, 41,
|
||||
12, 24, 15, 19, 12, 48, 12, 24,
|
||||
17, 29, 8, 34, 26, 60, 47, 69,
|
||||
40, 95, 94, 121, 151, 303, 468, 1041,
|
||||
1205, 1641, 1136, 986, 548, 304, 212, 195,
|
||||
123, 83, 55, 76, 27, 41, 33, 60,
|
||||
31, 36, 29, 24, 15, 27, 10, 17,
|
||||
6, 33, 8, 12, 3, 48, 26,
|
||||
},
|
||||
{
|
||||
42, 61, 6, 36, 16, 40, 8, 20,
|
||||
30, 20, 4, 30, 28, 40, 18, 47,
|
||||
26, 53, 22, 44, 26, 77, 53, 79,
|
||||
61, 128, 77, 108, 145, 265, 298, 776,
|
||||
670, 1079, 1128, 1269, 840, 603, 265, 226,
|
||||
165, 167, 63, 75, 49, 79, 42, 94,
|
||||
36, 44, 14, 59, 20, 30, 16, 28,
|
||||
12, 38, 22, 38, 12, 67, 34,
|
||||
},
|
||||
{
|
||||
22, 45, 8, 19, 5, 31, 8, 16,
|
||||
16, 28, 31, 14, 19, 36, 16, 56,
|
||||
31, 48, 59, 59, 22, 76, 50, 59,
|
||||
33, 96, 96, 127, 118, 266, 379, 651,
|
||||
577, 722, 835, 1152, 1019, 864, 535, 325,
|
||||
186, 184, 118, 101, 79, 73, 59, 127,
|
||||
50, 70, 45, 33, 25, 39, 22, 39,
|
||||
8, 28, 14, 8, 8, 45, 33,
|
||||
},
|
||||
{
|
||||
38, 53, 15, 34, 5, 25, 8, 44,
|
||||
20, 32, 19, 20, 19, 51, 25, 74,
|
||||
34, 55, 36, 76, 39, 67, 60, 74,
|
||||
36, 95, 82, 120, 131, 190, 352, 606,
|
||||
400, 509, 463, 769, 888, 966, 762, 570,
|
||||
330, 316, 162, 174, 120, 159, 86, 127,
|
||||
67, 86, 44, 53, 29, 70, 31, 38,
|
||||
24, 31, 10, 34, 12, 53, 53,
|
||||
},
|
||||
{
|
||||
46, 80, 7, 43, 4, 24, 7, 41,
|
||||
7, 48, 12, 43, 24, 51, 17, 73,
|
||||
38, 68, 29, 68, 34, 90, 14, 109,
|
||||
55, 126, 58, 146, 126, 221, 250, 630,
|
||||
370, 462, 370, 489, 430, 613, 737, 890,
|
||||
747, 535, 233, 197, 163, 185, 109, 99,
|
||||
65, 94, 29, 80, 51, 70, 31, 53,
|
||||
12, 48, 14, 41, 19, 87, 60,
|
||||
},
|
||||
{
|
||||
35, 86, 6, 41, 16, 25, 9, 38,
|
||||
45, 38, 28, 48, 22, 51, 28, 83,
|
||||
41, 73, 38, 41, 32, 112, 80, 80,
|
||||
70, 112, 96, 119, 141, 292, 337, 521,
|
||||
299, 347, 241, 340, 289, 488, 402, 649,
|
||||
572, 810, 440, 385, 295, 273, 167, 183,
|
||||
90, 102, 57, 102, 54, 73, 48, 61,
|
||||
32, 67, 25, 64, 12, 99, 115,
|
||||
},
|
||||
{
|
||||
47, 95, 21, 39, 13, 69, 8, 52,
|
||||
17, 65, 21, 60, 26, 43, 21, 95,
|
||||
82, 112, 21, 47, 43, 138, 52, 99,
|
||||
82, 125, 60, 130, 143, 273, 225, 555,
|
||||
286, 416, 251, 316, 234, 390, 268, 360,
|
||||
338, 507, 438, 646, 446, 386, 308, 281,
|
||||
182, 186, 86, 138, 26, 143, 34, 47,
|
||||
43, 121, 21, 69, 13, 30, 82,
|
||||
},
|
||||
{
|
||||
90, 129, 12, 60, 8, 51, 17, 17,
|
||||
30, 124, 38, 60, 34, 90, 47, 120,
|
||||
64, 99, 38, 94, 47, 163, 64, 112,
|
||||
73, 133, 77, 116, 133, 323, 262, 478,
|
||||
288, 353, 168, 185, 150, 336, 202, 232,
|
||||
232, 340, 284, 422, 469, 577, 478, 409,
|
||||
245, 189, 120, 163, 94, 155, 51, 112,
|
||||
64, 68, 51, 64, 21, 137, 107,
|
||||
},
|
||||
{
|
||||
67, 111, 29, 35, 24, 65, 16, 73,
|
||||
8, 51, 35, 70, 10, 97, 65, 189,
|
||||
59, 105, 40, 94, 51, 97, 62, 97,
|
||||
84, 127, 86, 151, 121, 311, 281, 512,
|
||||
289, 349, 178, 257, 151, 257, 214, 241,
|
||||
176, 273, 173, 252, 235, 344, 355, 650,
|
||||
376, 401, 214, 254, 140, 168, 84, 102,
|
||||
43, 97, 65, 97, 32, 140, 140,
|
||||
},
|
||||
{
|
||||
60, 174, 34, 60, 26, 87, 30, 43,
|
||||
17, 100, 26, 78, 47, 104, 52, 126,
|
||||
39, 108, 60, 113, 78, 113, 82, 143,
|
||||
60, 143, 69, 169, 91, 283, 239, 522,
|
||||
261, 274, 139, 217, 148, 174, 117, 226,
|
||||
156, 204, 143, 174, 191, 283, 248, 413,
|
||||
261, 331, 222, 383, 243, 296, 222, 239,
|
||||
100, 178, 74, 156, 34, 265, 222,
|
||||
},
|
||||
{
|
||||
160, 183, 41, 41, 5, 89, 29, 100,
|
||||
41, 89, 65, 47, 47, 77, 59, 136,
|
||||
53, 100, 47, 183, 47, 94, 35, 100,
|
||||
77, 142, 89, 142, 106, 272, 332, 522,
|
||||
249, 302, 178, 178, 178, 189, 106, 172,
|
||||
100, 261, 112, 178, 94, 290, 160, 284,
|
||||
136, 249, 106, 231, 172, 272, 201, 403,
|
||||
178, 308, 148, 213, 100, 338, 332,
|
||||
},
|
||||
{
|
||||
114, 158, 1, 86, 57, 86, 28, 100,
|
||||
86, 57, 28, 114, 57, 86, 43, 129,
|
||||
14, 86, 43, 57, 86, 114, 57, 158,
|
||||
57, 186, 129, 186, 158, 215, 215, 474,
|
||||
158, 316, 186, 172, 129, 316, 114, 114,
|
||||
201, 201, 71, 100, 186, 201, 114, 272,
|
||||
100, 172, 86, 143, 86, 330, 244, 301,
|
||||
158, 201, 129, 445, 86, 502, 675,
|
||||
},
|
||||
{
|
||||
173, 195, 21, 75, 37, 75, 5, 102,
|
||||
43, 113, 21, 86, 27, 92, 37, 173,
|
||||
37, 140, 54, 108, 48, 124, 48, 146,
|
||||
70, 173, 108, 195, 119, 227, 292, 596,
|
||||
238, 265, 151, 157, 130, 195, 54, 184,
|
||||
86, 249, 65, 130, 54, 178, 102, 254,
|
||||
124, 216, 54, 162, 86, 216, 92, 222,
|
||||
113, 205, 86, 216, 146, 807, 970,
|
||||
}
|
||||
*/};
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : CreateMvTrees
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Builds the VP5 huffman trees used for decoding motion vectors.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_CreateMvTrees ()
|
||||
{
|
||||
UINT32 i;
|
||||
|
||||
// Build the VP5 trees.
|
||||
memset( XMvHuffTables, 0, (sizeof(HUFF_NODE) * MV_ENTROPY_TABLES * (MV_ENTROPY_TOKENS-1)));
|
||||
memset( YMvHuffTables, 0, (sizeof(HUFF_NODE) * MV_ENTROPY_TABLES * (MV_ENTROPY_TOKENS-1)));
|
||||
for ( i = 0; i < MV_ENTROPY_TABLES; i ++ )
|
||||
{
|
||||
VP5_BuildHuffTree( XMvHuffTables[i], VP5_XMvFrequencyCounts[i], MV_ENTROPY_TOKENS );
|
||||
VP5_BuildHuffTree( YMvHuffTables[i], VP5_YMvFrequencyCounts[i], MV_ENTROPY_TOKENS );
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : CreateMvCodeArrays
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Creates the VP5 Mv huffman code arrays from the VP5
|
||||
* Mv huffman trees.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
//sjlhack - Jim, is this code used???????????????
|
||||
#if 0
|
||||
void VP5_CreateMvCodeArrays()
|
||||
{
|
||||
UINT32 i;
|
||||
|
||||
for ( i = 0; i < MV_ENTROPY_TABLES; i++ )
|
||||
{
|
||||
VP5_CreateCodeArray( XMvHuffTables[i], 0, XMvPatternTables[i], XMvBitsTables[i], 0, 0 );
|
||||
VP5_CreateCodeArray( YMvHuffTables[i], 0, YMvPatternTables[i], YMvBitsTables[i], 0, 0 );
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/* Decoder specific functions */
|
||||
#ifdef PBDLL
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_ExtractMVectorComponent
|
||||
*
|
||||
* INPUTS : Decoder Instance
|
||||
* Tree root
|
||||
* Invert sign flag
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Extracts a motion vector component for VP5
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
INT32 VP5_ExtractMVectorComponent(PB_INSTANCE *pbi, HUFF_NODE * hn, BOOL Invert )
|
||||
{
|
||||
int nodeptr = 0;
|
||||
int selector = 0;
|
||||
INT32 MvComponent;
|
||||
|
||||
// Loop searches down through tree based upon bits read from the bitstream
|
||||
// until it hits a leaf at which point we have decoded a token
|
||||
do
|
||||
{
|
||||
int which =DecodeBool(&pbi->br, hn[nodeptr].freq);
|
||||
if(which)
|
||||
{
|
||||
selector = hn[nodeptr].rightunion.right.selector;
|
||||
nodeptr = hn[nodeptr].rightunion.right.value;
|
||||
}
|
||||
else
|
||||
{
|
||||
selector = hn[nodeptr].leftunion.left.selector;
|
||||
nodeptr = (int) hn[nodeptr].leftunion.left.value;
|
||||
}
|
||||
}
|
||||
while ( !selector);
|
||||
|
||||
MvComponent = (INT32)(nodeptr - 31);
|
||||
return ( Invert ) ? (-MvComponent) : MvComponent;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : ExtractMVectorComponentA
|
||||
*
|
||||
* INPUTS : Decoder Instance
|
||||
* Tree root (Not used for VP4)
|
||||
* Invert sign flag (Not used for VP4)
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Extracts a motion vector component coded with method A.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
static INT32 ExtractMVectorComponentA(PB_INSTANCE *pbi, HUFF_NODE * hn, BOOL Invert )
|
||||
{
|
||||
INT32 MVectComponent; // temp storage for motion vector
|
||||
UINT32 MVCode = 0; // Temporary storage while decoding the MV
|
||||
UINT32 ExtraBits = 0;
|
||||
|
||||
// Get group to which coded component belongs
|
||||
MVCode = VP5_bitread( &pbi->br, 3 );
|
||||
|
||||
// Now extract the appropriate number of bits to identify the component
|
||||
switch ( MVCode )
|
||||
{
|
||||
case 0:
|
||||
MVectComponent = 0;
|
||||
break;
|
||||
case 1:
|
||||
MVectComponent = 1;
|
||||
break;
|
||||
case 2:
|
||||
MVectComponent = -1;
|
||||
break;
|
||||
case 3:
|
||||
if ( VP5_bitread1( &pbi->br ))
|
||||
MVectComponent = -2;
|
||||
else
|
||||
MVectComponent = 2;
|
||||
break;
|
||||
case 4:
|
||||
if ( VP5_bitread1( &pbi->br ) )
|
||||
MVectComponent = -3;
|
||||
else
|
||||
MVectComponent = 3;
|
||||
break;
|
||||
case 5:
|
||||
ExtraBits = VP5_bitread( &pbi->br, 2 );
|
||||
MVectComponent = 4 + ExtraBits;
|
||||
if ( VP5_bitread1( &pbi->br ) )
|
||||
MVectComponent = -MVectComponent;
|
||||
break;
|
||||
case 6:
|
||||
ExtraBits = VP5_bitread( &pbi->br, 3 );
|
||||
MVectComponent = 8 + ExtraBits;
|
||||
if ( VP5_bitread1( &pbi->br ))
|
||||
MVectComponent = -MVectComponent;
|
||||
break;
|
||||
case 7:
|
||||
ExtraBits = VP5_bitread( &pbi->br, 4 );
|
||||
MVectComponent = 16 + ExtraBits;
|
||||
if ( VP5_bitread1( &pbi->br ) )
|
||||
MVectComponent = -MVectComponent;
|
||||
break;
|
||||
}
|
||||
|
||||
return MVectComponent;
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : ExtractMVectorComponentB
|
||||
*
|
||||
* INPUTS : Decoder Instance
|
||||
* Tree root (Not used for VP4)
|
||||
* Invert sign flag (Not used for VP4)
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Extracts an MV component coded using the fallback method
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
static INT32 ExtractMVectorComponentB(PB_INSTANCE *pbi, HUFF_NODE * MvNodePtr, BOOL Invert )
|
||||
{
|
||||
INT32 MVectComponent; // temp storage for motion vector
|
||||
|
||||
// Get group to which coded component belongs
|
||||
MVectComponent = VP5_bitread( &pbi->br, 5 );
|
||||
if ( VP5_bitread1( &pbi->br ) )
|
||||
MVectComponent = -MVectComponent;
|
||||
|
||||
return MVectComponent;
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,439 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : TokenEntropy.c
|
||||
*
|
||||
* Description : Video CODEC: Coefficient token entropy module.
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.01 PGW 27 Jun 01 Created
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Header Frames
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#include "type_aliases.h"
|
||||
#include "systemdependant.h"
|
||||
#include "codec_common.h"
|
||||
#include "codec_common_interface.h"
|
||||
#include "tokenentropy.h"
|
||||
#include "pbdll.h"
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Explicit Imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Constants
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Types
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Data structures
|
||||
*****************************************************************************
|
||||
*/
|
||||
#ifndef MAPCA
|
||||
|
||||
// Costs in bits for different probabilities (expressed in range 0-255)
|
||||
// Costs are multiplied by 256
|
||||
const UINT32 ProbCost[256] =
|
||||
{
|
||||
2047,
|
||||
2047,1791,1641,1535,1452,1385,1328,1279,1235,1196,
|
||||
1161,1129,1099,1072,1046,1023,1000,979,959,940,
|
||||
922,905,889,873,858,843,829,816,803,790,
|
||||
778,767,755,744,733,723,713,703,693,684,
|
||||
675,666,657,649,641,633,625,617,609,602,
|
||||
594,587,580,573,567,560,553,547,541,534,
|
||||
528,522,516,511,505,499,494,488,483,477,
|
||||
472,467,462,457,452,447,442,437,433,428,
|
||||
424,419,415,410,406,401,397,393,389,385,
|
||||
381,377,373,369,365,361,357,353,349,346,
|
||||
342,338,335,331,328,324,321,317,314,311,
|
||||
307,304,301,297,294,291,288,285,281,278,
|
||||
275,272,269,266,263,260,257,255,252,249,
|
||||
246,243,240,238,235,232,229,227,224,221,
|
||||
219,216,214,211,208,206,203,201,198,196,
|
||||
194,191,189,186,184,181,179,177,174,172,
|
||||
170,168,165,163,161,159,156,154,152,150,
|
||||
148,145,143,141,139,137,135,133,131,129,
|
||||
127,125,123,121,119,117,115,113,111,109,
|
||||
107,105,103,101,99,97,95,93,92,90,
|
||||
88,86,84,82,81,79,77,75,73,72,
|
||||
70,68,66,65,63,61,60,58,56,55,
|
||||
53,51,50,48,46,45,43,41,40,38,
|
||||
37,35,33,32,30,29,27,25,24,22,
|
||||
21,19,18,16,15,13,12,10,9,7,
|
||||
6,4,3,1,
|
||||
1,
|
||||
};
|
||||
#endif
|
||||
// Index categories for previous tokens in this block
|
||||
const UINT8 PrevTokenIndex[MAX_ENTROPY_TOKENS] = { 0,1,2,2,2,2,2,2,2,2,2,0 };
|
||||
|
||||
// For details of tokens and extra bit breakdown see token definitions in huffman.h
|
||||
const UINT8 ExtraBitLengths_VP5[MAX_ENTROPY_TOKENS] = { 0, 1, 1, 1, 1, 2, 3, 4, 5, 6, 12, 0 };
|
||||
const UINT32 DctRangeMinVals[MAX_ENTROPY_TOKENS] = { 0, 1, 2, 3, 4, 5, 7, 11, 19, 35, 67, 0 };
|
||||
|
||||
const UINT8 DcUpdateProbs[2][MAX_ENTROPY_TOKENS-1] =
|
||||
{
|
||||
{ 146, 197, 181, 207, 232, 243, 238, 251, 244, 250, 249 },
|
||||
{ 179, 219, 214, 240, 250, 254, 244, 254, 254, 254, 254 }
|
||||
};
|
||||
|
||||
const UINT8 AcUpdateProbs[PREC_CASES][2][VP5_AC_BANDS][MAX_ENTROPY_TOKENS-1] =
|
||||
{
|
||||
{ // preceded by 0
|
||||
{
|
||||
{ 227, 246, 230, 247, 244, 254, 254, 254, 254, 254, 254 },
|
||||
{ 202, 254, 209, 231, 231, 249, 249, 253, 254, 254, 254 },
|
||||
{ 206, 254, 225, 242, 241, 251, 253, 254, 254, 254, 254 },
|
||||
{ 235, 254, 241, 253, 252, 254, 254, 254, 254, 254, 254 },
|
||||
{ 234, 254, 248, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
{
|
||||
{ 240, 254, 248, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 238, 254, 240, 253, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 244, 254, 251, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
},
|
||||
{ // preceded by 1
|
||||
{
|
||||
{ 206, 203, 227, 239, 247, 254, 253, 254, 254, 254, 254 },
|
||||
{ 207, 199, 220, 236, 243, 252, 252, 254, 254, 254, 254 },
|
||||
{ 212, 219, 230, 243, 244, 253, 252, 254, 254, 254, 254 },
|
||||
{ 236, 237, 247, 252, 253, 254, 254, 254, 254, 254, 254 },
|
||||
{ 240, 240, 248, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
{
|
||||
{ 230, 233, 249, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 238, 238, 250, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 248, 251, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
},
|
||||
{ // preceded by > 1
|
||||
{
|
||||
{ 225, 239, 227, 231, 244, 253, 243, 254, 254, 253, 254 },
|
||||
{ 232, 234, 224, 228, 242, 249, 242, 252, 251, 251, 254 },
|
||||
{ 235, 249, 238, 240, 251, 254, 249, 254, 253, 253, 254 },
|
||||
{ 249, 253, 251, 250, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 251, 250, 249, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
{
|
||||
{ 243, 244, 250, 250, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 249, 248, 250, 253, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 253, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
/*
|
||||
{
|
||||
{ // preceded by 0
|
||||
{
|
||||
{ 234, 246, 250, 249, 244, 254, 254, 254, 254, 254, 254 },
|
||||
{ 225, 254, 242, 238, 234, 253, 252, 254, 254, 254, 254 },
|
||||
{ 230, 254, 248, 243, 238, 254, 254, 254, 254, 254, 254 },
|
||||
{ 244, 254, 254, 252, 247, 254, 254, 254, 254, 254, 254 },
|
||||
{ 253, 254, 254, 254, 253, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
|
||||
227, 246, 230, 247, 244, 254, 254, 254, 254, 254, 254,
|
||||
202, 254, 209, 231, 231, 249, 249, 253, 254, 254, 254,
|
||||
206, 254, 225, 242, 241, 251, 253, 254, 254, 254, 254,
|
||||
235, 254, 241, 253, 252, 254, 254, 254, 254, 254, 254,
|
||||
234, 254, 248, 254, 254, 254, 254, 254, 254, 254, 254,
|
||||
254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254,
|
||||
},
|
||||
{
|
||||
{ 251, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 243, 254, 254, 253, 253, 254, 254, 254, 254, 254, 254 },
|
||||
{ 252, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
},
|
||||
{ // preceded by 1
|
||||
{
|
||||
{ 211, 216, 233, 233, 234, 252, 251, 254, 254, 254, 254 },
|
||||
{ 224, 219, 236, 237, 236, 252, 250, 254, 254, 253, 254 },
|
||||
{ 227, 230, 245, 241, 238, 253, 254, 254, 254, 254, 254 },
|
||||
{ 237, 235, 253, 252, 250, 254, 254, 254, 254, 254, 254 },
|
||||
{ 252, 251, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
{
|
||||
{ 237, 242, 253, 253, 253, 254, 254, 254, 254, 254, 254 },
|
||||
{ 248, 250, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 253, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
},
|
||||
{ // preceded by > 1
|
||||
{
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
{
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
{ 254, 254, 254, 254, 254, 254, 254, 254, 254, 254, 254 },
|
||||
},
|
||||
},
|
||||
};
|
||||
*/
|
||||
// DC context equations
|
||||
LINE_EQ DcNodeEqs[CONTEXT_NODES][TOKEN_CONTEXTS][TOKEN_CONTEXTS] =
|
||||
{
|
||||
{ // zero
|
||||
{ { 154, 61 },{ 141, 54 },{ 90, 45 },{ 54, 34 },{ 54, 13 },{ 128, 109 }, },
|
||||
{ { 136, 54 },{ 148, 45 },{ 92, 41 },{ 54, 33 },{ 51, 15 },{ 87, 113 }, },
|
||||
{ { 87, 44 },{ 97, 40 },{ 67, 36 },{ 46, 29 },{ 41, 15 },{ 64, 80 }, },
|
||||
{ { 59, 33 },{ 61, 31 },{ 51, 28 },{ 44, 22 },{ 33, 12 },{ 49, 63 }, },
|
||||
{ { 69, 12 },{ 59, 16 },{ 46, 14 },{ 31, 13 },{ 26, 6 },{ 92, 26 }, },
|
||||
{ { 128, 108 },{ 77, 119 },{ 54, 84 },{ 26, 71 },{ 87, 19 },{ 95, 155 }, },
|
||||
},
|
||||
{ // eob
|
||||
{ { 154, 4 },{ 182, 0 },{ 159, -8 },{ 128, -5 },{ 143, -5 },{ 187, 55 }, },
|
||||
{ { 182, 0 },{ 228, -3 },{ 187, -7 },{ 174, -9 },{ 189, -11 },{ 169, 79 }, },
|
||||
{ { 161, -9 },{ 192, -8 },{ 187, -9 },{ 169, -10 },{ 136, -9 },{ 184, 40 }, },
|
||||
{ { 164, -11 },{ 179, -10 },{ 174, -10 },{ 161, -10 },{ 115, -7 },{ 197, 20 }, },
|
||||
{ { 195, -11 },{ 195, -11 },{ 146, -10 },{ 110, -6 },{ 95, -4 },{ 195, 39 }, },
|
||||
{ { 182, 55 },{ 172, 77 },{ 177, 37 },{ 169, 29 },{ 172, 52 },{ 92, 162 }, },
|
||||
},
|
||||
{ // one
|
||||
{ { 174, 80 },{ 164, 80 },{ 95, 80 },{ 46, 66 },{ 56, 24 },{ 36, 193 }, },
|
||||
{ { 164, 80 },{ 166, 77 },{ 105, 76 },{ 49, 68 },{ 46, 31 },{ 49, 186 }, },
|
||||
{ { 97, 78 },{ 110, 74 },{ 72, 72 },{ 44, 60 },{ 33, 30 },{ 69, 131 }, },
|
||||
{ { 61, 61 },{ 69, 63 },{ 51, 57 },{ 31, 48 },{ 26, 27 },{ 64, 89 }, },
|
||||
{ { 67, 23 },{ 51, 32 },{ 36, 33 },{ 26, 28 },{ 20, 12 },{ 44, 68 }, },
|
||||
{ { 26, 197 },{ 41, 189 },{ 61, 129 },{ 28, 103 },{ 49, 52 },{ -12, 245 }, },
|
||||
},
|
||||
{ // low value
|
||||
{ { 102, 141 },{ 79, 166 },{ 72, 162 },{ 97, 125 },{ 179, 4 },{ 307, 0 }, },
|
||||
{ { 72, 168 },{ 69, 175 },{ 84, 160 },{ 105, 127 },{ 148, 34 },{ 310, 0 }, },
|
||||
{ { 84, 151 },{ 82, 161 },{ 87, 153 },{ 87, 135 },{ 115, 51 },{ 317, 0 }, },
|
||||
{ { 97, 125 },{ 102, 131 },{ 105, 125 },{ 87, 122 },{ 84, 64 },{ 54, 184 }, },
|
||||
{ { 166, 18 },{ 146, 43 },{ 125, 51 },{ 90, 64 },{ 95, 7 },{ 38, 154 }, },
|
||||
{ { 294, 0 },{ 13, 225 },{ 10, 225 },{ 67, 168 },{ 0, 167 },{ 161, 94 }, },
|
||||
},
|
||||
{ // two
|
||||
{ { 172, 76 },{ 172, 75 },{ 136, 80 },{ 64, 98 },{ 74, 67 },{ 315, 0 }, },
|
||||
{ { 169, 76 },{ 207, 56 },{ 164, 66 },{ 97, 80 },{ 67, 72 },{ 328, 0 }, },
|
||||
{ { 136, 80 },{ 187, 53 },{ 154, 62 },{ 72, 85 },{ -2, 105 },{ 305, 0 }, },
|
||||
{ { 74, 91 },{ 128, 64 },{ 113, 64 },{ 61, 77 },{ 41, 75 },{ 259, 0 }, },
|
||||
{ { 46, 84 },{ 51, 81 },{ 28, 89 },{ 31, 78 },{ 23, 77 },{ 202, 0 }, },
|
||||
{ { 323, 0 },{ 323, 0 },{ 300, 0 },{ 236, 0 },{ 195, 0 },{ 328, 0 }, },
|
||||
},
|
||||
};
|
||||
// AC context equations
|
||||
LINE_EQ AcNodeEqs[PREC_CASES][VP5_AC_BANDS-3][CONTEXT_NODES][TOKEN_CONTEXTS] =
|
||||
{
|
||||
{ // Preceded by 0
|
||||
{ // Band 0
|
||||
{ { 276, 0 },{ 238, 0 },{ 195, 0 },{ 156, 0 },{ 113, 0 },{ 274, 0 }, },
|
||||
{ { 0, 1 },{ 0, 1 },{ 0, 1 },{ 0, 1 },{ 0, 1 },{ 0, 1 }, },
|
||||
{ { 192, 59 },{ 182, 50 },{ 141, 48 },{ 110, 40 },{ 92, 19 },{ 125, 128 }, },
|
||||
{ { 169, 87 },{ 169, 83 },{ 184, 62 },{ 220, 16 },{ 184, 0 },{ 264, 0 }, },
|
||||
{ { 212, 40 },{ 212, 36 },{ 169, 49 },{ 174, 27 },{ 8, 120 },{ 182, 71 }, },
|
||||
},
|
||||
{ // Band 1
|
||||
{ { 259, 10 },{ 197, 19 },{ 143, 22 },{ 123, 16 },{ 110, 8 },{ 133, 88 }, },
|
||||
{ { 0, 1 },{ 256, 0 },{ 0, 1 },{ 0, 1 },{ 0, 1 },{ 0, 1 }, },
|
||||
{ { 207, 46 },{ 187, 50 },{ 97, 83 },{ 23, 100 },{ 41, 56 },{ 56, 188 }, },
|
||||
{ { 166, 90 },{ 146, 108 },{ 161, 88 },{ 136, 95 },{ 174, 0 },{ 266, 0 }, },
|
||||
{ { 264, 7 },{ 243, 18 },{ 184, 43 },{ -14, 154 },{ 20, 112 },{ 20, 199 }, },
|
||||
},
|
||||
{ // Band 2
|
||||
{ { 230, 26 },{ 197, 22 },{ 159, 20 },{ 146, 12 },{ 136, 4 },{ 54, 162 }, },
|
||||
{ { 0, 1 },{ 0, 1 },{ 0, 1 },{ 0, 1 },{ 0, 1 },{ 0, 1 }, },
|
||||
{ { 192, 59 },{ 156, 72 },{ 84, 101 },{ 49, 101 },{ 79, 47 },{ 79, 167 }, },
|
||||
{ { 138, 115 },{ 136, 116 },{ 166, 80 },{ 238, 0 },{ 195, 0 },{ 261, 0 }, },
|
||||
{ { 225, 33 },{ 205, 42 },{ 159, 61 },{ 79, 96 },{ 92, 66 },{ 28, 195 }, },
|
||||
},
|
||||
},
|
||||
{ // Preceded by 1
|
||||
{ // Band 0
|
||||
{ { 200, 37 },{ 197, 18 },{ 159, 13 },{ 143, 7 },{ 102, 5 },{ 123, 126 }, },
|
||||
{ { 197, 3 },{ 220, -9 },{ 210, -12 },{ 187, -6 },{ 151, -2 },{ 174, 80 }, },
|
||||
{ { 200, 53 },{ 187, 47 },{ 159, 40 },{ 118, 38 },{ 100, 18 },{ 141, 111 }, },
|
||||
{ { 179, 78 },{ 166, 86 },{ 197, 50 },{ 207, 27 },{ 187, 0 },{ 115, 139 }, },
|
||||
{ { 218, 34 },{ 220, 29 },{ 174, 46 },{ 128, 61 },{ 54, 89 },{ 187, 65 }, },
|
||||
},
|
||||
{ // Band 1
|
||||
{ { 238, 14 },{ 197, 18 },{ 125, 26 },{ 90, 25 },{ 82, 13 },{ 161, 86 }, },
|
||||
{ { 189, 1 },{ 205, -2 },{ 156, -4 },{ 143, -4 },{ 146, -4 },{ 172, 72 }, },
|
||||
{ { 230, 31 },{ 192, 45 },{ 102, 76 },{ 38, 85 },{ 56, 41 },{ 64, 173 }, },
|
||||
{ { 166, 91 },{ 141, 111 },{ 128, 116 },{ 118, 109 },{ 177, 0 },{ 23, 222 }, },
|
||||
{ { 253, 14 },{ 236, 21 },{ 174, 49 },{ 33, 118 },{ 44, 93 },{ 23, 187 }, },
|
||||
},
|
||||
{ // Band 2
|
||||
{ { 218, 28 },{ 179, 28 },{ 118, 35 },{ 95, 30 },{ 72, 24 },{ 128, 108 }, },
|
||||
{ { 187, 1 },{ 174, -1 },{ 125, -1 },{ 110, -1 },{ 108, -1 },{ 202, 52 }, },
|
||||
{ { 197, 53 },{ 146, 75 },{ 46, 118 },{ 33, 103 },{ 64, 50 },{ 118, 126 }, },
|
||||
{ { 138, 114 },{ 128, 122 },{ 161, 86 },{ 243, -6 },{ 195, 0 },{ 38, 210 }, },
|
||||
{ { 215, 39 },{ 179, 58 },{ 97, 101 },{ 95, 85 },{ 87, 70 },{ 69, 152 }, },
|
||||
},
|
||||
},
|
||||
{ // Preceded by 2
|
||||
{ // Band 0
|
||||
{ { 236, 24 },{ 205, 18 },{ 172, 12 },{ 154, 6 },{ 125, 1 },{ 169, 75 }, },
|
||||
{ { 187, 4 },{ 230, -2 },{ 228, -4 },{ 236, -4 },{ 241, -2 },{ 192, 66 }, },
|
||||
{ { 200, 46 },{ 187, 42 },{ 159, 34 },{ 136, 25 },{ 105, 10 },{ 179, 62 }, },
|
||||
{ { 207, 55 },{ 192, 63 },{ 192, 54 },{ 195, 36 },{ 177, 1 },{ 143, 98 }, },
|
||||
{ { 225, 27 },{ 207, 34 },{ 200, 30 },{ 131, 57 },{ 97, 60 },{ 197, 45 }, },
|
||||
},
|
||||
{ // Band 1
|
||||
{ { 271, 8 },{ 218, 13 },{ 133, 19 },{ 90, 19 },{ 72, 7 },{ 182, 51 }, },
|
||||
{ { 179, 1 },{ 225, -1 },{ 154, -2 },{ 110, -1 },{ 92, 0 },{ 195, 41 }, },
|
||||
{ { 241, 26 },{ 189, 40 },{ 82, 64 },{ 33, 60 },{ 67, 17 },{ 120, 94 }, },
|
||||
{ { 192, 68 },{ 151, 94 },{ 146, 90 },{ 143, 72 },{ 161, 0 },{ 113, 128 }, },
|
||||
{ { 256, 12 },{ 218, 29 },{ 166, 48 },{ 44, 99 },{ 31, 87 },{ 148, 78 }, },
|
||||
},
|
||||
{ // Band 2
|
||||
{ { 238, 20 },{ 184, 22 },{ 113, 27 },{ 90, 22 },{ 74, 9 },{ 192, 37 }, },
|
||||
{ { 184, 0 },{ 215, -1 },{ 141, -1 },{ 97, 0 },{ 49, 0 },{ 264, 13 }, },
|
||||
{ { 182, 51 },{ 138, 61 },{ 95, 63 },{ 54, 59 },{ 64, 25 },{ 200, 45 }, },
|
||||
{ { 179, 75 },{ 156, 87 },{ 174, 65 },{ 177, 44 },{ 174, 0 },{ 164, 85 }, },
|
||||
{ { 195, 45 },{ 148, 65 },{ 105, 79 },{ 95, 72 },{ 87, 60 },{ 169, 63 }, },
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
* Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : ConfigureContexts
|
||||
*
|
||||
* INPUTS : Decoder Instance
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Configures the context dependant entropy probabilities.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void ConfigureContexts(PB_INSTANCE *pbi)
|
||||
{
|
||||
UINT32 i,j;
|
||||
|
||||
UINT32 Band;
|
||||
UINT32 Node;
|
||||
UINT32 Plane;
|
||||
UINT32 Prec;
|
||||
INT32 Temp;
|
||||
|
||||
|
||||
// Clear MMX state so floating point can work again
|
||||
#ifndef MACPPC
|
||||
#ifndef MAPCA
|
||||
ClearSysState();
|
||||
#endif
|
||||
#endif
|
||||
|
||||
// DC Node Probabilities
|
||||
for ( Plane = 0; Plane < 2; Plane ++ )
|
||||
{
|
||||
for ( i = 0; i < TOKEN_CONTEXTS; i++ )
|
||||
{
|
||||
for ( j = 0; j < TOKEN_CONTEXTS; j++ )
|
||||
{
|
||||
// Tree Nodes
|
||||
for ( Node = 0; Node < CONTEXT_NODES; Node ++ )
|
||||
{
|
||||
Temp = ( ( pbi->DcProbs[DCProbOffset(Plane,Node)] * DcNodeEqs[Node][i][j].M + 128 ) >> 8)
|
||||
+ DcNodeEqs[Node][i][j].C;
|
||||
Temp = (Temp > 254)? 254: Temp;
|
||||
Temp = (Temp < 1)? 1 : Temp;
|
||||
pbi->DcNodeContexts[DCContextOffset(Plane,i,j,Node)] = (UINT8)Temp;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// AC Node Probabilities
|
||||
for ( Prec = 0; Prec < PREC_CASES; Prec++ )
|
||||
{
|
||||
for ( Plane = 0; Plane < 2; Plane ++ )
|
||||
{
|
||||
// Higher AC bands do not use contexts.
|
||||
for ( Band = 0; Band < VP5_AC_BANDS-3; Band++ )
|
||||
{
|
||||
for ( i = 0; i < TOKEN_CONTEXTS; i++ )
|
||||
{
|
||||
// Tree Nodes
|
||||
for ( Node = 0; Node < CONTEXT_NODES; Node ++ )
|
||||
{
|
||||
Temp = ( ( pbi->AcProbs[ACProbOffset(Plane,Prec,Band,Node)]
|
||||
* AcNodeEqs[Prec][Band][Node][i].M + 128 ) >> 8)
|
||||
+ AcNodeEqs[Prec][Band][Node][i].C;
|
||||
|
||||
Temp = (Temp > 254)? 254: Temp;
|
||||
Temp = (Temp < 1)? 1 : Temp;
|
||||
pbi->AcNodeContexts[ACContextOffset(Plane,Prec,Band,i,Node)] = (UINT8)Temp;
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,815 @@
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : boolhuff.c
|
||||
*
|
||||
* Description : Video CODEC
|
||||
*
|
||||
* AUTHOR : James Bankoski
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.00 JBB 01JUN01 Configuration baseline
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
#include "boolhuff.h"
|
||||
#ifdef MAPCA
|
||||
#include "eti/mm.h"
|
||||
#endif
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Forward references.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
// in the bool coder defined herein a probability of 4 means 4/256 chance its a 0 252/256 chance its a 1
|
||||
// so shannon cost of 0 given prob x = 8 - log2(x) | shannon cost of 1 given prob x = 8-log2(256-x)
|
||||
#ifndef MAPCA
|
||||
double shannonCost0[256]=
|
||||
{
|
||||
8.000000000,8.000000000,7.000000000,6.415037499,6.000000000,5.678071905,5.415037499,5.192645078,5.000000000,4.830074999,4.678071905,4.540568381,4.415037499,4.299560282,4.192645078,4.093109404,
|
||||
4.000000000,3.912537159,3.830074999,3.752072487,3.678071905,3.607682577,3.540568381,3.476438044,3.415037499,3.356143810,3.299560282,3.245112498,3.192645078,3.142019005,3.093109404,3.045803690,
|
||||
3.000000000,2.955605881,2.912537159,2.870716983,2.830074999,2.790546634,2.752072487,2.714597781,2.678071905,2.642447995,2.607682577,2.573735245,2.540568381,2.508146904,2.476438044,2.445411148,
|
||||
2.415037499,2.385290156,2.356143810,2.327574658,2.299560282,2.272079545,2.245112498,2.218640286,2.192645078,2.167109986,2.142019005,2.117356951,2.093109404,2.069262662,2.045803690,2.022720077,
|
||||
2.000000000,1.977632187,1.955605881,1.933910810,1.912537159,1.891475543,1.870716983,1.850252880,1.830074999,1.810175441,1.790546634,1.771181310,1.752072487,1.733213459,1.714597781,1.696219252,
|
||||
1.678071905,1.660149997,1.642447995,1.624960569,1.607682577,1.590609064,1.573735245,1.557056504,1.540568381,1.524266569,1.508146904,1.492205360,1.476438044,1.460841189,1.445411148,1.430144392,
|
||||
1.415037499,1.400087158,1.385290156,1.370643380,1.356143810,1.341788517,1.327574658,1.313499473,1.299560282,1.285754482,1.272079545,1.258533014,1.245112498,1.231815675,1.218640286,1.205584134,
|
||||
1.192645078,1.179821038,1.167109986,1.154509949,1.142019005,1.129635280,1.117356951,1.105182237,1.093109404,1.081136763,1.069262662,1.057485495,1.045803690,1.034215715,1.022720077,1.011315313,
|
||||
1.000000000,0.988772745,0.977632187,0.966576998,0.955605881,0.944717564,0.933910810,0.923184403,0.912537159,0.901967917,0.891475543,0.881058927,0.870716983,0.860448648,0.850252880,0.840128663,
|
||||
0.830074999,0.820090910,0.810175441,0.800327655,0.790546634,0.780831480,0.771181310,0.761595261,0.752072487,0.742612157,0.733213459,0.723875595,0.714597781,0.705379251,0.696219252,0.687117045,
|
||||
0.678071905,0.669083122,0.660149997,0.651271846,0.642447995,0.633677786,0.624960569,0.616295708,0.607682577,0.599120564,0.590609064,0.582147485,0.573735245,0.565371772,0.557056504,0.548788888,
|
||||
0.540568381,0.532394450,0.524266569,0.516184223,0.508146904,0.500154113,0.492205360,0.484300162,0.476438044,0.468618539,0.460841189,0.453105540,0.445411148,0.437757576,0.430144392,0.422571172,
|
||||
0.415037499,0.407542963,0.400087158,0.392669686,0.385290156,0.377948181,0.370643380,0.363375379,0.356143810,0.348948309,0.341788517,0.334664083,0.327574658,0.320519900,0.313499473,0.306513043,
|
||||
0.299560282,0.292640868,0.285754482,0.278900811,0.272079545,0.265290380,0.258533014,0.251807150,0.245112498,0.238448768,0.231815675,0.225212940,0.218640286,0.212097441,0.205584134,0.199100100,
|
||||
0.192645078,0.186218809,0.179821038,0.173451513,0.167109986,0.160796212,0.154509949,0.148250959,0.142019005,0.135813855,0.129635280,0.123483053,0.117356951,0.111256751,0.105182237,0.099133192,
|
||||
0.093109404,0.087110664,0.081136763,0.075187496,0.069262662,0.063362061,0.057485495,0.051632768,0.045803690,0.039998068,0.034215715,0.028456446,0.022720077,0.017006425,0.011315313,0.005646563
|
||||
};
|
||||
double shannonCost1[256]=
|
||||
{
|
||||
0.000000000,0.005646563,0.011315313,0.017006425,0.022720077,0.028456446,0.034215715,0.039998068,0.045803690,0.051632768,0.057485495,0.063362061,0.069262662,0.075187496,0.081136763,0.087110664,
|
||||
0.093109404,0.099133192,0.105182237,0.111256751,0.117356951,0.123483053,0.129635280,0.135813855,0.142019005,0.148250959,0.154509949,0.160796212,0.167109986,0.173451513,0.179821038,0.186218809,
|
||||
0.192645078,0.199100100,0.205584134,0.212097441,0.218640286,0.225212940,0.231815675,0.238448768,0.245112498,0.251807150,0.258533014,0.265290380,0.272079545,0.278900811,0.285754482,0.292640868,
|
||||
0.299560282,0.306513043,0.313499473,0.320519900,0.327574658,0.334664083,0.341788517,0.348948309,0.356143810,0.363375379,0.370643380,0.377948181,0.385290156,0.392669686,0.400087158,0.407542963,
|
||||
0.415037499,0.422571172,0.430144392,0.437757576,0.445411148,0.453105540,0.460841189,0.468618539,0.476438044,0.484300162,0.492205360,0.500154113,0.508146904,0.516184223,0.524266569,0.532394450,
|
||||
0.540568381,0.548788888,0.557056504,0.565371772,0.573735245,0.582147485,0.590609064,0.599120564,0.607682577,0.616295708,0.624960569,0.633677786,0.642447995,0.651271846,0.660149997,0.669083122,
|
||||
0.678071905,0.687117045,0.696219252,0.705379251,0.714597781,0.723875595,0.733213459,0.742612157,0.752072487,0.761595261,0.771181310,0.780831480,0.790546634,0.800327655,0.810175441,0.820090910,
|
||||
0.830074999,0.840128663,0.850252880,0.860448648,0.870716983,0.881058927,0.891475543,0.901967917,0.912537159,0.923184403,0.933910810,0.944717564,0.955605881,0.966576998,0.977632187,0.988772745,
|
||||
1.000000000,1.011315313,1.022720077,1.034215715,1.045803690,1.057485495,1.069262662,1.081136763,1.093109404,1.105182237,1.117356951,1.129635280,1.142019005,1.154509949,1.167109986,1.179821038,
|
||||
1.192645078,1.205584134,1.218640286,1.231815675,1.245112498,1.258533014,1.272079545,1.285754482,1.299560282,1.313499473,1.327574658,1.341788517,1.356143810,1.370643380,1.385290156,1.400087158,
|
||||
1.415037499,1.430144392,1.445411148,1.460841189,1.476438044,1.492205360,1.508146904,1.524266569,1.540568381,1.557056504,1.573735245,1.590609064,1.607682577,1.624960569,1.642447995,1.660149997,
|
||||
1.678071905,1.696219252,1.714597781,1.733213459,1.752072487,1.771181310,1.790546634,1.810175441,1.830074999,1.850252880,1.870716983,1.891475543,1.912537159,1.933910810,1.955605881,1.977632187,
|
||||
2.000000000,2.022720077,2.045803690,2.069262662,2.093109404,2.117356951,2.142019005,2.167109986,2.192645078,2.218640286,2.245112498,2.272079545,2.299560282,2.327574658,2.356143810,2.385290156,
|
||||
2.415037499,2.445411148,2.476438044,2.508146904,2.540568381,2.573735245,2.607682577,2.642447995,2.678071905,2.714597781,2.752072487,2.790546634,2.830074999,2.870716983,2.912537159,2.955605881,
|
||||
3.000000000,3.045803690,3.093109404,3.142019005,3.192645078,3.245112498,3.299560282,3.356143810,3.415037499,3.476438044,3.540568381,3.607682577,3.678071905,3.752072487,3.830074999,3.912537159,
|
||||
4.000000000,4.093109404,4.192645078,4.299560282,4.415037499,4.540568381,4.678071905,4.830074999,5.000000000,5.192645078,5.415037499,5.678071905,6.000000000,6.415037499,7.000000000,8.000000000
|
||||
};
|
||||
|
||||
unsigned int shannon64Cost0[256]={
|
||||
512,512,448,411,384,363,347,332,320,309,299,291,283,275,268,262,
|
||||
256,250,245,240,235,231,227,222,219,215,211,208,204,201,198,195,
|
||||
192,189,186,184,181,179,176,174,171,169,167,165,163,161,158,157,
|
||||
155,153,151,149,147,145,144,142,140,139,137,136,134,132,131,129,
|
||||
128,127,125,124,122,121,120,118,117,116,115,113,112,111,110,109,
|
||||
107,106,105,104,103,102,101,100,99,98,97,96,94,93,93,92,
|
||||
91,90,89,88,87,86,85,84,83,82,81,81,80,79,78,77,
|
||||
76,76,75,74,73,72,72,71,70,69,68,68,67,66,65,65,
|
||||
64,63,63,62,61,60,60,59,58,58,57,56,56,55,54,54,
|
||||
53,52,52,51,51,50,49,49,48,48,47,46,46,45,45,44,
|
||||
43,43,42,42,41,41,40,39,39,38,38,37,37,36,36,35,
|
||||
35,34,34,33,33,32,32,31,30,30,29,29,29,28,28,27,
|
||||
27,26,26,25,25,24,24,23,23,22,22,21,21,21,20,20,
|
||||
19,19,18,18,17,17,17,16,16,15,15,14,14,14,13,13,
|
||||
12,12,12,11,11,10,10,9,9,9,8,8,8,7,7,6,
|
||||
6,6,5,5,4,4,4,3,3,3,2,2,1,1,1,0,
|
||||
};
|
||||
unsigned int shannon64Cost1[256]={
|
||||
0,0,1,1,1,2,2,3,3,3,4,4,4,5,5,6,
|
||||
6,6,7,7,8,8,8,9,9,9,10,10,11,11,12,12,
|
||||
12,13,13,14,14,14,15,15,16,16,17,17,17,18,18,19,
|
||||
19,20,20,21,21,21,22,22,23,23,24,24,25,25,26,26,
|
||||
27,27,28,28,29,29,29,30,30,31,32,32,33,33,34,34,
|
||||
35,35,36,36,37,37,38,38,39,39,40,41,41,42,42,43,
|
||||
43,44,45,45,46,46,47,48,48,49,49,50,51,51,52,52,
|
||||
53,54,54,55,56,56,57,58,58,59,60,60,61,62,63,63,
|
||||
64,65,65,66,67,68,68,69,70,71,72,72,73,74,75,76,
|
||||
76,77,78,79,80,81,81,82,83,84,85,86,87,88,89,90,
|
||||
91,92,93,93,94,96,97,98,99,100,101,102,103,104,105,106,
|
||||
107,109,110,111,112,113,115,116,117,118,120,121,122,124,125,127,
|
||||
128,129,131,132,134,136,137,139,140,142,144,145,147,149,151,153,
|
||||
155,157,158,161,163,165,167,169,171,174,176,179,181,184,186,189,
|
||||
192,195,198,201,204,208,211,215,219,222,227,231,235,240,245,250,
|
||||
256,262,268,275,283,291,299,309,320,332,347,363,384,411,448,512,
|
||||
};
|
||||
#endif
|
||||
// TEMP STATS VARIABLES
|
||||
|
||||
/****************************************************************************
|
||||
* Module Static Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#ifdef NOTNORMALIZED
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StartDecode
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
* buffer ptr to data to start decoding
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function fills initializes the boolean coder
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void StartDecode(BOOL_CODER *bc, unsigned char *buffer)
|
||||
{
|
||||
bc->pos = 0;
|
||||
bc->value = 0;
|
||||
bc->range = 0;
|
||||
bc->buffer = buffer;
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DecodeBool
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
* prob probability of getting a 0 normalized to 8 bits
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : 0 or 1
|
||||
*
|
||||
* FUNCTION : This function determines the next value stored in the
|
||||
* boolean coder based upon the probability passed in.
|
||||
* It uses a simple probability model to approximate
|
||||
* an arithmetic coder.
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : The accuracy of this encoder gets worse as the range
|
||||
* approaches 0. This can be avoided with more complex
|
||||
* normalization functions (as in a standard arithmetic)
|
||||
* coder. I chose to avoid this for speed reasons.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
int DecodeBool(
|
||||
BOOL_CODER *bc,
|
||||
int probability)
|
||||
{
|
||||
unsigned int split;
|
||||
|
||||
// we don't have enough in our range to tell between a 0 and 1 so get
|
||||
// a new 3 bytes.
|
||||
if( bc->range < 2)
|
||||
{
|
||||
unsigned char *spot = bc->buffer+bc->pos;
|
||||
bc->v[0] = spot[0];
|
||||
bc->v[1] = spot[1];
|
||||
bc->v[2] = spot[2];
|
||||
|
||||
// range is set to 0x01000001 to avoid having the range * probability
|
||||
// calculation outrange ( this can be handled differently at the cost
|
||||
// of an extra if.
|
||||
bc->range = 0x01000000;
|
||||
bc->pos+=3;
|
||||
}
|
||||
|
||||
// calculate the decision point
|
||||
// black magic: This code works better than if I calculate probability *
|
||||
// range and then truncating to 1 ( I can't explain why)
|
||||
split = bc->range;
|
||||
split --; // we always have to maintain
|
||||
split *= probability;
|
||||
split >>= 8;
|
||||
split ++;
|
||||
|
||||
if( bc->value < split )
|
||||
{
|
||||
bc->range = split;
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
bc->range-=split;
|
||||
bc->value-=split;
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StopDecode
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function does clean up for boolean decoder
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void StopDecode(BOOL_CODER *bc)
|
||||
{
|
||||
return;
|
||||
}
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StartEncode
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
* buffer ptr to hold encoded data
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function fills initializes the boolean coder
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void StartEncode(BOOL_CODER *bc, unsigned char *buffer)
|
||||
{
|
||||
bc->pos = 0;
|
||||
bc->value = 0;
|
||||
bc->range = 0x01000000;
|
||||
bc->buffer = buffer;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : EncodeBool
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
* x value to encode
|
||||
* prob probability of getting a 0 normalized to 8 bits
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function encodes a boolean value using the
|
||||
* boolean coder.
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : The accuracy of this encoder gets worse as the range
|
||||
* approaches 0. This can be avoided with more complex
|
||||
* normalization functions (as in a standard arithmetic)
|
||||
* coder. I chose to avoid this for speed reasons.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void EncodeBool(BOOL_CODER *bc, int x, int probability)
|
||||
{
|
||||
unsigned int split;
|
||||
|
||||
// we don't have enough in our range to tell between a 0 and 1 so get
|
||||
// a new 3 bytes.
|
||||
if( bc->range < 2 )
|
||||
{
|
||||
bc->buffer[bc->pos] = bc->v[0];
|
||||
bc->buffer[bc->pos+1] = bc->v[1];
|
||||
bc->buffer[bc->pos+2] = bc->v[2];
|
||||
bc->pos+=3;
|
||||
|
||||
// range is set to 0x01000001 to avoid having the range * probability
|
||||
// calculation outrange ( this can be handled differently at the cost
|
||||
// of an extra if.
|
||||
bc->range = 0x01000000;
|
||||
bc->value = 0;
|
||||
}
|
||||
|
||||
// calculate the decision point
|
||||
// black magic: This code works better than if I calculate probability *
|
||||
// range and then truncating to 1 ( I can't explain why)
|
||||
split = bc->range;
|
||||
split --;
|
||||
split *= probability;
|
||||
split >>= 8;
|
||||
split ++;
|
||||
|
||||
if( x )
|
||||
{
|
||||
bc->range-=split;
|
||||
bc->value+=split;
|
||||
}
|
||||
else
|
||||
{
|
||||
bc->range = split;
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StopEncode
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function does clean up for boolean encoder
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void StopEncode(BOOL_CODER *bc)
|
||||
{
|
||||
int i;
|
||||
for(i=0;i<3;i++)
|
||||
{
|
||||
bc->buffer[bc->pos + i] =
|
||||
*((unsigned char *) &bc->value + i);
|
||||
}
|
||||
bc->pos+=3;
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
#ifndef MAPCA
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StartEncode
|
||||
*
|
||||
* INPUTS : br ptr to instance of our boolean coder
|
||||
* source ptr to data to start decoding
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function initializes the boolean coder
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void StartEncode
|
||||
(
|
||||
BOOL_CODER *br,
|
||||
unsigned char *source
|
||||
)
|
||||
{
|
||||
br->lowvalue = 0;
|
||||
br->range = 255;
|
||||
br->value = 0;
|
||||
br->count = -24;
|
||||
br->buffer=source;
|
||||
br->pos=0;
|
||||
}
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StopEncode
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function does clean up for boolean encoder
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void StopEncode
|
||||
(
|
||||
BOOL_CODER *br
|
||||
)
|
||||
{
|
||||
if(br->count<-16)
|
||||
br->lowvalue <<= (24-(br->count&7));
|
||||
else if(br->count<-8)
|
||||
br->lowvalue <<= (16-(br->count&7));
|
||||
else
|
||||
br->lowvalue <<= (8-(br->count&7));
|
||||
|
||||
br->buffer[br->pos++]=(br->lowvalue>>24);
|
||||
br->buffer[br->pos++]=(br->lowvalue>>16)& 0xff;
|
||||
br->buffer[br->pos++]=(br->lowvalue>>8)& 0xff;
|
||||
br->buffer[br->pos++]=(br->lowvalue)& 0xff;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : EncodeBool
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
* x value to encode
|
||||
* prob probability of getting a 0 normalized to 8 bits
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function encodes a boolean value using the
|
||||
* boolean coder.
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : This encoder uses normalizations, and is fairly accurate,
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void EncodeBool
|
||||
(
|
||||
BOOL_CODER * br,
|
||||
int bit,
|
||||
int probability
|
||||
)
|
||||
{
|
||||
unsigned int split;
|
||||
split = 1 + (((br->range-1) * probability) >> 8);
|
||||
if(bit)
|
||||
{
|
||||
br->lowvalue += split;
|
||||
br->range -= split;
|
||||
}
|
||||
else
|
||||
{
|
||||
br->range = split;
|
||||
}
|
||||
while(br->range < 0x80)
|
||||
{
|
||||
br->range <<= 1;
|
||||
|
||||
|
||||
if((br->lowvalue & 0x80000000 ))
|
||||
{
|
||||
int x = br->pos-1;
|
||||
while(x>=0 && br->buffer[x] == 0xff)
|
||||
{
|
||||
br->buffer[x] =(unsigned char)0;
|
||||
x--;
|
||||
}
|
||||
br->buffer[x]+=1;
|
||||
|
||||
}
|
||||
br->lowvalue <<= 1;
|
||||
if (!++br->count)
|
||||
{
|
||||
br->count = -8;
|
||||
br->buffer[br->pos++]=(br->lowvalue >> 24);
|
||||
br->lowvalue &= 0xffffff;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
// TEMP
|
||||
|
||||
extern const unsigned long ProbCost[256];
|
||||
extern const unsigned long ProbCost[256];
|
||||
void EncodeBool2
|
||||
(
|
||||
BOOL_CODER * br,
|
||||
int bit,
|
||||
int probability
|
||||
)
|
||||
{
|
||||
if (bit)
|
||||
br->BitCounter += ProbCost[255-probability];
|
||||
else
|
||||
br->BitCounter += ProbCost[probability];
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DecodeBool
|
||||
*
|
||||
* INPUTS : br ptr to instance of our boolean coder
|
||||
* prob probability of getting a 0 normalized to 8 bits
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : 0 or 1
|
||||
*
|
||||
* FUNCTION : This function determines the next value stored in the
|
||||
* boolean coder based upon the probability passed in.
|
||||
* It uses a simple probability model to approximate
|
||||
* an arithmetic coder.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
* SPECIAL NOTES : The DecodeBool128() is a special case for this
|
||||
* function that assums the input probability is 128
|
||||
*
|
||||
****************************************************************************/
|
||||
#ifdef MAPCA
|
||||
|
||||
int DecodeBool
|
||||
(
|
||||
BOOL_CODER * br,
|
||||
int probability
|
||||
)
|
||||
{
|
||||
|
||||
unsigned int bit;
|
||||
unsigned int split;
|
||||
unsigned int bigsplit;
|
||||
unsigned int lmbdoffset;
|
||||
int count = br->count;
|
||||
unsigned int range = br->range;
|
||||
unsigned int value = br->value;
|
||||
|
||||
split = 1 + (((range-1) * probability) >> 8);
|
||||
bigsplit = (split<<24);
|
||||
|
||||
if(value >= bigsplit)
|
||||
{
|
||||
range = range-split;
|
||||
value = value-bigsplit;
|
||||
bit = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
range = split;
|
||||
bit = 0;
|
||||
}
|
||||
|
||||
|
||||
if(range>=0x80)
|
||||
{
|
||||
br->value = value;
|
||||
br->range = range;
|
||||
return bit;
|
||||
|
||||
}
|
||||
|
||||
lmbdoffset = 7 - hmpv_lmo_32(range);
|
||||
value <<= lmbdoffset;
|
||||
range <<= lmbdoffset;
|
||||
count -= lmbdoffset;
|
||||
|
||||
if(count<=0)
|
||||
{
|
||||
count +=8;
|
||||
value |= ((unsigned int)br->buffer[br->pos]<<(8-count));
|
||||
br->pos++;
|
||||
|
||||
}
|
||||
|
||||
br->count = count;
|
||||
br->value = value;
|
||||
br->range = range;
|
||||
return bit;
|
||||
}
|
||||
|
||||
|
||||
#else
|
||||
int DecodeBool
|
||||
(
|
||||
BOOL_CODER * br,
|
||||
int probability
|
||||
)
|
||||
{
|
||||
|
||||
unsigned int bit=0;
|
||||
unsigned int split;
|
||||
unsigned int bigsplit;
|
||||
unsigned int count = br->count;
|
||||
unsigned int range = br->range;
|
||||
unsigned int value = br->value;
|
||||
|
||||
split = 1 + (((range-1) * probability) >> 8);
|
||||
bigsplit = (split<<24);
|
||||
|
||||
if(value >= bigsplit)
|
||||
{
|
||||
range -= split;
|
||||
value -= bigsplit;
|
||||
bit = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
range = split;
|
||||
}
|
||||
|
||||
if(range>=0x80)
|
||||
{
|
||||
br->value = value;
|
||||
br->range = range;
|
||||
return bit;
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
do
|
||||
{
|
||||
|
||||
range +=range;
|
||||
value <<=1;
|
||||
|
||||
if (!--count)
|
||||
{
|
||||
count = 8;
|
||||
value |= br->buffer[br->pos];
|
||||
br->pos++;
|
||||
}
|
||||
}while(range < 0x80 );
|
||||
}
|
||||
br->count = count;
|
||||
br->value = value;
|
||||
br->range = range;
|
||||
return bit;
|
||||
}
|
||||
#endif
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DecodeBool128
|
||||
*
|
||||
* INPUTS : br ptr to instance of our boolean coder
|
||||
*
|
||||
* RETURNS : 0 or 1
|
||||
*
|
||||
* FUNCTION : This function determines the next value stored in the
|
||||
* boolean coder based upon the probability passed in.
|
||||
* It uses a simple probability model to approximate
|
||||
* an arithmetic coder.
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
* SPECIAL NOTES : The DecodeBool128() is a special case for DecodeBool()
|
||||
* functionf and assums the input probability is 128
|
||||
*
|
||||
****************************************************************************/
|
||||
int DecodeBool128
|
||||
(
|
||||
BOOL_CODER * br
|
||||
)
|
||||
{
|
||||
unsigned int bit;
|
||||
unsigned int split;
|
||||
unsigned int bigsplit;
|
||||
unsigned int count = br->count;
|
||||
unsigned int range = br->range;
|
||||
unsigned int value = br->value;
|
||||
|
||||
split = ( range + 1) >> 1;
|
||||
bigsplit = (split<<24);
|
||||
|
||||
if(value >= bigsplit)
|
||||
{
|
||||
range = (range-split)<<1;
|
||||
value = (value-bigsplit)<<1;
|
||||
bit = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
range = split<<1;
|
||||
value = value<<1;
|
||||
bit = 0;
|
||||
}
|
||||
|
||||
if(!--count)
|
||||
{
|
||||
count=8;
|
||||
value |= br->buffer[br->pos];
|
||||
br->pos++;
|
||||
}
|
||||
br->count = count;
|
||||
br->value = value;
|
||||
br->range = range;
|
||||
return bit;
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StartDecode
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
* buffer ptr to data to start decoding
|
||||
*
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function fills initializes the boolean coder
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void StartDecode
|
||||
(
|
||||
BOOL_CODER *br,
|
||||
unsigned char *source
|
||||
)
|
||||
{
|
||||
br->lowvalue = 0;
|
||||
br->range = 255;
|
||||
br->count = 8;
|
||||
br->buffer=source;
|
||||
br->pos =0;
|
||||
br->value = (br->buffer[0]<<24)+(br->buffer[1]<<16)+(br->buffer[2]<<8)+(br->buffer[3]);
|
||||
br->pos+=4;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StopDecode
|
||||
*
|
||||
* INPUTS : bc ptr to instance of our boolean coder
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function does clean up for boolean decoder
|
||||
*
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void StopDecode(BOOL_CODER *bc)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,410 @@
|
||||
#include "pbdll.h"
|
||||
#include "misc_common.h"
|
||||
|
||||
|
||||
//#define OVERLAY_MOTION_VECTORS
|
||||
#include "xprintf.h"
|
||||
#if defined OVERLAY_MOTION_VECTORS
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DrawVector
|
||||
*
|
||||
* INPUTS : PB_INSTANCE *pbi
|
||||
* UINT8 *BlockPtr
|
||||
* INT32 x
|
||||
* INT32 y
|
||||
* UINT8 VectorColour
|
||||
* UINT8 DotColour
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None .
|
||||
*
|
||||
* FUNCTION : Draws motion vector into reconstruction buffer
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void DrawVector( PB_INSTANCE *pbi, UINT8 *BlockPtr, INT32 x, INT32 y, UINT8 VectorColour, UINT8 DotColour )
|
||||
{
|
||||
UINT8 *PixelPtr;
|
||||
double Xpos, Ypos;
|
||||
double Xdelta, Ydelta;
|
||||
INT32 x0, x1, y0, y1;
|
||||
|
||||
if ( abs(x) > abs(y) )
|
||||
{
|
||||
// Step along x axis
|
||||
if ( x < 0 )
|
||||
{
|
||||
x0 = x;
|
||||
x1 = 0;
|
||||
Ypos = (double)y;
|
||||
}
|
||||
else
|
||||
{
|
||||
x0 = 0;
|
||||
x1 = x;
|
||||
Ypos = 0.0;
|
||||
}
|
||||
|
||||
Ydelta = (double)y / (double)x;
|
||||
|
||||
for ( x=x0; x<=x1; x++ )
|
||||
{
|
||||
y = (UINT32)( Ypos<0.0 ? (Ypos-0.5) : (Ypos+0.5) );
|
||||
PixelPtr = BlockPtr + y*pbi->Configuration.YStride + x;
|
||||
*PixelPtr = VectorColour;
|
||||
Ypos += Ydelta;
|
||||
}
|
||||
}
|
||||
else if ( abs(y) > abs(x) )
|
||||
{
|
||||
// Step along y axis
|
||||
if ( y < 0 )
|
||||
{
|
||||
y0 = y;
|
||||
y1 = 0;
|
||||
Xpos = (double)x;
|
||||
}
|
||||
else
|
||||
{
|
||||
y0 = 0;
|
||||
y1 = y;
|
||||
Xpos = 0.0;
|
||||
}
|
||||
|
||||
Xdelta = (double)x / (double)y;
|
||||
|
||||
for ( y=y0; y<=y1; y++ )
|
||||
{
|
||||
x = (UINT32)( Xpos<0.0 ? (Xpos-0.5) : (Xpos+0.5) );
|
||||
PixelPtr = BlockPtr + y*pbi->Configuration.YStride + x;
|
||||
*PixelPtr = VectorColour;
|
||||
Xpos += Xdelta;
|
||||
}
|
||||
}
|
||||
|
||||
// Indicate current position in specified colour
|
||||
*BlockPtr = DotColour;
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DisplayMotionVectors
|
||||
*
|
||||
* INPUTS : PB_INSTANCE *pbi
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None .
|
||||
*
|
||||
* FUNCTION : Overlays colour coded motion vectors into reconstruction buffer
|
||||
*
|
||||
* SPECIAL NOTES : This routine will only display motion vectors when Post-processing
|
||||
* is enabled since it draws into the PostProcessBuffer.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void DisplayMotionVectors ( PB_INSTANCE *pbi )
|
||||
{
|
||||
INT32 FragIndex; // Fragment number
|
||||
UINT32 MB, B; // Macro-Block, Block indices
|
||||
UINT32 CodingMethod; // Temp Storage for coding mode.
|
||||
INT32 x, y;
|
||||
UINT32 Blocks;
|
||||
UINT32 BlockOffset[4] = {0, 1, pbi->HFragments, pbi->HFragments + 1};
|
||||
UINT8 *BlockPtr;
|
||||
UINT8 DotColour;
|
||||
UINT8 VectorColour;
|
||||
|
||||
// Nothing to display if keyframe
|
||||
if ( VP5_GetFrameType(pbi) == BASE_FRAME )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// Traverse the quad-tree
|
||||
for ( MB=0; MB<pbi->YMacroBlocks; MB++ )
|
||||
{
|
||||
// Is the Macro-Block coded:
|
||||
// if ( pbi->MBCodedFlags[MB] )
|
||||
{
|
||||
CodingMethod = pbi->FragInfo[FragIndex].FragCodingMode;
|
||||
|
||||
if ( VP5_ModeUsesMC[CodingMethod] )
|
||||
{
|
||||
// Indicate previous/golden frame predictor
|
||||
if ( CodingMethod == CODE_GOLDEN_MV )
|
||||
{
|
||||
DotColour = 0x00; // Black dot
|
||||
VectorColour = 0x7F; // Mid-Grey Vector
|
||||
}
|
||||
else if( (CodingMethod == CODE_INTER_LAST_MV) || (CodingMethod == CODE_INTER_PRIOR_LAST) )
|
||||
{
|
||||
DotColour = 0xFF; // White dot
|
||||
VectorColour = 0x00; // Black Vector
|
||||
}
|
||||
else
|
||||
{
|
||||
DotColour = 0x00; // Black dot
|
||||
VectorColour = 0xFF; // White Vector
|
||||
}
|
||||
|
||||
if ( CodingMethod == CODE_INTER_FOURMV )
|
||||
Blocks = 4;
|
||||
else
|
||||
Blocks = 1;
|
||||
|
||||
for ( B=0; B<Blocks; B++ )
|
||||
{
|
||||
// Pointer to top LH-corner of block
|
||||
BlockPtr = pbi->PostProcessBuffer ;// sorry adrian I'll fix it soon (removing getfragindex)
|
||||
//+ ReconGetFragIndex(pbi->recon_pixel_index_table, FragIndex+BlockOffset[B]);
|
||||
|
||||
// Motion vector ( oops motion vectors only remembered at the macroblock level now!!
|
||||
/*
|
||||
x = pbi->FragInfo[FragIndex + BlockOffset[B]].MVectorX;
|
||||
y = pbi->FragInfo[FragIndex + BlockOffset[B]].MVectorY;
|
||||
*/
|
||||
DrawVector( pbi, BlockPtr, x/2, y/2, VectorColour, DotColour );
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
/****************************************************************************
|
||||
Debugging Aid Only
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
Debugging Aid Only
|
||||
*/
|
||||
#ifdef _MSC_VER
|
||||
#include <stdio.h>
|
||||
void vp5_writeframe(PB_INSTANCE *pbi, char * address,int x)
|
||||
{
|
||||
// write the frame
|
||||
FILE *yframe;
|
||||
char filename[255];
|
||||
sprintf(filename,"y%04d.raw",x);
|
||||
yframe=fopen(filename,"wb");
|
||||
fwrite(address,pbi->ReconYPlaneSize+2*pbi->ReconUVPlaneSize,1,yframe);
|
||||
fclose(yframe);
|
||||
}
|
||||
void vp5_writeframe2(PB_INSTANCE *pbi, char * address,int x)
|
||||
{
|
||||
// write the frame
|
||||
FILE *yframe;
|
||||
char filename[255];
|
||||
sprintf(filename,"y%d.raw",x);
|
||||
yframe=fopen(filename,"wb");
|
||||
fwrite(address,pbi->YPlaneSize,1,yframe);
|
||||
fclose(yframe);
|
||||
}
|
||||
void vp5_draw(unsigned char *prefix, int frame, char * address,int size)
|
||||
{
|
||||
// write the frame
|
||||
FILE *yframe;
|
||||
char filename[255];
|
||||
sprintf(filename,"%s%04d.raw",prefix,frame);
|
||||
yframe=fopen(filename,"wb");
|
||||
fwrite(address,size,1,yframe);
|
||||
fclose(yframe);
|
||||
}
|
||||
void vp5_drawb(unsigned char *prefix, int frame, char * address,int pitch,int width,int height)
|
||||
{
|
||||
// write the frame
|
||||
FILE *yframe;
|
||||
int i;
|
||||
char filename[255];
|
||||
sprintf(filename,"%s%04d.raw",prefix,frame);
|
||||
yframe=fopen(filename,"wb");
|
||||
for(i=0;i<height;i++)
|
||||
{
|
||||
fwrite(address,width,1,yframe);
|
||||
address+=pitch;
|
||||
}
|
||||
fclose(yframe);
|
||||
}
|
||||
void vp5_drawc(char *filename, char * address,int pitch,int width,int height)
|
||||
{
|
||||
// write the frame
|
||||
FILE *yframe;
|
||||
int i;
|
||||
yframe=fopen(filename,"ab");
|
||||
for(i=0;i<height;i++)
|
||||
{
|
||||
fwrite(address,width,1,yframe);
|
||||
address+=pitch;
|
||||
}
|
||||
fclose(yframe);
|
||||
}
|
||||
|
||||
void vp5_showinfo2(PB_INSTANCE *pbi)
|
||||
{
|
||||
// int i;
|
||||
// for (i=0;i<pbi->PostProcessingLevel;i++)
|
||||
// pbi->PostProcessBuffer[pbi->Configuration.YStride * 32 + 32 + +4 +4*i] = 255;
|
||||
|
||||
vp5_xprintf(pbi,
|
||||
pbi->Configuration.YStride * 32 + 32,
|
||||
"F:%d Q:%d S:%d W:%d H:%d V:%d Decode:%8d, Blit:%8d, PP:%8d, P:%d",
|
||||
pbi->FrameType,
|
||||
pbi->quantizer->ThisFrameQuantizerValue,
|
||||
pbi->CurrentFrameSize,
|
||||
pbi->HFragments,
|
||||
pbi->VFragments,
|
||||
pbi->Vp3VersionNo,
|
||||
pbi->avgDecodeTime,
|
||||
pbi->avgBlitTime,
|
||||
pbi->avgPPTime[8],
|
||||
pbi->PostProcessingLevel);
|
||||
|
||||
}
|
||||
void vp5_appendframe(PB_INSTANCE *pbi)
|
||||
{
|
||||
// write the frame
|
||||
FILE *yframe;
|
||||
yframe=fopen("test.raw","ab");
|
||||
fwrite(pbi->LastFrameRecon,pbi->ReconYPlaneSize+2*pbi->ReconUVPlaneSize,1,yframe);
|
||||
fclose(yframe);
|
||||
}
|
||||
|
||||
void vp5_showinfo(PB_INSTANCE *pbi)
|
||||
{
|
||||
UINT32 MBrow, MBcol;
|
||||
UINT32 MBRows = pbi->MBRows;
|
||||
UINT32 MBCols = pbi->MBCols;
|
||||
|
||||
// for each row of macroblocks
|
||||
for ( MBrow=0; MBrow<MBRows; MBrow++ )
|
||||
{
|
||||
|
||||
// for each macroblock within a row of macroblocks
|
||||
for ( MBcol=0; MBcol<MBCols; MBcol++)
|
||||
{
|
||||
vp5_xprintf(pbi,
|
||||
((MBrow+1)* 16+5) * pbi->Configuration.YStride + (MBcol+1)*16+5,
|
||||
"%d",
|
||||
pbi->predictionMode[MBOffset(MBrow,MBcol)]);
|
||||
|
||||
} // mb col
|
||||
|
||||
|
||||
} // mbrow
|
||||
|
||||
{
|
||||
}
|
||||
}
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : PredictBlockToPostProcessBuffer
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Codes a DCT block
|
||||
*
|
||||
* Motion vectors and modes asumed to be defined at the MB level.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void PredictBlockToPostProcessBuffer
|
||||
(
|
||||
PB_INSTANCE *pbi,
|
||||
BLOCK_POSITION bp
|
||||
)
|
||||
{
|
||||
|
||||
memset(pbi->ReconDataBuffer,0,64*sizeof(short));
|
||||
|
||||
// Action depends on decode mode.
|
||||
if ( pbi->mbi.Mode == CODE_INTER_NO_MV ) // Inter with no motion vector
|
||||
{
|
||||
ReconInter( pbi->TmpDataBuffer, (UINT8 *)&pbi->PostProcessBuffer[pbi->mbi.Recon],
|
||||
(UINT8 *)&pbi->LastFrameRecon[pbi->mbi.Recon],
|
||||
pbi->ReconDataBuffer, pbi->mbi.CurrentReconStride);
|
||||
|
||||
}
|
||||
else if ( VP5_ModeUsesMC[pbi->mbi.Mode] ) // The mode uses a motion vector.
|
||||
{
|
||||
// For the compressor we did this already ( possible optimization).
|
||||
PredictFilteredBlock( pbi, pbi->TmpDataBuffer,bp);
|
||||
|
||||
ReconBlock(
|
||||
pbi->TmpDataBuffer,
|
||||
pbi->ReconDataBuffer,
|
||||
(UINT8 *)&pbi->PostProcessBuffer[pbi->mbi.Recon],
|
||||
pbi->mbi.CurrentReconStride );
|
||||
}
|
||||
else if ( pbi->mbi.Mode == CODE_USING_GOLDEN ) // Golden frame with motion vector
|
||||
{
|
||||
// Reconstruct the pixel data using the golden frame reconstruction and change data
|
||||
ReconInter( pbi->TmpDataBuffer, (UINT8 *)&pbi->PostProcessBuffer[pbi->mbi.Recon],
|
||||
(UINT8 *)&pbi->GoldenFrame[ pbi->mbi.Recon ],
|
||||
pbi->ReconDataBuffer, pbi->mbi.CurrentReconStride );
|
||||
}
|
||||
else // Simple Intra coding
|
||||
{
|
||||
// Get the pixel index for the first pixel in the fragment.
|
||||
ReconIntra( pbi->TmpDataBuffer, (UINT8 *)&pbi->PostProcessBuffer[pbi->mbi.Recon], (UINT16 *)pbi->ReconDataBuffer, pbi->mbi.CurrentReconStride );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void printmodes(PB_INSTANCE *pbi)
|
||||
{
|
||||
static int nFrame = 0; // PB_INSTANCE doesn't provide a frame number, does it?
|
||||
FILE *f=fopen("modes.txt","a");
|
||||
unsigned int i,j;
|
||||
|
||||
fprintf(f, "Frame %d\n\n", nFrame);
|
||||
|
||||
for(i=2;i<pbi->MBRows-2;i++)
|
||||
{
|
||||
if(pbi->Configuration.Interlaced == 1)
|
||||
{
|
||||
for(j=2;j<pbi->MBCols-2;j++)
|
||||
{
|
||||
fprintf(f,"%d",pbi->MBInterlaced[MBOffset(i,j)]);
|
||||
}
|
||||
fprintf(f," ");
|
||||
}
|
||||
for(j=2;j<pbi->MBCols-2;j++)
|
||||
{
|
||||
fprintf(f,"%d",pbi->predictionMode[MBOffset(i,j)]);
|
||||
}
|
||||
fprintf(f," ");
|
||||
for(j=2;j<pbi->MBCols-2;j++)
|
||||
{
|
||||
fprintf(f,"%3d:%-3d",pbi->MBMotionVector[MBOffset(i,j)].x,pbi->MBMotionVector[MBOffset(i,j)].y);
|
||||
}
|
||||
fprintf(f,"\n");
|
||||
}
|
||||
|
||||
fprintf(f,"\n");
|
||||
fprintf(f,"\n");
|
||||
fclose(f);
|
||||
|
||||
++nFrame;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,799 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : Decodemode.c
|
||||
*
|
||||
* Description : functions for decoding modes and motionvectors
|
||||
*
|
||||
* AUTHOR : James Bankoski
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.00 JBB 30OCT01 New Configuration baseline.
|
||||
* 1.01 JBB 04AP402 Reworked lower footprint mode compression scheme
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
//************************************************************************************
|
||||
// Decoding the Modes:
|
||||
//
|
||||
// Decode Mode Tree Looks like this :
|
||||
//
|
||||
//
|
||||
//
|
||||
//
|
||||
// zz
|
||||
//
|
||||
// 0 Mode Same As Last
|
||||
//
|
||||
//
|
||||
// 1 2
|
||||
//
|
||||
// 3 4 5 6
|
||||
//
|
||||
// NoMV +MV Nest Near Intra FourMV 7 8
|
||||
//
|
||||
// 00Gold GoldMV GNrst GNear
|
||||
//
|
||||
//
|
||||
// 30 probabilitity contexts are set up at each branch (in probMode) corresponding to
|
||||
//
|
||||
// 3 for what situation we are in at the mode level ( all modes available,
|
||||
// no nearest mv found, and no near mv found)
|
||||
//
|
||||
// 10 one for each possible last mode
|
||||
//
|
||||
// Note: if the last mode was near then the probability of getting near at position 4
|
||||
// above is set to 0 (it would have been coded as same as last). Note also that the
|
||||
// probablity of getting near when no near mv is available is also always set to 0.
|
||||
//
|
||||
// These probs are created from the 20 that can be xmitted in the bitstream (probXmitted)
|
||||
// For each mode 2 probabilities can be transmitted:
|
||||
// probability that the mode will appear if the last mode was the same
|
||||
// probability that the mode will appear if the last mode is not that mode
|
||||
//
|
||||
//************************************************************************************
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
#include "pbdll.h"
|
||||
#include "decodemode.h"
|
||||
#include "decodemv.h"
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Implicit Imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#ifdef MAPCA
|
||||
#include <eti/mm.h>
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
* Exported data structures.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Module statics.
|
||||
*****************************************************************************
|
||||
*/
|
||||
//*****************************************************************************
|
||||
// ModeVQ: This structure holds a table of probability vectors for encoding modes
|
||||
// To build this table a number of clips were run through and allowed to
|
||||
// select each of the probabilities that were best for them on each frame. These
|
||||
// choices were output and a vector quantizer was used to optimize the selection
|
||||
// of 16 vectors for each MODETYPE (allmodes available, nonearest, and no near)
|
||||
//*****************************************************************************
|
||||
UINT8 ModeVq[MODETYPES][MODEVECTORS][MAX_MODES*2]=
|
||||
{
|
||||
9,15,32,25,7,19,9,21,1,12,14,12,3,18,14,23,3,10,0,4,
|
||||
48,39,1,2,11,27,29,44,7,27,1,4,0,3,1,6,1,2,0,0,
|
||||
21,32,1,2,4,10,32,43,6,23,2,3,1,19,1,6,12,21,0,7,
|
||||
69,83,0,0,0,2,10,29,3,12,0,1,0,3,0,3,2,2,0,0,
|
||||
11,20,1,4,18,36,43,48,13,35,0,2,0,5,3,12,1,2,0,0,
|
||||
70,44,0,1,2,10,37,46,8,26,0,2,0,2,0,2,0,1,0,0,
|
||||
8,15,0,1,8,21,74,53,22,42,0,1,0,2,0,3,1,2,0,0,
|
||||
141,42,0,0,1,4,11,24,1,11,0,1,0,1,0,2,0,0,0,0,
|
||||
8,19,4,10,24,45,21,37,9,29,0,3,1,7,11,25,0,2,0,1,
|
||||
46,42,0,1,2,10,54,51,10,30,0,2,0,2,0,1,0,1,0,0,
|
||||
28,32,0,0,3,10,75,51,14,33,0,1,0,2,0,1,1,2,0,0,
|
||||
100,46,0,1,3,9,21,37,5,20,0,1,0,2,1,2,0,1,0,0,
|
||||
27,29,0,1,9,25,53,51,12,34,0,1,0,3,1,5,0,2,0,0,
|
||||
80,38,0,0,1,4,69,33,5,16,0,1,0,1,0,0,0,1,0,0,
|
||||
16,20,0,0,2,8,104,49,15,33,0,1,0,1,0,1,1,1,0,0,
|
||||
194,16,0,0,1,1,1,9,1,3,0,0,0,1,0,1,0,0,0,0,
|
||||
|
||||
41,22,1,0,1,31,0,0,0,0,0,1,1,7,0,1,98,25,4,10,
|
||||
123,37,6,4,1,27,0,0,0,0,5,8,1,7,0,1,12,10,0,2,
|
||||
26,14,14,12,0,24,0,0,0,0,55,17,1,9,0,36,5,7,1,3,
|
||||
209,5,0,0,0,27,0,0,0,0,0,1,0,1,0,1,0,0,0,0,
|
||||
2,5,4,5,0,121,0,0,0,0,0,3,2,4,1,4,2,2,0,1,
|
||||
175,5,0,1,0,48,0,0,0,0,0,2,0,1,0,2,0,1,0,0,
|
||||
83,5,2,3,0,102,0,0,0,0,1,3,0,2,0,1,0,0,0,0,
|
||||
233,6,0,0,0,8,0,0,0,0,0,1,0,1,0,0,0,1,0,0,
|
||||
34,16,112,21,1,28,0,0,0,0,6,8,1,7,0,3,2,5,0,2,
|
||||
159,35,2,2,0,25,0,0,0,0,3,6,0,5,0,1,4,4,0,1,
|
||||
75,39,5,7,2,48,0,0,0,0,3,11,2,16,1,4,7,10,0,2,
|
||||
212,21,0,1,0,9,0,0,0,0,1,2,0,2,0,0,2,2,0,0,
|
||||
4,2,0,0,0,172,0,0,0,0,0,1,0,2,0,0,2,0,0,0,
|
||||
187,22,1,1,0,17,0,0,0,0,3,6,0,4,0,1,4,4,0,1,
|
||||
133,6,1,2,1,70,0,0,0,0,0,2,0,4,0,3,1,1,0,0,
|
||||
251,1,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
|
||||
|
||||
2,3,2,3,0,2,0,2,0,0,11,4,1,4,0,2,3,2,0,4,
|
||||
49,46,3,4,7,31,42,41,0,0,2,6,1,7,1,4,2,4,0,1,
|
||||
26,25,1,1,2,10,67,39,0,0,1,1,0,14,0,2,31,26,1,6,
|
||||
103,46,1,2,2,10,33,42,0,0,1,4,0,3,0,1,1,3,0,0,
|
||||
14,31,9,13,14,54,22,29,0,0,2,6,4,18,6,13,1,5,0,1,
|
||||
85,39,0,0,1,9,69,40,0,0,0,1,0,3,0,1,2,3,0,0,
|
||||
31,28,0,0,3,14,130,34,0,0,0,1,0,3,0,1,3,3,0,1,
|
||||
171,25,0,0,1,5,25,21,0,0,0,1,0,1,0,0,0,0,0,0,
|
||||
17,21,68,29,6,15,13,22,0,0,6,12,3,14,4,10,1,7,0,3,
|
||||
51,39,0,1,2,12,91,44,0,0,0,2,0,3,0,1,2,3,0,1,
|
||||
81,25,0,0,2,9,106,26,0,0,0,1,0,1,0,1,1,1,0,0,
|
||||
140,37,0,1,1,8,24,33,0,0,1,2,0,2,0,1,1,2,0,0,
|
||||
14,23,1,3,11,53,90,31,0,0,0,3,1,5,2,6,1,2,0,0,
|
||||
123,29,0,0,1,7,57,30,0,0,0,1,0,1,0,1,0,1,0,0,
|
||||
13,14,0,0,4,20,175,20,0,0,0,1,0,1,0,1,1,1,0,0,
|
||||
202,23,0,0,1,3,2,9,0,0,0,1,0,1,0,1,0,0,0,0
|
||||
};
|
||||
|
||||
// These are the probabilities that we reset to after each keyframe.
|
||||
// It was created as the average probabilities of the trees.
|
||||
UINT8 BaselineXmittedProbs[4][2][10]=
|
||||
{
|
||||
42, 2, 7, 42, 22, 3, 2, 5, 1, 0, 69, 1, 1, 44, 6, 1, 0, 1, 0, 0,
|
||||
8, 1, 8, 0, 0, 2, 1, 0, 1, 0,229, 1, 0, 0, 0, 1, 0, 0, 1, 0,
|
||||
35, 1, 6, 34, 0, 2, 1, 1, 1, 0,122, 1, 1, 46, 0, 1, 0, 0, 1, 0,
|
||||
64, 0, 64, 64, 64, 0, 0, 0, 0, 0, 64, 0, 64, 64, 64, 0, 0, 0, 0, 0,
|
||||
};
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : BuildModeTree
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : Fills in probabilities at each branch of the huffman tree
|
||||
* based upon the frequencies transmitted in the bitstream.
|
||||
* probXmitted
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void BuildModeTree
|
||||
(
|
||||
PB_INSTANCE *pbi
|
||||
)
|
||||
{
|
||||
int i,j,k;
|
||||
|
||||
// make a huffman tree and code array for each of our modes (note each of the trees is minus the node give by probmodesame)
|
||||
for(i=0;i<10;i++)
|
||||
{
|
||||
unsigned int Counts[MAX_MODES];
|
||||
unsigned int total;
|
||||
|
||||
// set up the probabilities for each tree
|
||||
for(k=0;k<MODETYPES;k++)
|
||||
{
|
||||
total=0;
|
||||
for(j=0;j<10;j++)
|
||||
{
|
||||
if(i==j)
|
||||
{
|
||||
Counts[j]=0;
|
||||
}
|
||||
else
|
||||
{
|
||||
Counts[j]=100*pbi->probXmitted[k][0][j];
|
||||
}
|
||||
|
||||
|
||||
total+=Counts[j];
|
||||
}
|
||||
|
||||
|
||||
pbi->probModeSame[k][i] = 255-
|
||||
255 * pbi->probXmitted[k][1][i]
|
||||
/
|
||||
( 1 +
|
||||
pbi->probXmitted[k][1][i] +
|
||||
pbi->probXmitted[k][0][i]
|
||||
);
|
||||
|
||||
// each branch is basically calculated via
|
||||
// summing all posibilities at that branch.
|
||||
pbi->probMode[k][i][0]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_INTER_NO_MV]+
|
||||
Counts[CODE_INTER_PLUS_MV]+
|
||||
Counts[CODE_INTER_NEAREST_MV]+
|
||||
Counts[CODE_INTER_NEAR_MV]
|
||||
) /
|
||||
( 1 +
|
||||
total
|
||||
);
|
||||
|
||||
pbi->probMode[k][i][1]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_INTER_NO_MV]+
|
||||
Counts[CODE_INTER_PLUS_MV]
|
||||
) /
|
||||
(
|
||||
1 +
|
||||
Counts[CODE_INTER_NO_MV]+
|
||||
Counts[CODE_INTER_PLUS_MV]+
|
||||
Counts[CODE_INTER_NEAREST_MV]+
|
||||
Counts[CODE_INTER_NEAR_MV]
|
||||
);
|
||||
|
||||
pbi->probMode[k][i][2]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_INTRA]+
|
||||
Counts[CODE_INTER_FOURMV]
|
||||
) /
|
||||
(
|
||||
1 +
|
||||
Counts[CODE_INTRA]+
|
||||
Counts[CODE_INTER_FOURMV]+
|
||||
Counts[CODE_USING_GOLDEN]+
|
||||
Counts[CODE_GOLDEN_MV]+
|
||||
Counts[CODE_GOLD_NEAREST_MV]+
|
||||
Counts[CODE_GOLD_NEAR_MV]
|
||||
);
|
||||
|
||||
pbi->probMode[k][i][3]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_INTER_NO_MV]
|
||||
) /
|
||||
(
|
||||
1 +
|
||||
Counts[CODE_INTER_NO_MV]+
|
||||
Counts[CODE_INTER_PLUS_MV]
|
||||
);
|
||||
|
||||
pbi->probMode[k][i][4]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_INTER_NEAREST_MV]
|
||||
) /
|
||||
(
|
||||
1 +
|
||||
Counts[CODE_INTER_NEAREST_MV]+
|
||||
Counts[CODE_INTER_NEAR_MV]
|
||||
) ;
|
||||
|
||||
pbi->probMode[k][i][5]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_INTRA]
|
||||
) /
|
||||
(
|
||||
1 +
|
||||
Counts[CODE_INTRA]+
|
||||
Counts[CODE_INTER_FOURMV]
|
||||
);
|
||||
|
||||
pbi->probMode[k][i][6]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_USING_GOLDEN]+
|
||||
Counts[CODE_GOLDEN_MV]
|
||||
) /
|
||||
(
|
||||
1 +
|
||||
Counts[CODE_USING_GOLDEN]+
|
||||
Counts[CODE_GOLDEN_MV]+
|
||||
Counts[CODE_GOLD_NEAREST_MV]+
|
||||
Counts[CODE_GOLD_NEAR_MV]
|
||||
);
|
||||
|
||||
pbi->probMode[k][i][7]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_USING_GOLDEN]
|
||||
) /
|
||||
(
|
||||
1 +
|
||||
Counts[CODE_USING_GOLDEN]+
|
||||
Counts[CODE_GOLDEN_MV]
|
||||
);
|
||||
|
||||
pbi->probMode[k][i][8]= 1 + 255 *
|
||||
(
|
||||
Counts[CODE_GOLD_NEAREST_MV]
|
||||
) /
|
||||
(
|
||||
1 +
|
||||
Counts[CODE_GOLD_NEAREST_MV]+
|
||||
Counts[CODE_GOLD_NEAR_MV]
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : decodeModeDiff
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS : diff -> the probability difference value decoded from the bitstream
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : this function returns a value probability difference value
|
||||
* -256 to +256 in steps of 4 transmitted in the bitstream
|
||||
* using a fixed tree and hardcoded probabilities
|
||||
*
|
||||
* SPECIAL NOTES : The hard coded probabilities for the difference tree
|
||||
* were calcualated by taking the average number of times a
|
||||
* branch was taken on some sample material ie
|
||||
* (bond,bike,beautifulmind)
|
||||
*
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
int decodeModeDiff
|
||||
(
|
||||
PB_INSTANCE *pbi
|
||||
)
|
||||
{
|
||||
|
||||
int sign;
|
||||
if(DecodeBool(&pbi->br, 205)==0)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
sign = 1 + -2 * DecodeBool128(&pbi->br);
|
||||
|
||||
if( !DecodeBool(&pbi->br,171))
|
||||
{
|
||||
return sign<<(3-DecodeBool( &pbi->br,83));
|
||||
/*
|
||||
if( DecodeBool( &pbi->br,83))
|
||||
return sign*4;
|
||||
else
|
||||
return sign*8;
|
||||
*/
|
||||
}
|
||||
else
|
||||
{
|
||||
if( !DecodeBool( &pbi->br,199) )
|
||||
{
|
||||
if(DecodeBool( &pbi->br,140))
|
||||
return sign * 12;
|
||||
|
||||
if(DecodeBool( &pbi->br,125))
|
||||
return sign * 16;
|
||||
|
||||
if(DecodeBool( &pbi->br,104))
|
||||
return sign * 20;
|
||||
|
||||
return sign * 24;
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
int diff =VP5_bitread(&pbi->br,7);
|
||||
return sign *diff*4;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DecodeModeProbs
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : This function parses the probabilities xmitted in
|
||||
* the bitstream. The bitstream may either use the
|
||||
* lastframes baselines, or transmit a pointer to a
|
||||
* vector of new probabilities. It may then also
|
||||
* contain updates to each of these probabilities.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void DecodeModeProbs
|
||||
(
|
||||
PB_INSTANCE *pbi
|
||||
)
|
||||
{
|
||||
int i,j;
|
||||
// For each mode type (all modes available, no nearest, no near mode)
|
||||
for(j=0;j<MODETYPES;j++)
|
||||
{
|
||||
// determine whether we are sending a vector for this mode byte
|
||||
if(DecodeBool( &pbi->br, PROBVECTORXMIT) )
|
||||
{
|
||||
// figure out which vector we have encoded
|
||||
int whichVector = VP5_bitread(&pbi->br, 4);
|
||||
|
||||
// adjust the vector
|
||||
for(i=0;i<MAX_MODES;i++)
|
||||
{
|
||||
pbi->probXmitted[j][1][i] = ModeVq[j][whichVector][i*2];
|
||||
pbi->probXmitted[j][0][i] = ModeVq[j][whichVector][i*2+1];
|
||||
}
|
||||
}
|
||||
|
||||
// decode whether updates to bring it closer to ideal
|
||||
if( DecodeBool( &pbi->br, PROBIDEALXMIT) )
|
||||
{
|
||||
for(i=0;i<10;i++)
|
||||
{
|
||||
int diff;
|
||||
|
||||
// determine difference
|
||||
diff = decodeModeDiff(pbi);
|
||||
diff += pbi->probXmitted[j][1][i];
|
||||
|
||||
pbi->probXmitted[j][1][i] = (diff<0?0:(diff>255?255:diff));
|
||||
|
||||
// determine difference
|
||||
diff = decodeModeDiff(pbi);
|
||||
diff += pbi->probXmitted[j][0][i];
|
||||
|
||||
pbi->probXmitted[j][0][i] = (diff<0?0:(diff>255?255:diff));
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
BuildModeTree(pbi);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : decodeModeandMotionVector
|
||||
*
|
||||
* INPUTS : MBrow -> row
|
||||
MBcol -> column
|
||||
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : decodes a macroblock's mode and motion vectors from
|
||||
the bitstream
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void decodeModeAndMotionVector
|
||||
(
|
||||
PB_INSTANCE *pbi,
|
||||
UINT32 MBrow,
|
||||
UINT32 MBcol
|
||||
)
|
||||
{
|
||||
CODING_MODE mode;//lastmode;
|
||||
int type,type2;
|
||||
UINT32 k;
|
||||
MOTION_VECTORA NearestInterMVect,NearInterMVect;
|
||||
MOTION_VECTORA NearestGoldMVect,NearGoldMVect;
|
||||
MOTION_VECTOR mv;
|
||||
int x, y;
|
||||
|
||||
FindNearestandNextNearest(pbi,MBrow,MBcol,&NearestInterMVect,&NearInterMVect,1,&type);
|
||||
|
||||
mode = DecodeMode(pbi,pbi->LastMode,type);
|
||||
pbi->LastMode = mode;
|
||||
|
||||
pbi->predictionMode[MBOffset(MBrow,MBcol)] = mode;
|
||||
pbi->mbi.Mode = mode;
|
||||
if(mode ==CODE_INTER_FOURMV)
|
||||
{
|
||||
pbi->mbi.BlockMode[0] = DecodeBlockMode(pbi);
|
||||
pbi->mbi.BlockMode[1] = DecodeBlockMode(pbi);
|
||||
pbi->mbi.BlockMode[2] = DecodeBlockMode(pbi);
|
||||
pbi->mbi.BlockMode[3] = DecodeBlockMode(pbi);
|
||||
|
||||
pbi->mbi.BlockMode[4] = CODE_INTER_FOURMV;
|
||||
pbi->mbi.BlockMode[5] = CODE_INTER_FOURMV;
|
||||
|
||||
x=0;
|
||||
y=0;
|
||||
for(k=0;k<4;k++)
|
||||
{
|
||||
if(pbi->mbi.BlockMode[k]==CODE_INTER_NO_MV)
|
||||
{
|
||||
pbi->mbi.Mv[k].x = 0;
|
||||
pbi->mbi.Mv[k].y = 0;
|
||||
}
|
||||
else if( pbi->mbi.BlockMode[k]==CODE_INTER_NEAREST_MV)
|
||||
{
|
||||
pbi->mbi.Mv[k].x = NearestInterMVect.x;
|
||||
pbi->mbi.Mv[k].y = NearestInterMVect.y;
|
||||
x+=NearestInterMVect.x;
|
||||
y+=NearestInterMVect.y;
|
||||
}
|
||||
else if( pbi->mbi.BlockMode[k]==CODE_INTER_NEAR_MV)
|
||||
{
|
||||
pbi->mbi.Mv[k].x = NearInterMVect.x;
|
||||
pbi->mbi.Mv[k].y = NearInterMVect.y;
|
||||
x+=NearInterMVect.x;
|
||||
y+=NearInterMVect.y;
|
||||
}
|
||||
else if ( pbi->mbi.BlockMode[k]==CODE_INTER_PLUS_MV)
|
||||
{
|
||||
decodeMotionVector(pbi,&mv,NULL);
|
||||
pbi->mbi.Mv[k].x = mv.x;
|
||||
pbi->mbi.Mv[k].y = mv.y;
|
||||
x+=mv.x;
|
||||
y+=mv.y;
|
||||
}
|
||||
}
|
||||
x = (x+1+(x>=0))>>2;
|
||||
y = (y+1+(y>=0))>>2;
|
||||
|
||||
pbi->MBMotionVector[MBOffset(MBrow,MBcol)].x = pbi->mbi.Mv[3].x;
|
||||
pbi->MBMotionVector[MBOffset(MBrow,MBcol)].y = pbi->mbi.Mv[3].y;
|
||||
|
||||
pbi->mbi.Mv[4].x = x;
|
||||
pbi->mbi.Mv[4].y = y;
|
||||
|
||||
pbi->mbi.Mv[5].x = x;
|
||||
pbi->mbi.Mv[5].y = y;
|
||||
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
if(mode == CODE_INTER_NEAREST_MV)
|
||||
{
|
||||
x = NearestInterMVect.x;
|
||||
y = NearestInterMVect.y;
|
||||
}
|
||||
else if(mode == CODE_INTER_NEAR_MV)
|
||||
{
|
||||
x = NearInterMVect.x;
|
||||
y = NearInterMVect.y;
|
||||
}
|
||||
else
|
||||
{
|
||||
switch(mode)
|
||||
{
|
||||
/*
|
||||
case CODE_INTER_NEAREST_MV:
|
||||
x = NearestInterMVect.x;
|
||||
y = NearestInterMVect.y;
|
||||
break;
|
||||
case CODE_INTER_NEAR_MV:
|
||||
x = NearInterMVect.x;
|
||||
y = NearInterMVect.y;
|
||||
break;
|
||||
*/
|
||||
case CODE_GOLD_NEAREST_MV:
|
||||
FindNearestandNextNearest(pbi,MBrow,MBcol,&NearestGoldMVect,&NearGoldMVect,2,&type2);
|
||||
x = NearestGoldMVect.x;
|
||||
y = NearestGoldMVect.y;
|
||||
break;
|
||||
case CODE_GOLD_NEAR_MV:
|
||||
FindNearestandNextNearest(pbi,MBrow,MBcol,&NearestGoldMVect,&NearGoldMVect,2,&type2);
|
||||
x = NearGoldMVect.x;
|
||||
y = NearGoldMVect.y;
|
||||
break;
|
||||
case CODE_INTER_PLUS_MV:
|
||||
case CODE_GOLDEN_MV:
|
||||
decodeMotionVector(pbi,&mv,NULL);
|
||||
x = mv.x;
|
||||
y = mv.y;
|
||||
break;
|
||||
default:
|
||||
x =0;
|
||||
y =0;
|
||||
}
|
||||
}
|
||||
pbi->MBMotionVector[MBOffset(MBrow,MBcol)].x = x;
|
||||
pbi->MBMotionVector[MBOffset(MBrow,MBcol)].y = y;
|
||||
for(k=0;k<6;k++)
|
||||
{
|
||||
|
||||
pbi->mbi.Mv[k].x = x;
|
||||
pbi->mbi.Mv[k].y = y;
|
||||
pbi->mbi.BlockMode[k] = mode;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : decodeBlockMode
|
||||
*
|
||||
* INPUTS : mode -> mode we are trying to encode
|
||||
*
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : decodes a block mode from the bitstream as 2 bits
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
CODING_MODE
|
||||
DecodeBlockMode
|
||||
(
|
||||
PB_INSTANCE *pbi
|
||||
)
|
||||
|
||||
{
|
||||
|
||||
int choice = DecodeBool128(&pbi->br)<<1;
|
||||
choice += DecodeBool128(&pbi->br);
|
||||
|
||||
|
||||
switch(choice)
|
||||
{
|
||||
case 0:return CODE_INTER_NO_MV;//0
|
||||
case 1:return CODE_INTER_PLUS_MV;//2
|
||||
case 2:return CODE_INTER_NEAREST_MV;//3
|
||||
case 3:return CODE_INTER_NEAR_MV;//4
|
||||
}
|
||||
return (CODING_MODE)0;
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : decodeMode
|
||||
*
|
||||
* INPUTS : lastmode -> mode of the last coded macroblock
|
||||
* mode -> mode we are trying to encode
|
||||
* type -> MODE_TYPE (all modes available, nonearest
|
||||
* macroblock, no near macroblock)
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : decodes a MBmode from the bitstream using modecodearray
|
||||
* and probabilities that the value is the same as
|
||||
* lastmode stored in probModeSame, and the probability
|
||||
* of mode occuring if lastmode != mode stored in
|
||||
* probMode
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
CODING_MODE DecodeMode
|
||||
(
|
||||
PB_INSTANCE *pbi,
|
||||
CODING_MODE lastmode,
|
||||
UINT32 type
|
||||
)
|
||||
{
|
||||
CODING_MODE mode;
|
||||
if(DecodeBool(&pbi->br,pbi->probModeSame[type][lastmode]))
|
||||
{
|
||||
mode = lastmode;
|
||||
}
|
||||
else
|
||||
{ // 0
|
||||
UINT8 * Stats =pbi->probMode[type][lastmode];
|
||||
if(DecodeBool(&pbi->br,Stats[0]))
|
||||
{ // 2
|
||||
if(DecodeBool(&pbi->br,Stats[2]))
|
||||
{ //6
|
||||
if(DecodeBool(&pbi->br,Stats[6]))
|
||||
{ // 8
|
||||
|
||||
mode = CODE_GOLD_NEAREST_MV + DecodeBool(&pbi->br,Stats[8]);
|
||||
/*
|
||||
if(DecodeBool(&pbi->br,Stats[8]))
|
||||
{
|
||||
mode = CODE_GOLD_NEAR_MV;
|
||||
}
|
||||
else
|
||||
{
|
||||
mode = CODE_GOLD_NEAREST_MV;
|
||||
}
|
||||
*/
|
||||
|
||||
}
|
||||
else
|
||||
{ // 7
|
||||
mode = CODE_USING_GOLDEN + DecodeBool(&pbi->br,Stats[7]);
|
||||
/*
|
||||
if(DecodeBool(&pbi->br,Stats[7]))
|
||||
{
|
||||
mode = CODE_GOLDEN_MV;
|
||||
}
|
||||
else
|
||||
{
|
||||
mode = CODE_USING_GOLDEN;
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
||||
}
|
||||
else
|
||||
{ //5
|
||||
//mode = CODE_INTRA + 6*DecodeBool(&pbi->br,Stats[5]);
|
||||
|
||||
if(DecodeBool(&pbi->br,Stats[5]))
|
||||
{
|
||||
mode = CODE_INTER_FOURMV;
|
||||
}
|
||||
else
|
||||
{
|
||||
mode = CODE_INTRA;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
else
|
||||
{ // 1
|
||||
if(DecodeBool(&pbi->br,Stats[1]))
|
||||
{ // 4
|
||||
mode = CODE_INTER_NEAREST_MV + DecodeBool(&pbi->br,Stats[4]);
|
||||
/*
|
||||
if(DecodeBool(&pbi->br,Stats[4]))
|
||||
{
|
||||
mode = CODE_INTER_NEAR_MV;
|
||||
}
|
||||
else
|
||||
{
|
||||
mode = CODE_INTER_NEAREST_MV;
|
||||
}
|
||||
*/
|
||||
|
||||
}
|
||||
else
|
||||
{ // 3
|
||||
mode = CODE_INTER_NO_MV + 2 * DecodeBool(&pbi->br,Stats[3]);
|
||||
/*
|
||||
if(DecodeBool(&pbi->br,Stats[3]))
|
||||
{
|
||||
mode = CODE_INTER_PLUS_MV;
|
||||
}
|
||||
else
|
||||
{
|
||||
mode = CODE_INTER_NO_MV;
|
||||
}
|
||||
*/
|
||||
}
|
||||
}
|
||||
}
|
||||
return mode;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,366 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : Decodemv.c
|
||||
*
|
||||
* Description : functions for decoding modes and motionvectors
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.00 JBB 30OCT01 New Configuration baseline.
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
#include "pbdll.h"
|
||||
#include "boolhuff.h"
|
||||
#include "huffman.h"
|
||||
#include "stdio.h"
|
||||
#include "decodemode.h"
|
||||
#include "decodemv.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Implicit Imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#ifdef MAPCA
|
||||
#include <eti/mm.h>
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Exported data structures.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Module statics.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
UINT8 MvUpdateProbs[2][MV_NODES] =
|
||||
{
|
||||
{ 243, 220, 251, 253, 237, 232, 241, 245, 247, 251, 253 },
|
||||
{ 235, 211, 246, 249, 234, 231, 248, 249, 252, 252, 254 }
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : ConfigureMvEntropyDecoder
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : Build the MV entropy decoding tree
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
***************************************************************************/
|
||||
void ConfigureMvEntropyDecoder( PB_INSTANCE *pbi, UINT8 FrameType )
|
||||
{
|
||||
int i;
|
||||
|
||||
//This funciton is not called at all if it is a BASE_FRAME
|
||||
/*
|
||||
if ( FrameType == BASE_FRAME)
|
||||
{
|
||||
// Set up the default values for each of the MV probabilities
|
||||
// For now these are just 128
|
||||
memset ( pbi->MvSignProbs, 128, sizeof(pbi->MvSignProbs) );
|
||||
memset ( pbi->MvZeroProbs, 128, sizeof(pbi->MvZeroProbs) );
|
||||
memset ( pbi->MvHalfPixelProbs, DEFAULT_HALF_PIXEL_PROB, sizeof(pbi->MvHalfPixelProbs) );
|
||||
memset ( pbi->MvLowBitProbs, 128, sizeof(pbi->MvLowBitProbs) );
|
||||
memset ( pbi->MvSizeProbs, 128, sizeof(pbi->MvSizeProbs) );
|
||||
}
|
||||
else
|
||||
*/
|
||||
{
|
||||
// Calculate and if necessary send the Zero, sign, half pixel and Low order probabilities.
|
||||
for ( i = 0; i < 2; i++ )
|
||||
{
|
||||
// Zero probability
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][0]) )
|
||||
{
|
||||
pbi->MvZeroProbs[i] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvZeroProbs[i] == 0 )
|
||||
pbi->MvZeroProbs[i] = 1;
|
||||
}
|
||||
|
||||
// Sign probability
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][1]) )
|
||||
{
|
||||
pbi->MvSignProbs[i] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvSignProbs[i] == 0 )
|
||||
pbi->MvSignProbs[i] = 1;
|
||||
}
|
||||
|
||||
// Half pixel bit probability
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][2]) )
|
||||
{
|
||||
pbi->MvHalfPixelProbs[i] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvHalfPixelProbs[i] == 0 )
|
||||
pbi->MvHalfPixelProbs[i] = 1;
|
||||
}
|
||||
|
||||
// Low order magnitude bit Probability
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][3]) )
|
||||
{
|
||||
pbi->MvLowBitProbs[i] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvLowBitProbs[i] == 0 )
|
||||
pbi->MvLowBitProbs[i] = 1;
|
||||
}
|
||||
}
|
||||
|
||||
// Now vector magnitude Probabilities
|
||||
for ( i = 0; i < 2; i++ )
|
||||
{
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][4]) )
|
||||
{
|
||||
pbi->MvSizeProbs[i][0] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvSizeProbs[i][0] == 0 )
|
||||
pbi->MvSizeProbs[i][0] = 1;
|
||||
}
|
||||
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][5]) )
|
||||
{
|
||||
pbi->MvSizeProbs[i][1] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvSizeProbs[i][1] == 0 )
|
||||
pbi->MvSizeProbs[i][1] = 1;
|
||||
}
|
||||
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][6]) )
|
||||
{
|
||||
pbi->MvSizeProbs[i][2] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvSizeProbs[i][2] == 0 )
|
||||
pbi->MvSizeProbs[i][2] = 1;
|
||||
}
|
||||
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][7]) )
|
||||
{
|
||||
pbi->MvSizeProbs[i][3] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvSizeProbs[i][3] == 0 )
|
||||
pbi->MvSizeProbs[i][3] = 1;
|
||||
}
|
||||
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][8]) )
|
||||
{
|
||||
pbi->MvSizeProbs[i][4] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvSizeProbs[i][4] == 0 )
|
||||
pbi->MvSizeProbs[i][4] = 1;
|
||||
}
|
||||
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][9]) )
|
||||
{
|
||||
pbi->MvSizeProbs[i][5] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvSizeProbs[i][5] == 0 )
|
||||
pbi->MvSizeProbs[i][5] = 1;
|
||||
}
|
||||
|
||||
if ( DecodeBool(&pbi->br, MvUpdateProbs[i][10]) )
|
||||
{
|
||||
pbi->MvSizeProbs[i][6] = VP5_bitread( &pbi->br, PROB_UPDATE_BASELINE_COST ) << 1;
|
||||
if ( pbi->MvSizeProbs[i][6] == 0 )
|
||||
pbi->MvSizeProbs[i][6] = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : decodeMotionVector
|
||||
*
|
||||
* INPUTS : *mv -> returned motion vector
|
||||
*nearestMv -> passed in mv acting as context
|
||||
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
* FUNCTION : decodes a motion vector from the bitstream
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void decodeMotionVector
|
||||
(
|
||||
PB_INSTANCE *pbi,
|
||||
MOTION_VECTOR *mv,
|
||||
MOTION_VECTOR *nearestMv
|
||||
)
|
||||
{
|
||||
UINT32 i;
|
||||
INT32 Vector = 0;
|
||||
INT32 SignBit;
|
||||
INT32 HpBit;
|
||||
INT32 LowBit;
|
||||
|
||||
for ( i = 0; i < 2; i++ )
|
||||
{
|
||||
Vector = 0;
|
||||
|
||||
// Is the vector non-zero
|
||||
if ( DecodeBool(&pbi->br, pbi->MvZeroProbs[i]) )
|
||||
{
|
||||
// Read the sign, half pixel and low order bits
|
||||
SignBit = DecodeBool(&pbi->br, pbi->MvSignProbs[i]);
|
||||
|
||||
// Read half pixel and low order bits
|
||||
HpBit = DecodeBool(&pbi->br, pbi->MvHalfPixelProbs[i]);
|
||||
LowBit = DecodeBool(&pbi->br, pbi->MvLowBitProbs[i]);
|
||||
|
||||
// Now read the magnitude bits
|
||||
if ( DecodeBool(&pbi->br, pbi->MvSizeProbs[i][0] ) )
|
||||
{
|
||||
Vector = 1 << 4;
|
||||
if ( DecodeBool(&pbi->br, pbi->MvSizeProbs[i][4]) )
|
||||
{
|
||||
Vector |= (1 << 3);
|
||||
Vector |= DecodeBool(&pbi->br, pbi->MvSizeProbs[i][6]) << 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
Vector |= DecodeBool(&pbi->br, pbi->MvSizeProbs[i][5]) << 2;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( DecodeBool(&pbi->br, pbi->MvSizeProbs[i][1]) )
|
||||
{
|
||||
Vector |= (1 << 3);
|
||||
Vector |= DecodeBool(&pbi->br, pbi->MvSizeProbs[i][3]) << 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
Vector |= DecodeBool(&pbi->br, pbi->MvSizeProbs[i][2]) << 2;
|
||||
}
|
||||
}
|
||||
|
||||
// Now Add in the low order and sign bits
|
||||
Vector |= HpBit;
|
||||
Vector |= (LowBit << 1);
|
||||
if ( SignBit )
|
||||
Vector = -Vector;
|
||||
}
|
||||
|
||||
if ( i )
|
||||
mv->y = Vector;
|
||||
else
|
||||
mv->x = Vector;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : FindNearestandNextNearest
|
||||
*
|
||||
* INPUTS :
|
||||
MBrow row of macroblock to check
|
||||
MBcol col of macroblock to check
|
||||
*nearest returns nearest motion vector if found 0,0 otherwise
|
||||
*near returns next nearest motion vector if found 0,0 otherwise
|
||||
frame which frame motion vector should come from (gold or last)
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS : true if motion vector differs
|
||||
false otherwise
|
||||
*
|
||||
* FUNCTION : search through the existing motion vectors for two different MVs
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void FindNearestandNextNearest
|
||||
(
|
||||
PB_INSTANCE *pbi,
|
||||
UINT32 MBrow,
|
||||
UINT32 MBcol,
|
||||
MOTION_VECTORA *nearest,
|
||||
MOTION_VECTORA *nextnearest,
|
||||
UINT8 Frame,
|
||||
int *type
|
||||
)
|
||||
{
|
||||
UINT32 BaseMB = MBOffset(MBrow,MBcol);
|
||||
UINT32 OffsetMB;
|
||||
int i;
|
||||
|
||||
nearest->x=0;
|
||||
nearest->y=0;
|
||||
nextnearest->x=0;
|
||||
nextnearest->y=0;
|
||||
*type = NONEAREST_MACROBLOCK;
|
||||
|
||||
for(i=0;i<12;i++)
|
||||
{
|
||||
|
||||
OffsetMB = pbi->mvNearOffset[i]+BaseMB;
|
||||
|
||||
if(VP5_Mode2Frame[pbi->predictionMode[OffsetMB]] != Frame)
|
||||
continue;
|
||||
|
||||
if(*((unsigned int *) &pbi->MBMotionVector[OffsetMB]) == 0)
|
||||
continue;
|
||||
|
||||
*((unsigned int *) nearest) = *((unsigned int *) &pbi->MBMotionVector[OffsetMB]);
|
||||
*type = NONEAR_MACROBLOCK;
|
||||
|
||||
break;
|
||||
|
||||
}
|
||||
|
||||
if(*((unsigned int *) nearest))
|
||||
{
|
||||
for(i=i+1;i<12;i++)
|
||||
{
|
||||
|
||||
OffsetMB = pbi->mvNearOffset[i]+BaseMB;
|
||||
|
||||
if(VP5_Mode2Frame[pbi->predictionMode[OffsetMB]] != Frame)
|
||||
continue;
|
||||
|
||||
if( *((unsigned int *) &pbi->MBMotionVector[OffsetMB])
|
||||
== *((unsigned int *) nearest) )
|
||||
continue;
|
||||
|
||||
if(*((unsigned int *) &pbi->MBMotionVector[OffsetMB]) == 0)
|
||||
continue;
|
||||
|
||||
*((unsigned int *) nextnearest) = *((unsigned int *) &pbi->MBMotionVector[OffsetMB]);
|
||||
*type = MACROBLOCK;
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,438 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : vp5dxv.c
|
||||
*
|
||||
* Description : VP50 interface to DXV.
|
||||
*
|
||||
* AUTHOR : SJL
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.03 SJL 17/10/02 Up the version to 1.0.0.3, added new dxv interface
|
||||
* 1.02 YWX 30/09/02 Up the version to 1.0.0.2, added support of scaling
|
||||
* 1.01 YWX 19/09/02 Fixed bug in blit and up the version to 1.0.0.1
|
||||
* 1.00 SJL 17/06/02 Base
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
//#include <stdlib.h>
|
||||
|
||||
#include "duck_mem.h" /* interface to memory manager */
|
||||
#include "dxl_plugin.h" /* interface to dxv */
|
||||
|
||||
#include "pbdll.h"
|
||||
|
||||
|
||||
const char* VP5LIBVERSION="ON2 VP5 Decode Library for MAC Version 1.0.0.3";
|
||||
|
||||
typedef unsigned int FourCC;
|
||||
|
||||
#define VP50_FOURCC DXL_MKFOURCC( 'V', 'P', '5', '0')
|
||||
|
||||
|
||||
static dxvBitDepth bitDepths[] =
|
||||
{
|
||||
DXYV12,DXRGBNULL
|
||||
};
|
||||
|
||||
|
||||
void vp50_SetParameter(DXL_XIMAGE_HANDLE src,int Command, unsigned int Parameter );
|
||||
|
||||
extern void VP5_VPInitLibrary(void);
|
||||
extern void VP5_VPDeInitLibrary(void);
|
||||
|
||||
#include "duck_dxl.h"
|
||||
|
||||
typedef struct tFrameInfo
|
||||
{
|
||||
int KeyFrame;
|
||||
int Version;
|
||||
int Quality;
|
||||
int vp30Flag;
|
||||
} FrameInfo;
|
||||
|
||||
void
|
||||
vp50_GetInfo(unsigned char * source, FrameInfo * frameInfo)
|
||||
{
|
||||
|
||||
// Is the frame and inter frame or a key frame
|
||||
frameInfo->KeyFrame = !(source[0] > 0x7f);
|
||||
frameInfo->Quality = source[0] >> 2;
|
||||
if(frameInfo->KeyFrame)
|
||||
frameInfo->Version = ((source[2]>>3) & 0x1f );
|
||||
else
|
||||
frameInfo->Version = 0;
|
||||
|
||||
frameInfo->vp30Flag = (int)source[1];
|
||||
|
||||
}
|
||||
|
||||
|
||||
// YUV buffer configuration structure
|
||||
typedef struct
|
||||
{
|
||||
int YWidth;
|
||||
int YHeight;
|
||||
int YStride;
|
||||
|
||||
int UVWidth;
|
||||
int UVHeight;
|
||||
int UVStride;
|
||||
|
||||
char * YBuffer;
|
||||
char * UBuffer;
|
||||
char * VBuffer;
|
||||
|
||||
char * uvStart;
|
||||
int uvDstArea;
|
||||
int uvUsedArea;
|
||||
|
||||
} DXV_YUV_BUFFER_CONFIG;
|
||||
|
||||
/* define an algorithm base container */
|
||||
typedef struct tXImageCODEC
|
||||
{
|
||||
FourCC myFourCC;
|
||||
DXV_YUV_BUFFER_CONFIG FrameBuffer;
|
||||
PB_INSTANCE *myPBI;
|
||||
} vp50_XIMAGE, *vp50_XIMAGE_HANDLE;
|
||||
|
||||
|
||||
typedef void ((*VP5BLIT_FUNC)(unsigned char *, int, YUV_BUFFER_CONFIG *));
|
||||
//typedef void ((*vp5_VSCREEN_FUNC)(void));
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : vp50_decompress
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION :
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
****************************************************************************/
|
||||
static int
|
||||
vp50_decompress(DXL_XIMAGE_HANDLE src, DXL_VSCREEN_HANDLE vScreen)
|
||||
{
|
||||
|
||||
int retVal;
|
||||
vp50_XIMAGE_HANDLE thisAlgorithmBase = (vp50_XIMAGE_HANDLE)DXL_GetAlgorithmBasePtr(src);
|
||||
unsigned char *cAddr;
|
||||
int cSize;
|
||||
int w, h;
|
||||
|
||||
|
||||
// if we have a compressed frame decompress it ( otherwise we'll just redo
|
||||
// the scaling and postprocessing from the last frame )
|
||||
cAddr = DXL_GetXImageCDataAddr(src);
|
||||
cSize = DXL_GetXImageCSize(src);
|
||||
|
||||
if(cAddr)
|
||||
{
|
||||
if((cSize != 0) && (cAddr[0]>=1 || cAddr[1]>=1 || cAddr[2] >=1))
|
||||
{
|
||||
int w, h;
|
||||
|
||||
DXL_GetXImageXYWH(src, NULL, NULL, &w, &h);
|
||||
|
||||
// decode the frame
|
||||
retVal = VP5_DecodeFrameToYUV(thisAlgorithmBase->myPBI, (char *)cAddr, cSize, w, h);
|
||||
if(retVal != 0 )
|
||||
{
|
||||
if(retVal == -1)
|
||||
return DXL_VERSION_CONFLICT;
|
||||
else
|
||||
return DXL_BAD_DATA;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (vScreen) /* if there is a vScreen, blit to it */
|
||||
{
|
||||
unsigned char * ptrScrn;
|
||||
short thisPitch, vsHeight;
|
||||
dxvBlitQuality bq;
|
||||
dxvBitDepth bd;
|
||||
VP5BLIT_FUNC blitter;
|
||||
|
||||
DXL_GetVScreenAttributes(vScreen, (void **)&ptrScrn, &bq, &bd, &thisPitch, &vsHeight);
|
||||
|
||||
if(ptrScrn)
|
||||
{
|
||||
int x, y, pSize;
|
||||
int viewX, viewY;
|
||||
|
||||
DXL_GetVScreenView(vScreen, &viewX, &viewY, NULL, NULL);
|
||||
|
||||
/* get a frame pointer to the scaled and postprocessed reconstructed buffer */
|
||||
VP5_GetYUVConfig(thisAlgorithmBase->myPBI, (YUV_BUFFER_CONFIG *) &(thisAlgorithmBase->FrameBuffer));
|
||||
|
||||
pSize = VPX_GetSizeOfPixel(bd);
|
||||
|
||||
DXL_GetXImageXYWH(src, &x, &y, NULL, NULL);
|
||||
|
||||
/* remember to offset if requested */
|
||||
y += viewY;
|
||||
x += viewX;
|
||||
|
||||
ptrScrn += (x * pSize) + (y * thisPitch);
|
||||
|
||||
/* setup ptrs so we can work backwards through Paul's frame buffers */
|
||||
#if 1
|
||||
thisAlgorithmBase->FrameBuffer.YBuffer = thisAlgorithmBase->FrameBuffer.YBuffer +
|
||||
((thisAlgorithmBase->FrameBuffer.YHeight - 1) *
|
||||
(thisAlgorithmBase->FrameBuffer.YStride));
|
||||
|
||||
thisAlgorithmBase->FrameBuffer.UBuffer = thisAlgorithmBase->FrameBuffer.UBuffer +
|
||||
((thisAlgorithmBase->FrameBuffer.UVHeight - 1) *
|
||||
(thisAlgorithmBase->FrameBuffer.UVStride));
|
||||
|
||||
thisAlgorithmBase->FrameBuffer.VBuffer = thisAlgorithmBase->FrameBuffer.VBuffer +
|
||||
((thisAlgorithmBase->FrameBuffer.UVHeight - 1) *
|
||||
(thisAlgorithmBase->FrameBuffer.UVStride));
|
||||
#endif
|
||||
|
||||
if((bd != DXYUY2) && (bd != DXYV12))
|
||||
{
|
||||
if(bq == DXBLIT_STRETCH)
|
||||
{
|
||||
thisPitch *= 2;
|
||||
}
|
||||
}
|
||||
|
||||
if(bd == DXYV12 || bd == DXI420)
|
||||
{
|
||||
if(thisPitch < 0)
|
||||
{
|
||||
thisAlgorithmBase->FrameBuffer.uvStart = (char *) (ptrScrn + abs(thisPitch) + abs(thisPitch) * h/4 + thisPitch/2 );
|
||||
thisAlgorithmBase->FrameBuffer.uvDstArea = abs((thisPitch * h)/4);
|
||||
thisAlgorithmBase->FrameBuffer.uvUsedArea = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
thisAlgorithmBase->FrameBuffer.uvStart = (char *) (ptrScrn + (thisPitch * h));
|
||||
thisAlgorithmBase->FrameBuffer.uvDstArea = ((thisPitch * h)/4);
|
||||
thisAlgorithmBase->FrameBuffer.uvUsedArea = ((thisPitch * thisAlgorithmBase->FrameBuffer.UVHeight)/2);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
blitter = (VP5BLIT_FUNC)VPX_GetBlitter(bq, bd);
|
||||
|
||||
if ((void *)blitter != (void *)-1)
|
||||
{
|
||||
blitter(ptrScrn, thisPitch, (YUV_BUFFER_CONFIG *)(&thisAlgorithmBase->FrameBuffer));
|
||||
}
|
||||
else
|
||||
{
|
||||
return DXL_INVALID_BLIT;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
return DXL_OK;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : vp50_xImageDestroy
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : close down a decompressor, releasing the wilk decompressor,
|
||||
* the xImage (decompressor), and the intermediate vScreen (surface)
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
****************************************************************************/
|
||||
static int
|
||||
vp50_xImageDestroy(DXL_XIMAGE_HANDLE src)
|
||||
{
|
||||
vp50_XIMAGE_HANDLE thisAlgorithmBase = (vp50_XIMAGE_HANDLE)DXL_GetAlgorithmBasePtr(src);
|
||||
|
||||
if(thisAlgorithmBase)
|
||||
{
|
||||
VP5_StopDecoder(&(thisAlgorithmBase->myPBI));
|
||||
duck_free(thisAlgorithmBase);
|
||||
}
|
||||
|
||||
return DXL_OK;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : vp50_xImageReCreate
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION :
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
* called during initialization and/or when xImage (decompressor)
|
||||
* attributes change, note that nImage and src are actually
|
||||
* synonymous and should be cleared out a bit (to say the least!)
|
||||
*
|
||||
*
|
||||
* !!!!!!
|
||||
* This function should be prepared to get data that is NOT of the
|
||||
* type native to the decoder, It should do it's best to verify it
|
||||
* as valid data and should clean up after itself and return NULL
|
||||
* if it doesn't recognize the format of the data
|
||||
*
|
||||
****************************************************************************/
|
||||
static void *
|
||||
vp50_xImageReCreate(DXL_XIMAGE_HANDLE src, unsigned char *data, int type, enum BITDEPTH bitDepth, int w, int h)
|
||||
{
|
||||
vp50_XIMAGE_HANDLE thisAlgorithmBase = (vp50_XIMAGE_HANDLE)DXL_GetAlgorithmBasePtr(src);
|
||||
|
||||
(void) bitDepth;
|
||||
|
||||
if(type != VP50_FOURCC)
|
||||
return NULL;
|
||||
|
||||
/* if an algorithm base container already exists, destroy it */
|
||||
if(thisAlgorithmBase != NULL)
|
||||
{
|
||||
VP5_StopDecoder(&(thisAlgorithmBase->myPBI));
|
||||
duck_free(thisAlgorithmBase);
|
||||
}
|
||||
|
||||
/* create a new algorithm base container */
|
||||
thisAlgorithmBase = (vp50_XIMAGE_HANDLE)duck_calloc(1,sizeof(vp50_XIMAGE),DMEM_GENERAL);
|
||||
if(thisAlgorithmBase == NULL)
|
||||
return NULL;
|
||||
|
||||
|
||||
DXL_RegisterXImageRecreate(src, (RECREATE_FUNC) vp50_xImageReCreate);
|
||||
|
||||
DXL_RegisterXImageDestroy(src, (DESTROY_FUNC) vp50_xImageDestroy);
|
||||
|
||||
DXL_RegisterXImageDx(src, (DX_FUNC) vp50_decompress);
|
||||
|
||||
DXL_RegisterXImageSetParameter(src, (SET_PARAMETER_FUNC) vp50_SetParameter);
|
||||
|
||||
thisAlgorithmBase->myFourCC = VP50_FOURCC;
|
||||
|
||||
/* create new PBI */
|
||||
if(!VP5_StartDecoder( &(thisAlgorithmBase->myPBI), w, h))
|
||||
{
|
||||
duck_free(thisAlgorithmBase);
|
||||
thisAlgorithmBase = NULL;
|
||||
}
|
||||
|
||||
return (DXL_HANDLE) thisAlgorithmBase;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : vp50_xImageCreate
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION :
|
||||
*
|
||||
* SPECIAL NOTES : in this "glue" case, just calls through to the create function.
|
||||
*
|
||||
****************************************************************************/
|
||||
static DXL_HANDLE
|
||||
vp50_xImageCreate(DXL_XIMAGE_HANDLE src, unsigned char *data)
|
||||
{
|
||||
/* our default wxh is always 320x240 */
|
||||
return vp50_xImageReCreate(src, data, VP50_FOURCC, (enum BITDEPTH ) 0, 320, 240);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : vp50_Init
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION :
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
int
|
||||
vp50_Init(void)
|
||||
{
|
||||
DXL_RegisterXImage((CREATE_FUNC) vp50_xImageCreate, VP50_FOURCC);
|
||||
|
||||
|
||||
vp3SetBlit();
|
||||
|
||||
/* initialize all the global variables */
|
||||
VP5_VPInitLibrary();
|
||||
|
||||
return DXL_OK;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : vp50_Exit
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : main exit routine, called during DXL_ExitVideo()
|
||||
* clean up any global information if necessary
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
int
|
||||
vp50_Exit(void)
|
||||
{
|
||||
VP5_VPDeInitLibrary();
|
||||
|
||||
return DXL_OK;
|
||||
}
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE :
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION :
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void
|
||||
vp50_SetParameter(DXL_XIMAGE_HANDLE src, int Command, unsigned int Parameter)
|
||||
{
|
||||
vp50_XIMAGE_HANDLE thisAlgorithmBase = (vp50_XIMAGE_HANDLE)DXL_GetAlgorithmBasePtr(src);
|
||||
|
||||
VP5_SetPbParam(thisAlgorithmBase->myPBI, (PB_COMMAND_TYPE) Command, (UINT32) Parameter );
|
||||
}
|
||||
@@ -0,0 +1,389 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : PB_Globals.c
|
||||
*
|
||||
* Description : Video CODEC Demo: playback dll global declarations
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.21 JBB 13 Jun 01 VP4 Code Clean Out
|
||||
* 1.20 AWG 08-Jun-01 Added support for DCT16
|
||||
* 1.19 JBB 01-MAY-01 VP5 Functionality (set up coefftoband array)
|
||||
* 1.18 YWX 26-Apr 01 Added global "CPUFrequency" and its initializing
|
||||
* in VPInitlibrary()
|
||||
* 1.17 JBB 06 Apr 01 new cpu free variable initialized
|
||||
* 1.16 SJL 30 Mar 01 Added #if defined(POSTPROCESS) around InitPostProcessing();
|
||||
* 1.15 PGW 25 Jan 01 Add code to create and destroy MV huffman trees.
|
||||
* 1.15 JBB 26 Jan 01 No need to destroy huffman trees
|
||||
* 1.14 JBB 22 Aug 00 Ansi C conversion
|
||||
* 1.13 JBB 21 Aug 00 New More Blurry in high variance area deringer
|
||||
* 1.12 YWX 2 Aug 00 Removed redundant kernel modifiers
|
||||
* 1.11 JBB 27 Jul 00 Moved kernel modifiers to pbi mallocs -> duck_malloc
|
||||
* for scott added malloc checks
|
||||
* 1.10 YWX 15/05/00 change the initialization of PostProcessLevel
|
||||
* 1.09 JBB 27/01/99 Globals Removed, use of PB_INSTANCE, added PB_Instance
|
||||
* allocation and deletion funcitons
|
||||
* 1.08 PGW 17/12/99 Draw dib functionality removed.
|
||||
* 1.07 PGW 16/12/99 Added support for VP3 version id.
|
||||
* 1.06 PGW 15/12/99 Added key frame type variable
|
||||
* 1.05 PGW 22/11/99 Changes relating to restructuring of block map stuff.
|
||||
* 1.04 PGW 14/10/99 Changes to reduce uneccessary dependancies.
|
||||
* 1.05 PGW 06/09/99 DivBySix changed to UINT8 [].
|
||||
* 1.04 PGW 24/08/99 Removed of EOF token and assosciated data sturctures etc.
|
||||
* Deleted COrderList[].
|
||||
* 1.03 PGW 15/07/99 Added bit extraction variables.
|
||||
* 1.02 PGW 14/07/99 Changes to interface to idct and reconstruction functions.
|
||||
* Added ModeUsesMC[] truth table. Added (*ReconIntra) funtion
|
||||
* pointer.
|
||||
* 1.01 PGW 09/07/99 Added code to support profile timing
|
||||
* 1.00 PGW 22/06/99 Configuration baseline
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#include "pbdll.h"
|
||||
#include "duck_mem.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Explicit imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
extern unsigned long VP5_GetProcessorFrequency();
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
//extern Q_LIST_ENTRY VP5_DcScaleFactorTableV1[ Q_TABLE_SIZE ] ;
|
||||
extern Q_LIST_ENTRY VP5_DcQuant[ Q_TABLE_SIZE ];
|
||||
|
||||
UINT32 DCQuantScaleP[Q_TABLE_SIZE];
|
||||
|
||||
//****************************************************************
|
||||
// Function Pointers now library globals!
|
||||
//****************************************************************
|
||||
|
||||
// Process Frequency
|
||||
unsigned int CPUFrequency;
|
||||
|
||||
// Truth table to indicate if the given mode uses motion estimation
|
||||
BOOL VP5_ModeUsesMC[MAX_MODES] = { FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE };
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DeleteTmpBuffers
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_DeleteTmpBuffers(PB_INSTANCE * pbi)
|
||||
{
|
||||
|
||||
if(pbi->ReconDataBufferAlloc)
|
||||
duck_free(pbi->ReconDataBufferAlloc);
|
||||
if(pbi->LoopFilteredBlockAlloc)
|
||||
duck_free(pbi->LoopFilteredBlockAlloc);
|
||||
if(pbi->TmpDataBufferAlloc)
|
||||
duck_free(pbi->TmpDataBufferAlloc);
|
||||
if(pbi->TmpReconBufferAlloc)
|
||||
duck_free(pbi->TmpReconBufferAlloc);
|
||||
if(pbi->ScaleBufferAlloc)
|
||||
duck_free(pbi->ScaleBufferAlloc);
|
||||
|
||||
pbi->ReconDataBufferAlloc=0;
|
||||
pbi->TmpDataBufferAlloc = 0;
|
||||
pbi->TmpReconBufferAlloc = 0;
|
||||
pbi->ScaleBufferAlloc = 0;
|
||||
pbi->ScaleBuffer = 0;
|
||||
pbi->ReconDataBuffer=0;
|
||||
pbi->TmpDataBuffer = 0;
|
||||
pbi->TmpReconBuffer = 0;
|
||||
|
||||
pbi->LoopFilteredBlockAlloc = 0;
|
||||
pbi->LoopFilteredBlock = 0;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : AllocateTmpBuffers
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
#define ROUNDUP32(X) ( ( ( (unsigned long) X ) + 31 )&( 0xFFFFFFE0 ) )
|
||||
BOOL VP5_AllocateTmpBuffers(PB_INSTANCE * pbi)
|
||||
{
|
||||
|
||||
// clear any existing info
|
||||
VP5_DeleteTmpBuffers(pbi);
|
||||
#ifdef MAPCA
|
||||
pbi->ReconDataBufferAlloc = (INT16 (*)[64])duck_malloc(32+64*sizeof(INT16)*6, DMEM_GENERAL);
|
||||
if(!pbi->ReconDataBufferAlloc) { VP5_DeleteTmpBuffers(pbi); return FALSE;};
|
||||
pbi->ReconDataBuffer = (INT16 (*)[64])ROUNDUP32(pbi->ReconDataBufferAlloc);
|
||||
#else
|
||||
// Adjust the position of all of our temporary
|
||||
pbi->ReconDataBufferAlloc = (INT16 *)duck_malloc(32+64*sizeof(INT16), DMEM_GENERAL);
|
||||
if(!pbi->ReconDataBufferAlloc) { VP5_DeleteTmpBuffers(pbi); return FALSE;};
|
||||
pbi->ReconDataBuffer = (INT16 *)ROUNDUP32(pbi->ReconDataBufferAlloc);
|
||||
#endif
|
||||
|
||||
pbi->TmpDataBufferAlloc = (INT16 *)duck_malloc(32 + 64 * sizeof(INT16), DMEM_GENERAL);
|
||||
if(!pbi->TmpDataBufferAlloc) { VP5_DeleteTmpBuffers(pbi); return FALSE;};
|
||||
pbi->TmpDataBuffer = (INT16 *)ROUNDUP32(pbi->TmpDataBufferAlloc);
|
||||
|
||||
pbi->LoopFilteredBlockAlloc = (UINT8 *)duck_malloc(32 + 256 * sizeof(UINT8), DMEM_GENERAL);
|
||||
if(!pbi->LoopFilteredBlockAlloc) { VP5_DeleteTmpBuffers(pbi); return FALSE;};
|
||||
pbi->LoopFilteredBlock = (UINT8 *)ROUNDUP32(pbi->LoopFilteredBlockAlloc);
|
||||
|
||||
pbi->TmpReconBufferAlloc = (INT16 *)duck_malloc(32 + 64 * sizeof(INT16), DMEM_GENERAL);
|
||||
if(!pbi->TmpReconBufferAlloc) { VP5_DeleteTmpBuffers(pbi); return FALSE;};
|
||||
pbi->TmpReconBuffer = (INT16 *)ROUNDUP32(pbi->TmpReconBufferAlloc);
|
||||
|
||||
|
||||
return TRUE;
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DeletePBInstance
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be deleted
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : frees the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_DeletePBInstance(PB_INSTANCE **pbi)
|
||||
{
|
||||
// clear any existing info
|
||||
if(*pbi)
|
||||
{
|
||||
// Delete the motion vector huffman trees.
|
||||
//DestroyMvTrees(*pbi);
|
||||
|
||||
// Delete any other dynamically allocaed temporary buffers
|
||||
VP5_DeleteTmpBuffers(*pbi);
|
||||
VP5_DeleteQuantizer(&(*pbi)->quantizer);
|
||||
#ifndef MAPCA
|
||||
DeletePostProcInstance(&(*pbi)->postproc);
|
||||
#endif
|
||||
}
|
||||
|
||||
duck_free(*pbi);
|
||||
*pbi=0;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : CreatePBInstance
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
PB_INSTANCE * VP5_CreatePBInstance(void)
|
||||
{
|
||||
PB_INSTANCE *pbi=0;
|
||||
CONFIG_TYPE ConfigurationInit =
|
||||
{
|
||||
0,0,0,0,
|
||||
8,8,
|
||||
};
|
||||
|
||||
|
||||
int pbi_size = sizeof(PB_INSTANCE);
|
||||
pbi=(PB_INSTANCE *) duck_malloc(pbi_size, DMEM_GENERAL);
|
||||
if(!pbi)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
// initialize whole structure to 0
|
||||
memset((unsigned char *) pbi, 0, sizeof(PB_INSTANCE));
|
||||
|
||||
memcpy((void *) &pbi->Configuration, (void *) &ConfigurationInit, sizeof(CONFIG_TYPE));
|
||||
|
||||
if(!VP5_AllocateTmpBuffers(pbi))
|
||||
{
|
||||
duck_free(pbi);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
pbi->KeyFrameType = DCT_KEY_FRAME;
|
||||
pbi->CPUFree = 70;
|
||||
#ifndef MAPCA
|
||||
pbi->idct = idct;
|
||||
#endif
|
||||
|
||||
// Initialise Entropy related data structures.
|
||||
memset( pbi->DcProbs, 0, sizeof(pbi->DcProbs) );
|
||||
memset( pbi->AcProbs, 0, sizeof(pbi->AcProbs) );
|
||||
|
||||
|
||||
return pbi;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VPInitLibrary
|
||||
*
|
||||
*
|
||||
* INPUTS : init VP library
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Fully initializes the playback library
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_VPInitLibrary(void)
|
||||
{
|
||||
int i;
|
||||
#if !defined(__POWERPC__)
|
||||
CPUFrequency = VP5_GetProcessorFrequency();
|
||||
#endif
|
||||
|
||||
|
||||
VP5_DMachineSpecificConfig();
|
||||
|
||||
for( i = 0 ; i < Q_TABLE_SIZE; i++)
|
||||
{
|
||||
INT32 dcScale;
|
||||
|
||||
// if(i<4)
|
||||
// dcScale = ((6-i) * VP5_DcQuant[i]/4);
|
||||
// else
|
||||
dcScale = VP5_DcQuant[i]/2;
|
||||
|
||||
DCQuantScaleP[i] = dcScale;
|
||||
|
||||
}
|
||||
|
||||
#ifndef MAPCA
|
||||
InitPostProcessing(
|
||||
DCQuantScaleP,
|
||||
DCQuantScaleP,
|
||||
DCQuantScaleP,
|
||||
CURRENT_DECODE_VERSION);
|
||||
InitVPUtil();
|
||||
#else
|
||||
VP5_InitPostProcess();
|
||||
#endif
|
||||
}
|
||||
|
||||
/*********************************************************/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VPDeinitLibrary
|
||||
*
|
||||
*
|
||||
* INPUTS : init VP library
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Fully initializes the playback library
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_VPDeInitLibrary(void)
|
||||
{
|
||||
#ifdef MAPCA
|
||||
VP5_ClosePostProcess();
|
||||
#endif
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,845 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : Quantise
|
||||
*
|
||||
* Description : Quantisation and dequanitsation of an 8x8 dct block. .
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
*
|
||||
* 1.18 PGW 03 Dec 01 Changes to available Q values.
|
||||
* 1.17 PGW 14 Sep 01 Added support for ZB varying on zero-run.
|
||||
* 1.16 JBX 22-Mar-01 Merged with vp4-mapca bitstream
|
||||
* 1.15 PGW 19 Oct 00 Added select_InterUV_quantiser and related data structures
|
||||
* to support use of different DC behaviour for UV.
|
||||
* 1.11 PGW 18 Sep 00 QThreshTable[] and Inter_coeffs[] made instacne specific.
|
||||
* 1.10 PGW 14 Sep 00 Added support for different Q, ZB and Rounding tables
|
||||
* in different encoder versions.
|
||||
* 1.09 PGW 04 Sep 00 Fixed bugs in code to set up rounding and zero bins
|
||||
* Added support for ZB to change with Q and coefficient.
|
||||
* 1.08 PGW 29 Aug 00 Correction to UpdateQ() and UpdateQC() re. Q limits.
|
||||
* Changes to rounding and ZBF.
|
||||
* 1.08 JBB 22 Aug 00 Ansi C conversion
|
||||
* 1.07 SJL 14/04/00 Added the BuildQuantIndex function.
|
||||
* 1.06 PGW 18/02/00 Rate targeting changes.
|
||||
* 1.05 JBB 27/01/99 Globals Removed, use of QUANTIZER, Dequant no longer
|
||||
* used
|
||||
* 1.04 PGW 05/11/99 Changes to support AC range entropy tables
|
||||
* 1.03 PGW 12/10/99 Removal of spurious windows dependancies.
|
||||
* 1.02 PGW 14/09/99 Removal of some floating point code.
|
||||
* 1.01 PGW 13/07/99 Changes to keep dequant output to 16 bit
|
||||
* 1.01 PGW 07/07/99 Tweaks to baseline matrix.
|
||||
* 1.00 PGW 18/06/99 Configuration baseline
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Frames
|
||||
*****************************************************************************
|
||||
*/
|
||||
#define STRICT /* Strict type checking. */
|
||||
#include <string.h>
|
||||
#include "quantize.h"
|
||||
#include "duck_mem.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
#define MIN16 ((1<<16)-1)
|
||||
|
||||
// DC quantizer characteristics
|
||||
#define VP5_MIN_QUANT 1
|
||||
|
||||
#define UV_Q_ADJUSTMENT 0
|
||||
|
||||
// Scale factors used to improve precision of DCT/IDCT
|
||||
#define IDCT_SCALE_FACTOR 2 // Shift left bits to improve IDCT precision
|
||||
|
||||
/****************************************************************************
|
||||
* Imported Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Imported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
void (*VP5_BuildQuantIndex)( QUANTIZER * pbi);
|
||||
|
||||
UINT8 QTableSelect[6] = { 0,0,0,0,1,1 }; // Controls selection of Q Table,rounding,zero bin etc for Y, U & V blocks
|
||||
|
||||
/****************************************************************************
|
||||
* Foreward References
|
||||
*****************************************************************************
|
||||
*/
|
||||
void VP5_InitQTables( QUANTIZER *pbi, UINT8 Vp3VersionNo );
|
||||
void VP5_BuildQuantIndex_Generic(QUANTIZER *pbi);
|
||||
void VP5_UpdateQ( QUANTIZER *pbi, UINT8 Vp3VersionNo );
|
||||
void VP5_UpdateQC( QUANTIZER *pbi,UINT8 Vp3VersionNo );
|
||||
void VP5_init_quantizer ( QUANTIZER *pbi, UINT8 Vp3VersionNo );
|
||||
void (*VP5_quantize)( QUANTIZER *pbi, INT16 * DCT_block, Q_LIST_ENTRY * quantized_list, UINT8 bp );
|
||||
void VP5_init_dequantizer ( QUANTIZER *pbi, UINT8 Vp3VersionNo );
|
||||
QUANTIZER * VP5_CreateQuantizer(void);
|
||||
void VP5_DeleteQuantizer(QUANTIZER **pbi);
|
||||
|
||||
/****************************************************************************
|
||||
* Module Statics
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
// AC Quantizer Tables
|
||||
static UINT32 VP5_QThreshTable[Q_TABLE_SIZE] =
|
||||
{ 94, 92, 90, 88, 86, 82, 78, 74,
|
||||
70, 66, 62, 58, 54, 53, 52, 51,
|
||||
50, 49, 48, 47, 46, 45, 44, 43,
|
||||
42, 40, 39, 37, 36, 35, 34, 33,
|
||||
32, 31, 30, 29, 28, 27, 26, 25,
|
||||
24, 23, 22, 21, 20, 19, 18, 17,
|
||||
16, 15, 14, 13, 12, 11, 10, 9,
|
||||
8, 7, 6, 5, 4, 3, 2, 1
|
||||
};
|
||||
static UINT32 VP5_UvQThreshTable[Q_TABLE_SIZE] =
|
||||
{ 94, 92, 90, 88, 86, 82, 78, 74,
|
||||
70, 66, 62, 58, 54, 53, 52, 51,
|
||||
50, 49, 48, 47, 46, 45, 44, 43,
|
||||
42, 40, 39, 37, 36, 35, 34, 33,
|
||||
32, 31, 30, 29, 28, 27, 26, 25,
|
||||
24, 23, 22, 21, 20, 19, 18, 17,
|
||||
16, 15, 14, 13, 12, 11, 10, 9,
|
||||
8, 7, 6, 5, 4, 3, 2, 1
|
||||
};
|
||||
|
||||
// AC Zero Bin and Rounding Tables (include fdct normalisation)
|
||||
UINT32 VP5_ZBinTable[Q_TABLE_SIZE] =
|
||||
{
|
||||
330,314,298,284,264,246,228,213,
|
||||
201,190,178,167,156,153,149,146,
|
||||
144,141,138,135,132,130,127,124,
|
||||
121,115,110,104,99, 96, 94, 90,
|
||||
85, 82, 79, 76, 74, 71, 69, 66,
|
||||
63, 61, 58, 55, 53, 50, 47, 45,
|
||||
43, 40, 38, 36, 33, 31, 28, 24,
|
||||
21, 18, 16, 13, 10, 7, 4, 2,
|
||||
};
|
||||
UINT32 VP5_UvZBinTable[Q_TABLE_SIZE] =
|
||||
{
|
||||
330,314,298,284,264,246,228,213,
|
||||
201,190,178,167,156,153,149,146,
|
||||
144,141,138,135,132,130,127,124,
|
||||
121,115,110,104,99, 96, 94, 90,
|
||||
85, 82, 79, 76, 74, 71, 69, 66,
|
||||
63, 61, 58, 55, 53, 50, 47, 45,
|
||||
43, 40, 38, 36, 33, 31, 28, 24,
|
||||
21, 18, 16, 13, 10, 7, 4, 2,
|
||||
};
|
||||
UINT32 VP5_RTable[Q_TABLE_SIZE] =
|
||||
{
|
||||
48, 56, 64, 70, 78, 82, 86, 88,
|
||||
91, 92, 94, 94, 99,103,102,100,
|
||||
99, 97, 95, 93, 91, 89, 87, 85,
|
||||
83, 79, 77, 73, 71, 69, 67, 65,
|
||||
64, 62, 60, 58, 56, 54, 52, 50,
|
||||
48, 46, 44, 42, 40, 38, 36, 34,
|
||||
32, 30, 28, 26, 24, 22, 20, 18,
|
||||
16, 14, 12, 10, 8, 6, 4, 2,
|
||||
};
|
||||
UINT32 VP5_UvRTable[Q_TABLE_SIZE] =
|
||||
{
|
||||
48, 56, 64, 70, 78, 82, 86, 88,
|
||||
91, 92, 94, 94, 99,103,102,100,
|
||||
99, 97, 95, 93, 91, 89, 87, 85,
|
||||
83, 79, 77, 73, 71, 69, 67, 65,
|
||||
64, 62, 60, 58, 56, 54, 52, 50,
|
||||
48, 46, 44, 42, 40, 38, 36, 34,
|
||||
32, 30, 28, 26, 24, 22, 20, 18,
|
||||
16, 14, 12, 10, 8, 6, 4, 2,
|
||||
};
|
||||
|
||||
// DC Quantizer tables
|
||||
Q_LIST_ENTRY VP5_DcQuant[ Q_TABLE_SIZE ] =
|
||||
{
|
||||
47, 47, 47, 47, 45, 43, 43, 43,
|
||||
43, 43, 42, 41, 41, 40, 40, 40,
|
||||
40, 35, 35, 35, 35, 33, 33, 33,
|
||||
33, 32, 32, 32, 27, 27, 26, 26,
|
||||
25, 25, 24, 24, 23, 23, 19, 19,
|
||||
19, 19, 18, 18, 17, 16, 16, 16,
|
||||
16, 16, 15, 11, 11, 11, 10, 10,
|
||||
9, 8, 7, 5, 3, 3, 2, 2,
|
||||
};
|
||||
Q_LIST_ENTRY VP5_UvDcQuant[ Q_TABLE_SIZE ] =
|
||||
{
|
||||
47, 47, 47, 47, 45, 43, 43, 43,
|
||||
43, 43, 42, 41, 41, 40, 40, 40,
|
||||
40, 35, 35, 35, 35, 33, 33, 33,
|
||||
33, 32, 32, 32, 27, 27, 26, 26,
|
||||
25, 25, 24, 24, 23, 23, 19, 19,
|
||||
19, 19, 18, 18, 17, 16, 16, 16,
|
||||
16, 16, 15, 11, 11, 11, 10, 10,
|
||||
9, 8, 7, 5, 3, 3, 2, 2,
|
||||
};
|
||||
// DC Zero Bin and Rounding Tables (include fdct normalisation)
|
||||
UINT32 VP5_DcZBinTable[Q_TABLE_SIZE] =
|
||||
{
|
||||
170,162,152,150,140,130,125,121,
|
||||
121,118,113,111,110,108,108,106,
|
||||
105,96, 93, 87, 86, 83, 83, 83,
|
||||
83, 78, 78, 78, 66, 66, 63, 63,
|
||||
61, 61, 58, 58, 56, 56, 46, 46,
|
||||
46, 46, 43, 43, 41, 38, 38, 38,
|
||||
38, 38, 35, 24, 24, 24, 23, 23,
|
||||
20, 19, 16, 13, 6, 6, 4, 4,
|
||||
};
|
||||
UINT32 VP5_UvDcZBinTable[Q_TABLE_SIZE] =
|
||||
{
|
||||
170,162,152,150,140,130,125,121,
|
||||
121,118,113,111,110,108,108,106,
|
||||
105,96, 93, 87, 86, 83, 83, 83,
|
||||
83, 78, 78, 78, 66, 66, 63, 63,
|
||||
61, 61, 58, 58, 56, 56, 46, 46,
|
||||
46, 46, 43, 43, 41, 38, 38, 38,
|
||||
38, 38, 35, 24, 24, 24, 23, 23,
|
||||
20, 19, 16, 13, 6, 6, 4, 4,
|
||||
};
|
||||
|
||||
UINT32 VP5_DcRTable[Q_TABLE_SIZE] =
|
||||
{
|
||||
20, 28, 38, 40, 44, 46, 50, 50,
|
||||
51, 57, 59, 61, 62, 64, 66, 67,
|
||||
67, 62, 63, 64, 64, 62, 62, 62,
|
||||
62, 62, 62, 62, 54, 54, 52, 52,
|
||||
50, 50, 48, 48, 46, 46, 38, 38,
|
||||
38, 38, 36, 36, 34, 32, 32, 32,
|
||||
32, 32, 30, 22, 22, 22, 20, 20,
|
||||
18, 16, 14, 10, 6, 6, 4, 4,
|
||||
};
|
||||
UINT32 VP5_UvDcRTable[Q_TABLE_SIZE] =
|
||||
{
|
||||
20, 30, 38, 40, 44, 46, 50, 50,
|
||||
51, 57, 59, 61, 62, 64, 66, 67,
|
||||
67, 62, 63, 64, 64, 62, 62, 62,
|
||||
62, 62, 62, 62, 54, 54, 52, 52,
|
||||
50, 50, 48, 48, 46, 46, 38, 38,
|
||||
38, 38, 36, 36, 34, 32, 32, 32,
|
||||
32, 32, 30, 22, 22, 22, 20, 20,
|
||||
18, 16, 14, 10, 6, 6, 4, 4,
|
||||
};
|
||||
|
||||
/* Inverse fast DCT index */
|
||||
/* This contains the offsets needed to convert zigzag order into */
|
||||
/* x, y order for decoding. It is generated from the input zigzag */
|
||||
/* indexat run time. */
|
||||
|
||||
/* For maximum speed during both quantisation and dequantisation */
|
||||
/* we maintain separate quantisation and zigzag tables for each */
|
||||
/* operation. */
|
||||
|
||||
/* pbi->quant_index: the zigzag index used during quantisation */
|
||||
/* dequant_index: zigzag index used during dequantisation */
|
||||
/* the pbi->quant_index is the inverse of dequant_index */
|
||||
/* and is calculated during initialisation */
|
||||
|
||||
static UINT32 dequant_index[64] =
|
||||
{ 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
|
||||
};
|
||||
|
||||
static UINT32 transIndexC[64] =
|
||||
{
|
||||
0, 1, 2, 3, 4, 5, 6, 7,
|
||||
8, 9, 10, 11, 12, 13, 14, 15,
|
||||
16, 17, 18, 19, 20, 21, 22, 23,
|
||||
24, 25, 26, 27, 28, 29, 30, 31,
|
||||
|
||||
32, 33, 34, 35, 36, 37, 38, 39,
|
||||
40, 41, 42, 43, 44, 45, 46, 47,
|
||||
48, 49, 50, 51, 52, 53, 54, 55,
|
||||
56, 57, 58, 59, 60, 61, 62, 63
|
||||
};
|
||||
|
||||
static UINT32 quant_indexC[64] =
|
||||
{
|
||||
0, 1, 5, 6, 14, 15, 27, 28,
|
||||
2, 4, 7, 13, 16, 26, 29, 42,
|
||||
3, 8, 12, 17, 25, 30, 41, 43,
|
||||
9, 11, 18, 24, 31, 40, 44, 53,
|
||||
10, 19, 23, 32, 39, 45, 52, 54,
|
||||
20, 22, 33, 38, 46, 51, 55, 60,
|
||||
21, 34, 37, 47, 50, 56, 59, 61,
|
||||
35, 36, 48, 49, 57, 58, 62, 63
|
||||
};
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : InitQTables
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Initialises Q tables based upon version number
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_InitQTables( QUANTIZER *pbi, UINT8 Vp3VersionNo )
|
||||
{
|
||||
// Make version specific assignments.
|
||||
memcpy ( pbi->QThreshTable, VP5_QThreshTable, sizeof( pbi->QThreshTable ) );
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : BuildQuantIndex_Generic
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Builds the quant_index table.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_BuildQuantIndex_Generic(QUANTIZER *pbi)
|
||||
{
|
||||
INT32 i,j;
|
||||
|
||||
pbi->transIndex = transIndexC;
|
||||
|
||||
// invert the dequant index into the quant index
|
||||
for ( i = 0; i < BLOCK_SIZE; i++ )
|
||||
{
|
||||
j = dequant_index[i];
|
||||
pbi->quant_index[j] = i;
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : UpdateQ
|
||||
*
|
||||
* INPUTS : UINT32 NewQ
|
||||
* (A New Q value (50 - 1000))
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Updates the quantisation tables for a new Q
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_UpdateQ( QUANTIZER *pbi, UINT8 Vp3VersionNo )
|
||||
{
|
||||
if ( pbi->QThreshTable[pbi->FrameQIndex] == pbi->LastQuantizerValue )
|
||||
return;
|
||||
|
||||
// Update the record of last Q and last Q index.
|
||||
pbi->LastQuantizerValue = pbi->ThisFrameQuantizerValue;
|
||||
|
||||
// invert the dequant index into the quant index
|
||||
// the dxer has a different order than the cxer.
|
||||
VP5_BuildQuantIndex(pbi);
|
||||
|
||||
// Re-initialise the q tables for forward and reverse transforms.
|
||||
VP5_init_dequantizer ( pbi, Vp3VersionNo );
|
||||
}
|
||||
|
||||
/********************* COMPRESSOR SPECIFIC **********************************/
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : UpdateQC (compressor's update q)
|
||||
*
|
||||
* INPUTS : UINT32 NewQ
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Updates the quantisation tables for a new Q
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_UpdateQC( QUANTIZER *pbi, UINT8 Vp3VersionNo )
|
||||
{
|
||||
if ( pbi->QThreshTable[pbi->FrameQIndex] == pbi->LastQuantizerValue )
|
||||
return;
|
||||
|
||||
// Update the record of last Q.
|
||||
pbi->LastQuantizerValue = pbi->ThisFrameQuantizerValue;
|
||||
|
||||
// invert the dequant index into the quant index
|
||||
// the dxer has a different order than the cxer.
|
||||
VP5_BuildQuantIndex_Generic(pbi);
|
||||
|
||||
// Re-initialise the q tables for forward and reverse transforms.
|
||||
VP5_init_quantizer ( pbi, Vp3VersionNo );
|
||||
VP5_init_dequantizer ( pbi, Vp3VersionNo );
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* Routine: init_quantizer
|
||||
*
|
||||
* Purpose: Used to initialize the encoding/decoding data structures
|
||||
* and to select DCT algorithm
|
||||
*
|
||||
* Parameters :
|
||||
* Input :
|
||||
* UINT32 scale_factor
|
||||
* Defines the factor by which to scale QUANT_ARRAY to
|
||||
* produce quantization_array
|
||||
*
|
||||
* UINT8 QIndex ::
|
||||
* Index into Q table for current quantiser value.
|
||||
* Return value :
|
||||
* None.
|
||||
*
|
||||
****************************************************************************
|
||||
*/
|
||||
#define SHIFT16 (1<<16)
|
||||
void VP5_init_quantizer ( QUANTIZER *pbi, UINT8 Vp3VersionNo )
|
||||
{
|
||||
int i; // Loop counters
|
||||
|
||||
double temp_fp_quant_coeffs;
|
||||
|
||||
|
||||
// Notes on setup of quantisers.
|
||||
// The "* 4" is a normalisation factor for the forward DCT transform.
|
||||
|
||||
// ******************* Y *********************
|
||||
|
||||
// Calculate DC quant values (Include a *4 for FDCT normalization)
|
||||
temp_fp_quant_coeffs = ( VP5_DcQuant[pbi->FrameQIndex] * 4 );
|
||||
|
||||
// 1/X (Y)
|
||||
temp_fp_quant_coeffs = 1.0 / temp_fp_quant_coeffs;
|
||||
pbi->QuantCoeffs[0][0] = (INT32) (0.5 + SHIFT16 * temp_fp_quant_coeffs);
|
||||
|
||||
// DC rounding (Y)
|
||||
pbi->QuantRound[0][0] = VP5_DcRTable[pbi->FrameQIndex];
|
||||
|
||||
// Set DC zero Bin (Y)
|
||||
pbi->ZeroBinSize[0][0] = VP5_DcZBinTable[pbi->FrameQIndex];
|
||||
|
||||
|
||||
// AC for Y
|
||||
for ( i = 1; i < 64; i++ )
|
||||
{
|
||||
// Normalize the quantizer (* 4 for fdct normalisation)
|
||||
temp_fp_quant_coeffs = (double)(VP5_QThreshTable[pbi->FrameQIndex] * 4);
|
||||
|
||||
// Convert to 1/x
|
||||
temp_fp_quant_coeffs = 1.0 / temp_fp_quant_coeffs;
|
||||
pbi->QuantCoeffs[0][i] = (INT32) (0.5 + SHIFT16 * temp_fp_quant_coeffs);
|
||||
|
||||
// AC rounding
|
||||
pbi->QuantRound[0][i] = VP5_RTable[pbi->FrameQIndex];
|
||||
|
||||
// Zero Bins
|
||||
pbi->ZeroBinSize[0][i] = VP5_ZBinTable[pbi->FrameQIndex];
|
||||
}
|
||||
|
||||
|
||||
// ******************* UV *********************
|
||||
// Calculate DC quant values (Include a *4 for FDCT normalization)
|
||||
temp_fp_quant_coeffs = ( VP5_UvDcQuant[pbi->FrameQIndex] * 4 );
|
||||
|
||||
// 1/X (UV)
|
||||
temp_fp_quant_coeffs = 1.0 / temp_fp_quant_coeffs;
|
||||
pbi->QuantCoeffs[1][0] = (INT32) (0.5 + SHIFT16 * temp_fp_quant_coeffs);
|
||||
|
||||
// DC rounding (UV)
|
||||
pbi->QuantRound[1][0] = VP5_UvDcRTable[pbi->FrameQIndex];
|
||||
|
||||
// Set DC zero Bin (UV)
|
||||
pbi->ZeroBinSize[1][0] = VP5_UvDcZBinTable[pbi->FrameQIndex];
|
||||
|
||||
|
||||
// AC for UV
|
||||
for ( i = 1; i < 64; i++ )
|
||||
{
|
||||
// Normalize the quantizer (* 4 for fdct normalisation)
|
||||
temp_fp_quant_coeffs = (double)(VP5_UvQThreshTable[pbi->FrameQIndex] * 4);
|
||||
|
||||
// 1/x
|
||||
temp_fp_quant_coeffs = 1.0 / temp_fp_quant_coeffs;
|
||||
pbi->QuantCoeffs[1][i] = (INT32) (0.5 + SHIFT16 * temp_fp_quant_coeffs);
|
||||
|
||||
// AC rounding
|
||||
pbi->QuantRound[1][i] = VP5_UvRTable[pbi->FrameQIndex];
|
||||
|
||||
// Zero Bins
|
||||
pbi->ZeroBinSize[1][i] = VP5_UvZBinTable[pbi->FrameQIndex];
|
||||
}
|
||||
for(i=0;i<8;i++)
|
||||
{
|
||||
pbi->round[i] = pbi->QuantRound[0][1];
|
||||
pbi->mult[i] = pbi->QuantCoeffs[0][1];
|
||||
pbi->zbin[i] = pbi->ZeroBinSize[0][1]-1;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************
|
||||
*
|
||||
* Routine: quantize
|
||||
*
|
||||
* Purpose: Quantizes a block of pixels by dividing
|
||||
* each element by the corresponding entry in the quantization
|
||||
* array. Output is in a list of values in the zig-zag order.
|
||||
*
|
||||
* Parameters :
|
||||
* Input :
|
||||
* DCT_block -- The block to by quantized
|
||||
* Output :
|
||||
* quantized_list -- The quantized values in zig-zag order
|
||||
*
|
||||
* Return value :
|
||||
* None.
|
||||
*
|
||||
* Persistent data referenced :
|
||||
* quantization_array Module static array read
|
||||
* zig_zag_index Module static array read
|
||||
*
|
||||
****************************************************************************
|
||||
*/
|
||||
#define HIGHBITDUPPED(X) (((signed short) X) >> 15)
|
||||
void VP5_quantize_c( QUANTIZER *pbi, INT16 * DCT_block, Q_LIST_ENTRY * quantized_list, UINT8 bp )
|
||||
{
|
||||
UINT32 i, j;
|
||||
|
||||
INT32 * QuantRoundPtr = pbi->QuantRound[QTableSelect[bp]];
|
||||
INT32 * QuantCoeffsPtr = pbi->QuantCoeffs[QTableSelect[bp]];
|
||||
INT32 * ZBinPtr = pbi->ZeroBinSize[QTableSelect[bp]];
|
||||
|
||||
INT16 * DCT_blockPtr = DCT_block;
|
||||
INT32 temp;
|
||||
INT32 NonZeroACs = 0;
|
||||
INT16 *round = &pbi->round[0];
|
||||
INT16 *mult = &pbi->mult[0];
|
||||
INT16 *zbin = &pbi->zbin[0];
|
||||
|
||||
// Set the quantized_list to default to 0
|
||||
memset( quantized_list, 0, 64 * sizeof(Q_LIST_ENTRY) );
|
||||
|
||||
// dc quantization (disabled the zerobinning!!)
|
||||
temp = 0;
|
||||
if ( DCT_blockPtr[0] >= QuantRoundPtr[0] )
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] + QuantRoundPtr[0] ) ;
|
||||
else if ( DCT_blockPtr[0] <= -QuantRoundPtr[0] )
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] - QuantRoundPtr[0] ) + MIN16;
|
||||
quantized_list[0] = (Q_LIST_ENTRY) (temp>>16);
|
||||
|
||||
// Note that we add in a value to effect rounding.
|
||||
// AC Quantization
|
||||
for( i = 1; i < 64; i++)
|
||||
{
|
||||
// Zig Zag order
|
||||
j = dequant_index[i];
|
||||
|
||||
if ( DCT_blockPtr[j] >= ZBinPtr[j] )
|
||||
{
|
||||
temp = QuantCoeffsPtr[j] * ( DCT_blockPtr[j] + QuantRoundPtr[j] ) ;
|
||||
quantized_list[i] = (Q_LIST_ENTRY) (temp>>16);
|
||||
//NonZeroACs += quantized_list[i];;
|
||||
}
|
||||
else if ( DCT_blockPtr[j] <= -ZBinPtr[j] )
|
||||
{
|
||||
temp = QuantCoeffsPtr[j] * ( DCT_blockPtr[j] - QuantRoundPtr[j] ) + MIN16;
|
||||
quantized_list[i] = (Q_LIST_ENTRY) (temp>>16);
|
||||
//NonZeroACs -= quantized_list[i];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Now the DC quantization
|
||||
/*
|
||||
if ( NonZeroACs > 0 )
|
||||
{
|
||||
if ( DCT_blockPtr[0] >= QuantRoundPtr[0] )
|
||||
{
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] + QuantRoundPtr[0] ) ;
|
||||
quantized_list[0] = (Q_LIST_ENTRY) (temp>>16);
|
||||
}
|
||||
else if ( DCT_blockPtr[0] <= -QuantRoundPtr[0] )
|
||||
{
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] - QuantRoundPtr[0] ) + MIN16;
|
||||
quantized_list[0] = (Q_LIST_ENTRY) (temp>>16);
|
||||
}
|
||||
}
|
||||
// Use larger Zero Bin only if there are no ACs as this will help us get an EOB
|
||||
else
|
||||
{
|
||||
if ( DCT_blockPtr[0] >= ZBinPtr[0] )
|
||||
{
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] + QuantRoundPtr[0] ) ;
|
||||
quantized_list[0] = (Q_LIST_ENTRY) (temp>>16);
|
||||
}
|
||||
else if ( DCT_blockPtr[0] <= -ZBinPtr[0] )
|
||||
{
|
||||
temp = QuantCoeffsPtr[0] * ( DCT_blockPtr[0] - QuantRoundPtr[0] ) + MIN16;
|
||||
quantized_list[0] = (Q_LIST_ENTRY) (temp>>16);
|
||||
}
|
||||
}
|
||||
*/
|
||||
}
|
||||
/**************************** END COMPRESSOR SPECIFIC **********************************/
|
||||
/***************************************************************************************
|
||||
* Dequantiser code for decode loop
|
||||
/***************************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* Routine: init_pbi->dequantizer
|
||||
*
|
||||
* Purpose: Used to initialize the encoding/decoding data structures
|
||||
* and to select DCT algorithm
|
||||
*
|
||||
* Parameters :
|
||||
* Input :
|
||||
* UINT32 scale_factor
|
||||
* Defines the factor by which to scale QUANT_ARRAY to
|
||||
* produce quantization_array
|
||||
*
|
||||
* UINT8 QIndex ::
|
||||
* Index into Q table for current quantiser value.
|
||||
* Return value :
|
||||
* None.
|
||||
*
|
||||
****************************************************************************
|
||||
*/
|
||||
|
||||
void VP5_init_dequantizer ( QUANTIZER *pbi, UINT8 Vp3VersionNo )
|
||||
{
|
||||
int i, j;
|
||||
|
||||
|
||||
// *************** Y ******************/
|
||||
// Set up the Ac dequant values and then place in the zig-zag/transposed order as appropriate.
|
||||
for ( i = 1; i < 64; i++ )
|
||||
{
|
||||
j = pbi->quant_index[i];
|
||||
|
||||
pbi->dequant_coeffs[0][j] = VP5_QThreshTable[pbi->FrameQIndex] << IDCT_SCALE_FACTOR;
|
||||
}
|
||||
|
||||
// DC
|
||||
pbi->dequant_coeffs[0][0] = VP5_DcQuant[pbi->FrameQIndex] << IDCT_SCALE_FACTOR;
|
||||
|
||||
// *************** UV ******************/
|
||||
// Set up the Ac dequant values and then place in the zig-zag/transposed order as appropriate.
|
||||
for ( i = 1; i < 64; i++ )
|
||||
{
|
||||
j = pbi->quant_index[i];
|
||||
|
||||
pbi->dequant_coeffs[1][j] = VP5_UvQThreshTable[pbi->FrameQIndex] << IDCT_SCALE_FACTOR;
|
||||
}
|
||||
|
||||
// DC
|
||||
pbi->dequant_coeffs[1][0] = VP5_UvDcQuant[pbi->FrameQIndex] << IDCT_SCALE_FACTOR;
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************/
|
||||
/* */
|
||||
/* Select Quantisation Parameters */
|
||||
/* */
|
||||
/* void select_Y_dequantiser ( void ) */
|
||||
/* sets dequantiser to use for intra Y */
|
||||
/* */
|
||||
/* void select_Inter_dequantiser ( void ) */
|
||||
/* sets dequantiser to use for inter Y */
|
||||
/* */
|
||||
/* void select_UV_dequantiser ( void ) */
|
||||
/* sets dequantiser to use UV compression constants */
|
||||
/* */
|
||||
/****************************************************************************/
|
||||
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DeleteQuantizerBuffers
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be cleared
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
static void DeleteQuantizerBuffers(QUANTIZER *pbi)
|
||||
{
|
||||
|
||||
if(pbi->dequant_coeffsAlloc[0])
|
||||
duck_free(pbi->dequant_coeffsAlloc[0]);
|
||||
pbi->dequant_coeffsAlloc[0] = 0;
|
||||
pbi->dequant_coeffs[0] = 0;
|
||||
|
||||
if(pbi->dequant_coeffsAlloc[1])
|
||||
duck_free(pbi->dequant_coeffsAlloc[1]);
|
||||
pbi->dequant_coeffsAlloc[1] = 0;
|
||||
pbi->dequant_coeffs[1] = 0;
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : AllocateQuantizerBuffers
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
#define ROUNDUP32(X) ( ( ( (unsigned long) X ) + 31 )&( 0xFFFFFFE0 ) )
|
||||
static INT32 AllocateQuantizerBuffers(QUANTIZER *pbi)
|
||||
{
|
||||
DeleteQuantizerBuffers(pbi);
|
||||
|
||||
pbi->dequant_coeffsAlloc[0] = (INT16 *)duck_malloc(32+64*sizeof(INT16), DMEM_GENERAL);
|
||||
if(!pbi->dequant_coeffsAlloc[0]) { DeleteQuantizerBuffers(pbi); return FALSE;};
|
||||
pbi->dequant_coeffs[0] = (INT16 *)ROUNDUP32(pbi->dequant_coeffsAlloc[0]);
|
||||
|
||||
pbi->dequant_coeffsAlloc[1] = (INT16 *)duck_malloc(32+64*sizeof(INT16), DMEM_GENERAL);
|
||||
if(!pbi->dequant_coeffsAlloc[1]) { DeleteQuantizerBuffers(pbi); return FALSE;};
|
||||
pbi->dequant_coeffs[1] = (INT16 *)ROUNDUP32(pbi->dequant_coeffsAlloc[1]);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : DeleteQuantizer
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of POSTPROC to be deleted
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : frees the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void VP5_DeleteQuantizer(QUANTIZER **pbi)
|
||||
{
|
||||
// clear any existing info
|
||||
if(*pbi)
|
||||
{
|
||||
// Delete any other dynamically allocaed temporary buffers
|
||||
|
||||
DeleteQuantizerBuffers(*pbi);
|
||||
duck_free(*pbi);
|
||||
*pbi=0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : CreateQuantizer
|
||||
*
|
||||
*
|
||||
* INPUTS : Instance of PB to be initialized
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS :
|
||||
*
|
||||
*
|
||||
* FUNCTION : Initializes the Playback instance passed in
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
QUANTIZER * VP5_CreateQuantizer(void)
|
||||
{
|
||||
QUANTIZER *pbi=0;
|
||||
int postproc_size = sizeof(QUANTIZER);
|
||||
pbi=(QUANTIZER *) duck_malloc(postproc_size, DMEM_GENERAL);
|
||||
if(!pbi)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
// initialize whole structure to 0
|
||||
memset((unsigned char *) pbi, 0, sizeof(QUANTIZER));
|
||||
|
||||
if(!AllocateQuantizerBuffers(pbi))
|
||||
VP5_DeleteQuantizer(&pbi);
|
||||
|
||||
return pbi;
|
||||
}
|
||||
@@ -0,0 +1,338 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : recon.c
|
||||
*
|
||||
* Description : reconstruction code
|
||||
*
|
||||
* AUTHOR : jimb b
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.19 JBB 18 Mar 01 Reorganized code created this file
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
|
||||
#include "pbdll.h"
|
||||
#include "codec_common_interface.h"
|
||||
#include <string.h>
|
||||
|
||||
/****************************************************************************
|
||||
* Explicit imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
extern void AverageBlockBicubic_C( UINT8 *ReconPtr1, UINT8 *ReconPtr2, UINT16 *ReconRefPtr, UINT32 ReconPixelsPerLine);
|
||||
extern void NewAverageBlock( UINT8 *ReconPtr1, UINT8 *ReconPtr2, UINT16 *ReconRefPtr, UINT32 ReconPixelsPerLine);
|
||||
extern void UvAverageBlock( UINT8 *ReconPtr1, UINT8 *ReconPtr2, UINT16 *ReconRefPtr, UINT32 ReconPixelsPerLine, INT8 ModX, INT8 ModY );
|
||||
|
||||
/****************************************************************************
|
||||
* Module constants.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Functions
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Module Statics
|
||||
*****************************************************************************
|
||||
*/
|
||||
#define MIN(a, b) ( ( a < b ) ? a : b )
|
||||
#define Mod8(a) ( ((a) & 7))
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : PredictFilteredBlock
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : try to build an 8x8 block motion prediction block. If
|
||||
* the block is copied across a block boundary attempt
|
||||
* to eliminate the internal block border by applying the
|
||||
* loop filter internally to the block
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
*****************************************************************************/
|
||||
void PredictFiltered
|
||||
(
|
||||
PB_INSTANCE *pbi,
|
||||
UINT8 *SrcPtr,
|
||||
INT32 mx,
|
||||
INT32 my,
|
||||
INT32 MvShift
|
||||
)
|
||||
{
|
||||
|
||||
INT32 BoundaryX, BoundaryY;
|
||||
INT32 mVx, mVy;
|
||||
UINT32 ReconIndex = 0;
|
||||
MACROBLOCK_INFO *mbi=&pbi->mbi;
|
||||
|
||||
UINT8 TempPtr1 = 2 * 16 + 2;
|
||||
UINT32 TempPtr2 = TempPtr1;
|
||||
UINT8 *TempBuffer = pbi->LoopFilteredBlock;
|
||||
|
||||
// Calculate full pixel motion vector position
|
||||
if(mx > 0 )
|
||||
mVx = (mx >> MvShift);
|
||||
else
|
||||
mVx = -((-mx) >> MvShift);
|
||||
|
||||
if(my > 0 )
|
||||
mVy = (my >> MvShift);
|
||||
else
|
||||
mVy = -((-my) >> MvShift);
|
||||
|
||||
// calculate offset in last frame matching motion vector
|
||||
ReconIndex += mbi->FrameReconStride * mVy + mVx;
|
||||
|
||||
// give our selves a border of 2 extra pixel on all sides (for loop filter and half pixel moves)
|
||||
ReconIndex -= 2 * mbi->CurrentReconStride;
|
||||
ReconIndex -= 2;
|
||||
|
||||
// copy the 12x12 region starting from reconpixel index into our temp buffer.
|
||||
Copy12x12( SrcPtr + ReconIndex, TempBuffer, mbi->CurrentReconStride, 16);
|
||||
|
||||
// calculate block border position for x
|
||||
BoundaryX = (8 - Mod8(mVx))&7;
|
||||
|
||||
// calculate block border position for y
|
||||
BoundaryY = (8 - Mod8(mVy))&7;
|
||||
|
||||
// apply the loop filter at the horizontal boundary we selected
|
||||
if(BoundaryX)
|
||||
FilteringHoriz_12(
|
||||
pbi ->quantizer->FrameQIndex,
|
||||
TempBuffer + 2 + BoundaryX,
|
||||
16);
|
||||
|
||||
// apply the loop filter at the vertical boundary we selected
|
||||
if(BoundaryY)
|
||||
FilteringVert_12(
|
||||
pbi->quantizer->FrameQIndex,
|
||||
TempBuffer + 2 * 16 + BoundaryY * 16,
|
||||
16);
|
||||
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : PredictFilteredBlock
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : try to build an 8x8 block motion prediction block. If
|
||||
* the block is copied across a block boundary attempt
|
||||
* to eliminate the internal block border by applying the
|
||||
* loop filter internally to the block
|
||||
*
|
||||
* SPECIAL NOTES :
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
*****************************************************************************/
|
||||
#define AVERAGE_ROUTINE AverageBlock
|
||||
//#define AVERAGE_ROUTINE AverageBlockBicubic_C
|
||||
//#define AVERAGE_ROUTINE NewAverageBlock
|
||||
|
||||
//#define UV_AVERAGE_ROUTINE AverageBlock
|
||||
#define UV_AVERAGE_ROUTINE UvAverageBlock
|
||||
|
||||
void PredictFilteredBlock
|
||||
(
|
||||
PB_INSTANCE *pbi,
|
||||
INT16* OutputPtr,
|
||||
BLOCK_POSITION bp
|
||||
)
|
||||
{
|
||||
MACROBLOCK_INFO *mbi=&pbi->mbi;
|
||||
|
||||
UINT8 *SrcPtr;
|
||||
|
||||
UINT8 *TempBuffer = pbi->LoopFilteredBlock;
|
||||
|
||||
UINT32 TempPtr1 = 2*16+2;
|
||||
UINT32 TempPtr2 = TempPtr1;
|
||||
INT8 ModX, ModY;
|
||||
|
||||
// Which buffer are we working on?
|
||||
if ( VP5_Mode2Frame[pbi->mbi.Mode] == 2 )
|
||||
{
|
||||
SrcPtr = pbi->GoldenFrame;
|
||||
}
|
||||
else
|
||||
{
|
||||
SrcPtr = pbi->LastFrameRecon;
|
||||
}
|
||||
|
||||
PredictFiltered( pbi, SrcPtr+mbi->Recon, pbi->mbi.Mv[bp].x, pbi->mbi.Mv[bp].y, pbi->mbi.MvShift) ;
|
||||
|
||||
// determine if we have a half pixel move in the x direction
|
||||
if(pbi->mbi.Mv[bp].x & pbi->mbi.MvModMask)
|
||||
{
|
||||
if ( pbi->mbi.Mv[bp].x > 0 )
|
||||
{
|
||||
TempPtr2 += 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
TempPtr2 -= 1;
|
||||
}
|
||||
}
|
||||
|
||||
// handle half pixel motion in Y
|
||||
if(pbi->mbi.Mv[bp].y & pbi->mbi.MvModMask)
|
||||
{
|
||||
if ( pbi->mbi.Mv[bp].y > 0 )
|
||||
{
|
||||
TempPtr2 += 16;
|
||||
}
|
||||
else
|
||||
{
|
||||
TempPtr2 -= 16;
|
||||
}
|
||||
}
|
||||
|
||||
// put the results back into the real reconstruction buffer
|
||||
if (TempPtr1!=TempPtr2)
|
||||
{
|
||||
if ( bp < 4 )
|
||||
AVERAGE_ROUTINE(&TempBuffer[TempPtr1], &TempBuffer[TempPtr2], (unsigned short *)OutputPtr, 16);
|
||||
else
|
||||
{
|
||||
ModX = pbi->mbi.Mv[bp].x & 0x03;
|
||||
ModY = pbi->mbi.Mv[bp].y & 0x03;
|
||||
|
||||
//UV_AVERAGE_ROUTINE(&TempBuffer[TempPtr1], &TempBuffer[TempPtr2], (unsigned short *)OutputPtr, 16, ModX, ModY );
|
||||
AverageBlock(&TempBuffer[TempPtr1], &TempBuffer[TempPtr2], (unsigned short *)OutputPtr, 16);
|
||||
}
|
||||
}
|
||||
else
|
||||
UnpackBlock(&TempBuffer[TempPtr1], OutputPtr, 16);
|
||||
|
||||
}
|
||||
|
||||
#ifndef RECONSTRUCTMBATONCE
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : ReconstructBlock
|
||||
*
|
||||
* INPUTS :
|
||||
*
|
||||
*
|
||||
* OUTPUTS :
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Codes a DCT block
|
||||
*
|
||||
* Motion vectors and modes asumed to be defined at the MB level.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void ReconstructBlock
|
||||
(
|
||||
PB_INSTANCE *pbi,
|
||||
BLOCK_POSITION bp
|
||||
)
|
||||
{
|
||||
|
||||
// Action depends on decode mode.
|
||||
if ( pbi->mbi.Mode == CODE_INTER_NO_MV ) // Inter with no motion vector
|
||||
{
|
||||
ReconInter( pbi->TmpDataBuffer, (UINT8 *)&pbi->ThisFrameRecon[pbi->mbi.Recon],
|
||||
(UINT8 *)&pbi->LastFrameRecon[pbi->mbi.Recon],
|
||||
pbi->ReconDataBuffer, pbi->mbi.CurrentReconStride);
|
||||
|
||||
}
|
||||
else if ( VP5_ModeUsesMC[pbi->mbi.Mode] ) // The mode uses a motion vector.
|
||||
{
|
||||
// For the compressor we did this already ( possible optimization).
|
||||
PredictFilteredBlock( pbi, pbi->TmpDataBuffer,bp);
|
||||
|
||||
ReconBlock(
|
||||
pbi->TmpDataBuffer,
|
||||
pbi->ReconDataBuffer,
|
||||
(UINT8 *)&pbi->ThisFrameRecon[pbi->mbi.Recon],
|
||||
pbi->mbi.CurrentReconStride );
|
||||
}
|
||||
else if ( pbi->mbi.Mode == CODE_USING_GOLDEN ) // Golden frame with motion vector
|
||||
{
|
||||
// Reconstruct the pixel data using the golden frame reconstruction and change data
|
||||
ReconInter( pbi->TmpDataBuffer, (UINT8 *)&pbi->ThisFrameRecon[pbi->mbi.Recon],
|
||||
(UINT8 *)&pbi->GoldenFrame[ pbi->mbi.Recon ],
|
||||
pbi->ReconDataBuffer, pbi->mbi.CurrentReconStride );
|
||||
}
|
||||
else // Simple Intra coding
|
||||
{
|
||||
// Get the pixel index for the first pixel in the fragment.
|
||||
ReconIntra( pbi->TmpDataBuffer, (UINT8 *)&pbi->ThisFrameRecon[pbi->mbi.Recon], (UINT16 *)pbi->ReconDataBuffer, pbi->mbi.CurrentReconStride );
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/************************************************************************** *
|
||||
* ROUTINE : CopyBlock
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None
|
||||
*
|
||||
* RETURNS : None.
|
||||
*
|
||||
* FUNCTION : Copies a block from source to destination
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void CopyBlockC(unsigned char *src, unsigned char *dest, unsigned int srcstride)
|
||||
{
|
||||
unsigned char * s = src;
|
||||
unsigned char * d = dest;
|
||||
unsigned int stride = srcstride;
|
||||
|
||||
int j;
|
||||
for ( j = 0; j < 8; j++ )
|
||||
{
|
||||
((UINT32*)d)[0] = ((UINT32*)s)[0];
|
||||
((UINT32*)d)[1] = ((UINT32*)s)[1];
|
||||
s+=stride;
|
||||
d+=stride;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,750 @@
|
||||
/****************************************************************************
|
||||
*
|
||||
* Module Title : vfwpbdll_if.c
|
||||
*
|
||||
* Description : Video codec demo playback dll interface
|
||||
*
|
||||
* AUTHOR : Paul Wilkins
|
||||
*
|
||||
*****************************************************************************
|
||||
* Revision History
|
||||
*
|
||||
* 1.29 YWX 17/dec/02 Added support of deinterlace
|
||||
* 1.28 YWX 05/08/02 Changed postprocess level setup for interlaced material
|
||||
* 1.27 AWG 20 Jun 01 Added code to overlay Motion Vectors onto display
|
||||
* 1.26 JBB 13 Jun 01 VP4 Code Clean Out
|
||||
* 1.25 YWX 26-Apr-01 Removed call of SetPbParam() in StartDecoder()
|
||||
* And set CPUFree as 70 when PostProcessingLevel=9
|
||||
* 1.24 JBB 25-apr-01 clear sysstate added at end of frame blit
|
||||
* 1.23 JBB 06-Apr-01 CPU Free variable respond
|
||||
* 1.22 SJL 22-Mar-01 Fixed MAC compile errors
|
||||
* 1.21 JBX 22-Mar-01 Merged with new vp4-mapca bitstream
|
||||
* 1.20 SJL 01 Dec 00 Fixed MAC compile errors
|
||||
* 1.19 JBB 30 Nov 00 Version number changes
|
||||
* 1.18 JBB 14 Nov 00 Added version information function and pragma and cleaned
|
||||
* out unused code
|
||||
* 1.17 JBB 17-oct-00 Ifdefs around version information
|
||||
* 1.16 SJL 25 Aug 00 Fixed Mac compile error
|
||||
* 1.15 JBB 25 Aug 00 Better versioning
|
||||
* 1.14 JBB 22 Aug 00 Ansi C conversion
|
||||
* 1.13 SJL 14 Aug00 Moved SetPbParam into another file for the MAC
|
||||
* 1.12 YWX 2 Aug00 Changed Postprocessing level initialization
|
||||
* 1.11 JBB 31Jul00 Changed requirements for postprocessing due to new
|
||||
* optimiztions
|
||||
* 1.10 JBB 27Jul00 Added malloc checks
|
||||
* 1.09 YWX 15/05/00 Check Processor and Frame size to enable/disable
|
||||
* postprocessor
|
||||
* 1.08 YWX 08/05/00 Added #if defined directives for postprocess
|
||||
* 1.07 JBB 05/05/00 Added PostProcessing Parameter
|
||||
* 1.06 JBB 27/01/99 Globals Removed, use of PB_INSTANCE, must be created
|
||||
* 1.05 PGW 05/11/99 Changes to support AC range entropy tables and to output
|
||||
* the appropriate stats to tune them.
|
||||
* 1.04 PGW 01/09/99 Modified to simulate Tim's DxReference interface.
|
||||
* 1.03 PGW 30/07/99 Added exception handlers and some code to try and insure
|
||||
* decoder is initialised before any frames are decoded.
|
||||
* 1.02 PGW 09/07/99 Added code to support profile timing
|
||||
* 1.01 PGW 29/06/99 Changes in DecodeFrame() to handle inversion of DIB when
|
||||
* requested plus offsets into and pitch of the output image
|
||||
* buffer.
|
||||
* 1.00 PGW 28/06/99 New Configuration baseline.
|
||||
*
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Header Files
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
#define STRICT /* Strict type checking. */
|
||||
#include <stdio.h>
|
||||
|
||||
#ifndef _MSC_VER
|
||||
|
||||
#define __try
|
||||
|
||||
#endif
|
||||
|
||||
#include "huffman.h"
|
||||
#include "pbdll.h"
|
||||
#include <math.h>
|
||||
#include "vp50dversion.h"
|
||||
#include "decodemode.h"
|
||||
#include "postproc_if.h"
|
||||
|
||||
#ifndef MAPCA
|
||||
#define CommentString "\nON2.COM VERSION VP50D " VP50DVERSION "\n"
|
||||
#pragma comment(exestr,CommentString)
|
||||
#endif
|
||||
/****************************************************************************
|
||||
* Explicit Imports
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
extern void DecodeFrameMbs(PB_INSTANCE *pbi);
|
||||
extern unsigned int CPUFrequency;
|
||||
|
||||
/****************************************************************************
|
||||
* Module statics.
|
||||
*****************************************************************************
|
||||
*/
|
||||
|
||||
|
||||
#ifdef PBSTATS1
|
||||
INT32 TotQ = 0;
|
||||
INT32 PBFrameNumber = 0;
|
||||
#endif
|
||||
static const char vp31dVersion[] = VP50DVERSION;
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Exported Global Variables
|
||||
*****************************************************************************
|
||||
*/
|
||||
#if defined(_MSC_VER)
|
||||
#if defined(POSTPROCESS)
|
||||
static const unsigned long PP_MACHINE_LOWLIMIT = 350; //Lowest CPU (MHz) to enable PostProcess
|
||||
static const unsigned long PP_MACHINE_MIDLIMIT = 400; //Lowest CPU (MHz) to enable PostProcess
|
||||
static const unsigned long PP_MACHINE_TOPLIMIT = 590; //Lowest CPU (MHz) to enable PostProcess
|
||||
#endif
|
||||
#endif
|
||||
|
||||
extern void VP5_InitialiseConfiguration(PB_INSTANCE *pbi);
|
||||
#ifdef PBSTATS1
|
||||
// TEMP diagnostic variables
|
||||
INT32 TotBlocksCoded;
|
||||
#endif
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Foreward references
|
||||
*****************************************************************************
|
||||
*/
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP31D_GetVersionNumber
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None .
|
||||
*
|
||||
* FUNCTION : Returns a pointer to the version string
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
const char * CCONV VP50D_GetVersionNumber(void)
|
||||
{
|
||||
return vp31dVersion;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : StartDecoder
|
||||
*
|
||||
* INPUTS : The handle of the display window.
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : TRUE if succeeds else FALSE.
|
||||
*
|
||||
* FUNCTION : Starts the compressor grabber
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
BOOL CCONV VP5_StartDecoder( PB_INSTANCE **pbi, UINT32 ImageWidth, UINT32 ImageHeight )
|
||||
{
|
||||
__try
|
||||
{
|
||||
|
||||
|
||||
// set up our structure holding all formerly global information about a playback instance
|
||||
*pbi = VP5_CreatePBInstance();
|
||||
|
||||
// Set Flag to indicate that a key frame is required as the first input
|
||||
(*pbi)->ScaleWidth = ImageWidth;
|
||||
(*pbi)->ScaleHeight = ImageHeight;
|
||||
(*pbi)->OutputWidth = ImageWidth;
|
||||
(*pbi)->OutputHeight = ImageHeight;
|
||||
(*pbi)->OutputStride = ImageWidth + 32;
|
||||
|
||||
|
||||
// Validate the combination of height and width.
|
||||
(*pbi)->Configuration.VideoFrameWidth = ImageWidth;
|
||||
(*pbi)->Configuration.VideoFrameHeight = ImageHeight;
|
||||
|
||||
#ifndef MAPCA
|
||||
(*pbi)->postproc = CreatePostProcInstance(&(*pbi)->Configuration);
|
||||
#endif
|
||||
//(*pbi)->postproc = CreatePostProcInstance(&(*pbi)->Configuration);
|
||||
(*pbi)->quantizer = VP5_CreateQuantizer();
|
||||
|
||||
(*pbi)->ProcessorFrequency = CPUFrequency;
|
||||
(*pbi)->DeInterlaceMode = 1;
|
||||
// Fills in fragment counts as well
|
||||
if(!VP5_InitFrameDetails(*pbi) )
|
||||
{
|
||||
VP5_DeletePBInstance(pbi);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
/* Set last_dct_thresh to an illegal value to make sure the
|
||||
* Q tables are initialised for the new video sequence.
|
||||
*/
|
||||
(*pbi)->quantizer->LastQuantizerValue = -1;
|
||||
|
||||
// Set up various configuration parameters.
|
||||
VP5_InitialiseConfiguration(*pbi);
|
||||
|
||||
#ifdef MAPCA
|
||||
InitDMAWriteReconDS(*pbi);
|
||||
InitDMAReadReferenceDS(*pbi);
|
||||
#endif
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
__except( TRUE )
|
||||
{
|
||||
VP5_ErrorTrap( *pbi, GEN_EXCEPTIONS );
|
||||
return FALSE;
|
||||
}
|
||||
#endif
|
||||
|
||||
}
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_GetPbParam
|
||||
*
|
||||
* INPUTS : PB_COMMAND_TYPE Command
|
||||
* char * Parameter
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Generalised command interface to decoder.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void CCONV VP5_GetPbParam( PB_INSTANCE *pbi, PB_COMMAND_TYPE Command, UINT32 *Parameter )
|
||||
{
|
||||
switch ( Command )
|
||||
{
|
||||
#if defined(POSTPROCESS)
|
||||
case PBC_SET_POSTPROC:
|
||||
*Parameter =pbi->PostProcessingLevel;
|
||||
#endif
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#define CRITICALWATERMARK (int) (31000 * pbi->CPUFree / 100)
|
||||
#define DOWNWATERMARK (int) (30000 * pbi->CPUFree / 100)
|
||||
#define UPWATERMARK (int) (28000 * pbi->CPUFree / 100)
|
||||
int PickPostProcessingLevel(PB_INSTANCE *pbi)
|
||||
{
|
||||
int minimumTime = pbi->thisDecodeTime + pbi->avgBlitTime + pbi->avgPPTime[8];
|
||||
int thisTime = minimumTime + pbi->avgPPTime[pbi->PostProcessingLevel];
|
||||
int avgTime = pbi->avgDecodeTime + pbi->avgBlitTime;
|
||||
|
||||
// estimate the times of all of our unknown postprocessors
|
||||
if(pbi->avgPPTime[6]==0)
|
||||
pbi->avgPPTime[6] = avgTime>>1;
|
||||
|
||||
if(pbi->avgPPTime[5]==0)
|
||||
pbi->avgPPTime[5] = avgTime>>1;
|
||||
|
||||
if(pbi->avgPPTime[4]==0)
|
||||
pbi->avgPPTime[4] = (avgTime ) >> 2;
|
||||
|
||||
if(pbi->avgPPTime[8]==0)
|
||||
pbi->avgPPTime[8] = avgTime>>3;
|
||||
|
||||
|
||||
if(pbi->CPUFree == 0 )
|
||||
return pbi->PostProcessingLevel;
|
||||
|
||||
// automatically select a postprocessing level based on the amount
|
||||
// of time taken to decode blit and postprocess etc
|
||||
|
||||
// more than 1/30 of a second no postprocessing at all (its better to show an
|
||||
// ugly frame than none at all). We use 1/30th of a second because nothing
|
||||
// tells us the actual framerate
|
||||
if(thisTime > (int) (CRITICALWATERMARK))
|
||||
{
|
||||
// this frame's taking to long try to make up time on the subsequent frames
|
||||
pbi->avgDecodeTime = pbi->thisDecodeTime;
|
||||
|
||||
// pick a post processor we can decode in less than 2/3 the time
|
||||
if(pbi->avgPPTime[6] + minimumTime < CRITICALWATERMARK )
|
||||
return 6;
|
||||
|
||||
if(pbi->avgPPTime[5] + minimumTime < CRITICALWATERMARK )
|
||||
return 5;
|
||||
|
||||
if(pbi->avgPPTime[4] + minimumTime < CRITICALWATERMARK )
|
||||
return 4;
|
||||
|
||||
if(pbi->avgPPTime[8] + minimumTime < CRITICALWATERMARK )
|
||||
return 8;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(thisTime < DOWNWATERMARK && thisTime > UPWATERMARK)
|
||||
return pbi->PostProcessingLevel;
|
||||
|
||||
|
||||
|
||||
// pick a post processor we can decode in less than 2/3 the time
|
||||
if(pbi->avgPPTime[6] + avgTime < UPWATERMARK )
|
||||
return 6;
|
||||
|
||||
if(pbi->avgPPTime[5] + avgTime < UPWATERMARK )
|
||||
return 5;
|
||||
|
||||
if(pbi->avgPPTime[4] + avgTime < UPWATERMARK )
|
||||
return 4;
|
||||
|
||||
if(pbi->avgPPTime[8] + avgTime < UPWATERMARK )
|
||||
return 8;
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
||||
#ifndef MAPCA
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_GetYUVConfig
|
||||
*
|
||||
* INPUTS : YUV_BUFFER_CONFIG * YuvConfig
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Gets details of the reconstruction buffer
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
void CCONV VP5_GetYUVConfig( PB_INSTANCE (*pbi), YUV_BUFFER_CONFIG * YuvConfig )
|
||||
{
|
||||
__try
|
||||
{
|
||||
#ifdef _MSC_VER
|
||||
unsigned int duration;
|
||||
unsigned int starttsc,endtsc;
|
||||
VP5_readTSC(&starttsc);
|
||||
pbi->PostProcessingLevel = PickPostProcessingLevel(pbi);
|
||||
#endif
|
||||
if( pbi->PostProcessingLevel ||(pbi->Configuration.Interlaced && pbi->DeInterlaceMode))
|
||||
{
|
||||
#ifdef _MSC_VER
|
||||
extern void vp5_showinfo2(PB_INSTANCE *pbi);
|
||||
extern void vp5_showinfo(PB_INSTANCE *pbi);
|
||||
|
||||
|
||||
if(pbi->PostProcessingLevel > 200 )
|
||||
{
|
||||
PostProcess
|
||||
(
|
||||
pbi->postproc,
|
||||
pbi->Vp3VersionNo,
|
||||
pbi->FrameType,
|
||||
pbi->PostProcessingLevel-200,
|
||||
pbi->AvgFrameQIndex,
|
||||
pbi->LastFrameRecon,
|
||||
pbi->PostProcessBuffer,
|
||||
(unsigned char *) pbi->FragInfo,
|
||||
sizeof(FRAG_INFO),
|
||||
0x0001
|
||||
);
|
||||
VP5_readTSC(&endtsc);
|
||||
vp5_showinfo(pbi);
|
||||
}
|
||||
else if(pbi->PostProcessingLevel > 100 )
|
||||
{
|
||||
|
||||
PostProcess
|
||||
(
|
||||
pbi->postproc,
|
||||
pbi->Vp3VersionNo,
|
||||
pbi->FrameType,
|
||||
pbi->PostProcessingLevel-100,
|
||||
pbi->AvgFrameQIndex,
|
||||
pbi->LastFrameRecon,
|
||||
pbi->PostProcessBuffer,
|
||||
(unsigned char *) pbi->FragInfo,
|
||||
sizeof(FRAG_INFO),
|
||||
0x0001
|
||||
);
|
||||
VP5_readTSC(&endtsc);
|
||||
vp5_showinfo2(pbi);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
pbi->AvgFrameQIndex = pbi->quantizer->FrameQIndex;
|
||||
|
||||
PostProcess
|
||||
(
|
||||
pbi->postproc,
|
||||
pbi->Vp3VersionNo,
|
||||
pbi->FrameType,
|
||||
pbi->PostProcessingLevel,
|
||||
pbi->AvgFrameQIndex,
|
||||
pbi->LastFrameRecon,
|
||||
pbi->PostProcessBuffer,
|
||||
(unsigned char *) pbi->FragInfo,
|
||||
sizeof(FRAG_INFO),
|
||||
0x0001
|
||||
);
|
||||
#ifdef _MSC_VER
|
||||
VP5_readTSC(&endtsc);
|
||||
#endif
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if(pbi->BlackClamp)
|
||||
{
|
||||
ClampLevels( pbi->postproc,pbi->BlackClamp,pbi->WhiteClamp,pbi->PostProcessBuffer, pbi->PostProcessBuffer);
|
||||
}
|
||||
if( pbi->Configuration.VideoFrameWidth < pbi->OutputWidth ||
|
||||
pbi->Configuration.VideoFrameHeight < pbi->OutputHeight )
|
||||
{
|
||||
YuvConfig->YWidth = pbi->OutputWidth+32;
|
||||
YuvConfig->YHeight = pbi->OutputHeight+32;
|
||||
YuvConfig->YStride = YuvConfig->YWidth;
|
||||
|
||||
YuvConfig->UVWidth = YuvConfig->YWidth / 2;
|
||||
YuvConfig->UVHeight = YuvConfig->YHeight / 2;
|
||||
YuvConfig->UVStride = YuvConfig->YStride / 2;
|
||||
|
||||
YuvConfig->YBuffer = (char *)pbi->ScaleBuffer;
|
||||
YuvConfig->UBuffer = (char *)pbi->ScaleBuffer+YuvConfig->YWidth*YuvConfig->YHeight;
|
||||
YuvConfig->VBuffer = (char *)pbi->ScaleBuffer+YuvConfig->YWidth*YuvConfig->YHeight+YuvConfig->UVWidth*YuvConfig->UVHeight;
|
||||
|
||||
if(pbi->PostProcessingLevel)
|
||||
{
|
||||
ScaleOrCenter( pbi->postproc, pbi->PostProcessBuffer, YuvConfig );
|
||||
}
|
||||
else
|
||||
{
|
||||
ScaleOrCenter( pbi->postproc, pbi->LastFrameRecon, YuvConfig );
|
||||
}
|
||||
|
||||
YuvConfig->YBuffer +=
|
||||
(YuvConfig->YHeight - pbi->OutputHeight ) / 2 * YuvConfig->YStride
|
||||
+(YuvConfig->YWidth - pbi->OutputWidth) / 2;
|
||||
YuvConfig->YWidth = pbi->OutputWidth;
|
||||
YuvConfig->YHeight = pbi->OutputHeight;
|
||||
|
||||
YuvConfig->UBuffer +=
|
||||
(YuvConfig->UVHeight - pbi->OutputHeight/2 ) / 2 * YuvConfig->UVStride
|
||||
+(YuvConfig->UVWidth - pbi->OutputWidth/2) / 2;
|
||||
|
||||
YuvConfig->VBuffer +=
|
||||
(YuvConfig->UVHeight - pbi->OutputHeight/2 ) / 2 * YuvConfig->UVStride
|
||||
+(YuvConfig->UVWidth - pbi->OutputWidth/2) / 2;
|
||||
|
||||
YuvConfig->UVWidth = pbi->OutputWidth / 2;
|
||||
YuvConfig->UVHeight = pbi->OutputHeight / 2;
|
||||
//YuvConfig->UVStride = pbi->OutputWidth / 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
YuvConfig->YWidth = pbi->Configuration.VideoFrameWidth;
|
||||
YuvConfig->YHeight = pbi->Configuration.VideoFrameHeight;
|
||||
YuvConfig->YStride = pbi->Configuration.YStride;
|
||||
|
||||
YuvConfig->UVWidth = pbi->Configuration.VideoFrameWidth / 2;
|
||||
YuvConfig->UVHeight = pbi->Configuration.VideoFrameHeight / 2;
|
||||
YuvConfig->UVStride = pbi->Configuration.UVStride;
|
||||
|
||||
//if(pbi->PostProcessingLevel && (pbi->quantizer->FrameQIndex < PPROC_QTHRESH))
|
||||
if( pbi->PostProcessingLevel ||(pbi->Configuration.Interlaced && pbi->DeInterlaceMode))
|
||||
{
|
||||
YuvConfig->YBuffer = (char *)&pbi->PostProcessBuffer[pbi->ReconYDataOffset+(pbi->Configuration.YStride * UMV_BORDER) + UMV_BORDER];
|
||||
YuvConfig->UBuffer = (char *)&pbi->PostProcessBuffer[pbi->ReconUDataOffset+ (pbi->Configuration.UVStride * (UMV_BORDER/2)) + (UMV_BORDER/2)];
|
||||
YuvConfig->VBuffer = (char *)&pbi->PostProcessBuffer[pbi->ReconVDataOffset+ (pbi->Configuration.UVStride * (UMV_BORDER/2)) + (UMV_BORDER/2)];
|
||||
}
|
||||
else
|
||||
{
|
||||
YuvConfig->YBuffer = (char *)&pbi->LastFrameRecon[pbi->ReconYDataOffset+ (pbi->Configuration.YStride * UMV_BORDER) + UMV_BORDER];
|
||||
YuvConfig->UBuffer = (char *)&pbi->LastFrameRecon[pbi->ReconUDataOffset+ (pbi->Configuration.UVStride * (UMV_BORDER/2)) + (UMV_BORDER/2)];
|
||||
YuvConfig->VBuffer = (char *)&pbi->LastFrameRecon[pbi->ReconVDataOffset+ (pbi->Configuration.UVStride * (UMV_BORDER/2)) + (UMV_BORDER/2)];
|
||||
}
|
||||
}
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
duration = ( endtsc - starttsc )/ pbi->ProcessorFrequency ;
|
||||
|
||||
if( pbi->avgPPTime[pbi->PostProcessingLevel%10] == 0)
|
||||
{
|
||||
pbi->avgPPTime[pbi->PostProcessingLevel%10] = duration;
|
||||
}
|
||||
else
|
||||
{
|
||||
pbi->avgPPTime[pbi->PostProcessingLevel%10] = ( 7 * pbi->avgPPTime[pbi->PostProcessingLevel%10] + duration ) >> 3;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#if defined(_MSC_VER)
|
||||
__except ( TRUE )
|
||||
{
|
||||
VP5_ErrorTrap( pbi, GEN_EXCEPTIONS );
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
/****************************************************************************
|
||||
Debugging Aid Only */
|
||||
|
||||
void writeframeYX(PB_INSTANCE *pbi, char * address,int x)
|
||||
{ // write the frame
|
||||
FILE *yframe;
|
||||
char filename[255];
|
||||
#ifdef MAPCA
|
||||
sprintf(filename,"MapYF%d.raw",x);
|
||||
#else
|
||||
sprintf(filename,"PcYF%d.raw",x);
|
||||
#endif
|
||||
yframe=fopen(filename,"wb");
|
||||
fwrite(address,pbi->ReconYPlaneSize,1,yframe);
|
||||
fclose(yframe);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_DecodeFrameToYUV
|
||||
*
|
||||
* INPUTS : UINT8 * VideoBufferPtr
|
||||
* Compressed input video data
|
||||
*
|
||||
* UINT32 ByteCount
|
||||
* Number of bytes compressed data in buffer. *
|
||||
*
|
||||
* UINT32 Height and width of image to be decoded
|
||||
*
|
||||
* OUTPUTS : None
|
||||
* None
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Decodes a frame into the internal YUV reconstruction buffer.
|
||||
* Details of this buffer can be obtained by calling GetYUVConfig().
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
int CCONV VP5_DecodeFrameToYUV( PB_INSTANCE (*pbi), char * VideoBufferPtr, unsigned int ByteCount,
|
||||
UINT32 ImageWidth, UINT32 ImageHeight )
|
||||
{
|
||||
unsigned char *tmp;
|
||||
(void) ImageHeight;
|
||||
(void) ImageWidth;
|
||||
__try
|
||||
{
|
||||
#ifdef _MSC_VER
|
||||
unsigned int duration;
|
||||
unsigned int starttsc,endtsc;
|
||||
VP5_readTSC(&starttsc);
|
||||
#endif
|
||||
pbi->CurrentFrameSize = ByteCount;
|
||||
|
||||
// start the boolean decoder
|
||||
StartDecode(&pbi->br, (unsigned char*)VideoBufferPtr);
|
||||
|
||||
// decode the frame header
|
||||
if ( !VP5_LoadFrame(pbi) )
|
||||
return -1;
|
||||
|
||||
|
||||
// decode and reconstruct frame
|
||||
DecodeFrameMbs(pbi);
|
||||
|
||||
// switch pointers so lastframe recon is this frame
|
||||
tmp = pbi->LastFrameRecon;
|
||||
pbi->LastFrameRecon = pbi->ThisFrameRecon;
|
||||
pbi->ThisFrameRecon = tmp;
|
||||
|
||||
|
||||
#ifndef MAPCA
|
||||
// update the border
|
||||
UpdateUMVBorder(pbi->postproc, pbi->LastFrameRecon);
|
||||
#else
|
||||
VP5_UpdateUMVBorder(pbi, pbi->LastFrameRecon);
|
||||
#endif
|
||||
|
||||
|
||||
if( pbi->FrameType == BASE_FRAME )
|
||||
{
|
||||
memcpy(pbi->GoldenFrame, pbi->LastFrameRecon, pbi->ReconYPlaneSize + 2* pbi->ReconUVPlaneSize);
|
||||
}
|
||||
|
||||
#ifdef MAPCA
|
||||
//if(debugme<1)
|
||||
{
|
||||
//EtiSysDcFlushDcache();
|
||||
//writeframeYX(pbi,pbi->LastFrameRecon,debugme);
|
||||
//debugme++;
|
||||
}
|
||||
#endif
|
||||
// If appropriate clear the MMX state.
|
||||
ClearSysState();
|
||||
|
||||
//temp
|
||||
//vp5_appendframe(pbi);
|
||||
|
||||
#ifdef PBSTATS1
|
||||
// Update PB stats
|
||||
TotQ += pbi->quantizer->ThisFrameQualityValue;
|
||||
PBFrameNumber += 1;
|
||||
#endif
|
||||
|
||||
if(pbi->FrameType == BASE_FRAME )
|
||||
pbi->AvgFrameQIndex = pbi->quantizer->FrameQIndex;
|
||||
else
|
||||
pbi->AvgFrameQIndex = (2 + 3 * pbi->AvgFrameQIndex + pbi->quantizer->FrameQIndex) / 4 ;
|
||||
|
||||
#ifdef _MSC_VER
|
||||
VP5_readTSC(&endtsc);
|
||||
|
||||
duration = (endtsc-starttsc)/ (pbi->ProcessorFrequency) ;
|
||||
|
||||
pbi->thisDecodeTime = duration;
|
||||
|
||||
if( pbi->avgDecodeTime == 0)
|
||||
{
|
||||
pbi->avgDecodeTime = duration;
|
||||
}
|
||||
else
|
||||
{
|
||||
pbi->avgDecodeTime = (7*pbi->avgDecodeTime + duration)>>3;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
}
|
||||
#if defined(_MSC_VER)
|
||||
__except ( TRUE )
|
||||
{
|
||||
VP5_ErrorTrap( pbi, GEN_EXCEPTIONS );
|
||||
return -2;
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_StopDecoder
|
||||
*
|
||||
* INPUTS : None
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None .
|
||||
*
|
||||
* FUNCTION : Stops the encoder and grabber
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int CCONV VP5_StopDecoder(PB_INSTANCE **pbi)
|
||||
{
|
||||
|
||||
#ifdef MAPCA
|
||||
CloseDMAReadReferenceDS();
|
||||
CloseDMAWriteReconDS();
|
||||
#endif
|
||||
|
||||
__try
|
||||
{
|
||||
if(*pbi)
|
||||
{
|
||||
// Set flag to say that the decoder is no longer initialised
|
||||
VP5_DeleteQuantizer(&(*pbi)->quantizer);
|
||||
#ifndef MAPCA
|
||||
DeletePostProcInstance(&(*pbi)->postproc);
|
||||
#endif
|
||||
VP5_DeleteFragmentInfo(*pbi);
|
||||
VP5_DeleteFrameInfo(*pbi);
|
||||
|
||||
|
||||
VP5_DeletePBInstance(pbi);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
__except ( TRUE )
|
||||
{
|
||||
VP5_ErrorTrap( *pbi, GEN_EXCEPTIONS );
|
||||
return FALSE;
|
||||
}
|
||||
#endif
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
#ifndef MAPCA
|
||||
/****************************************************************************
|
||||
*
|
||||
* ROUTINE : VP5_ErrorTrap
|
||||
*
|
||||
* INPUTS : Nonex.
|
||||
*
|
||||
* OUTPUTS : None.
|
||||
*
|
||||
* RETURNS : None
|
||||
*
|
||||
* FUNCTION : Called when a fatal error is detected.
|
||||
* Sets an error flag and loops untill the thread is
|
||||
* terminated.
|
||||
*
|
||||
* SPECIAL NOTES : None.
|
||||
*
|
||||
*
|
||||
* ERRORS : None.
|
||||
*
|
||||
****************************************************************************/
|
||||
static void VP5_ErrorTrap( PB_INSTANCE *pbi, int ErrorCode )
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
@@ -0,0 +1,429 @@
|
||||
/*
|
||||
dxvmpg.cpp : Defines the entry point for the console application.
|
||||
*/
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "dkpltfrm.h" /* platform specifics */
|
||||
#include "duktypes.h" /* predefined general types used at duck */
|
||||
|
||||
#include "duck_mem.h" /* interface to memory manager */
|
||||
#include "dxl_main.h" /* interface to dxv */
|
||||
#include "pbdll.h"
|
||||
|
||||
typedef unsigned long FourCC;
|
||||
|
||||
#define VP50_FOURCC DXL_MKFOURCC( 'V', 'P', '5', '0')
|
||||
void vp50_SetParameter(DXL_XIMAGE_HANDLE src,int Command, unsigned long Parameter );
|
||||
|
||||
extern void vp3SetBlit(void);
|
||||
extern void VP5_VPInitLibrary(void);
|
||||
extern void VP5_VPDeInitLibrary(void);
|
||||
#ifdef _MSC_VER
|
||||
#pragma warning(disable:4055)
|
||||
#endif
|
||||
|
||||
#include "duck_dxl.h"
|
||||
extern void VP5_readTSC(unsigned long *tsc);
|
||||
|
||||
void vp50_GetInfo(unsigned char * source, FrameInfo * frameInfo)
|
||||
{
|
||||
|
||||
// Is the frame and inter frame or a key frame
|
||||
frameInfo->KeyFrame = !(source[0] > 0x7f);
|
||||
frameInfo->Quality = source[0] >> 2;
|
||||
if(frameInfo->KeyFrame)
|
||||
frameInfo->Version = ((source[2]>>3) & 0x1f );
|
||||
else
|
||||
frameInfo->Version = 0;
|
||||
|
||||
frameInfo->vp30Flag = (int)source[1];
|
||||
|
||||
}
|
||||
|
||||
|
||||
// YUV buffer configuration structure
|
||||
typedef struct
|
||||
{
|
||||
int YWidth;
|
||||
int YHeight;
|
||||
int YStride;
|
||||
|
||||
int UVWidth;
|
||||
int UVHeight;
|
||||
int UVStride;
|
||||
|
||||
char * YBuffer;
|
||||
char * UBuffer;
|
||||
char * VBuffer;
|
||||
|
||||
char * uvStart;
|
||||
int uvDstArea;
|
||||
int uvUsedArea;
|
||||
|
||||
} DXV_YUV_BUFFER_CONFIG;
|
||||
|
||||
/* define an xImage structure based on the core xImage struct */
|
||||
typedef struct tXImageCODEC
|
||||
{
|
||||
xImageBaseStruct;
|
||||
FourCC myFourCC;
|
||||
DXV_YUV_BUFFER_CONFIG FrameBuffer;
|
||||
PB_INSTANCE *myPBI;
|
||||
int owned;
|
||||
|
||||
} vp50_XIMAGE,*vp50_XIMAGE_HANDLE;
|
||||
|
||||
static dxvBitDepth bitDepths[] =
|
||||
{
|
||||
DXRGB32,DXRGB24,DXRGB16,DXRGBNULL
|
||||
};
|
||||
|
||||
|
||||
typedef void ((*vp5BLIT_FUNC)(unsigned char *, int, YUV_BUFFER_CONFIG *));
|
||||
typedef void ((*vp5_VSCREEN_FUNC)(void));
|
||||
|
||||
|
||||
DXL_INTERNAL_FORMAT vp50_GetXImageInternalFormat(DXL_XIMAGE_HANDLE xImage,
|
||||
DXL_VSCREEN_HANDLE vScreen)
|
||||
{
|
||||
(void) vScreen;
|
||||
(void) xImage;
|
||||
return YV12;
|
||||
}
|
||||
int vp50_blit(PB_INSTANCE *pbi,DXL_XIMAGE_HANDLE src, DXL_VSCREEN_HANDLE vScreen,DXV_YUV_BUFFER_CONFIG *FrameBuffer,int x, int y )
|
||||
{
|
||||
if(vScreen && ((void *)(src->internalFormat) != NULL)) {
|
||||
/* get your hamdy damdy((c)1997 Duck North) registered blitter setup */
|
||||
vScreen->blitSetup = DXL_GetBlitSetupFunc(src,vScreen);
|
||||
vScreen->blitExit = DXL_GetBlitExitFunc(src,vScreen);
|
||||
vScreen->blitter = DXL_GetBlitFunc(src, vScreen);
|
||||
|
||||
if (vScreen->blitter == (void *) -1)
|
||||
return DXL_INVALID_BLIT;
|
||||
}
|
||||
|
||||
if (vScreen) /* if there is a vScreen, blit to it */
|
||||
{
|
||||
if (vScreen->addr)
|
||||
{
|
||||
int pSize;
|
||||
int w,h;
|
||||
unsigned char *ptrScrn;
|
||||
int thisPitch = vScreen->pitch;
|
||||
unsigned int duration;
|
||||
unsigned int starttsc,endtsc;
|
||||
|
||||
/* get a frame pointer to the scaled and postprocessed reconstructed buffer */
|
||||
VP5_GetYUVConfig(pbi, (YUV_BUFFER_CONFIG *) FrameBuffer);
|
||||
|
||||
pSize = DXL_GetVScreenSizeOfPixel(vScreen);
|
||||
|
||||
/* remember to offset if requested */
|
||||
y += vScreen->viewY;
|
||||
x += vScreen->viewX ;
|
||||
|
||||
/* for planar destinations */
|
||||
w = vScreen->viewW;//pitch;
|
||||
h = vScreen->height;
|
||||
|
||||
if(w != FrameBuffer->YWidth)
|
||||
{
|
||||
FrameBuffer->YWidth = w;
|
||||
FrameBuffer->UVWidth = (w+1)/2;
|
||||
}
|
||||
if(h != FrameBuffer->YHeight)
|
||||
{
|
||||
FrameBuffer->YHeight = h;
|
||||
FrameBuffer->UVHeight = (h+1)/2;
|
||||
}
|
||||
ptrScrn = vScreen->addr;
|
||||
ptrScrn += (x * pSize) + (y * thisPitch);
|
||||
|
||||
/* setup ptrs so we can work backwards through Paul's frame buffers */
|
||||
FrameBuffer->YBuffer = FrameBuffer->YBuffer +
|
||||
((FrameBuffer->YHeight - 1) *
|
||||
(FrameBuffer->YStride));
|
||||
|
||||
FrameBuffer->UBuffer = FrameBuffer->UBuffer +
|
||||
((FrameBuffer->UVHeight - 1) *
|
||||
(FrameBuffer->UVStride));
|
||||
|
||||
FrameBuffer->VBuffer = FrameBuffer->VBuffer +
|
||||
((FrameBuffer->UVHeight - 1) *
|
||||
(FrameBuffer->UVStride));
|
||||
|
||||
|
||||
if((vScreen->bd != DXYUY2) && (vScreen->bd != DXYV12))
|
||||
{
|
||||
if(vScreen->bq == DXBLIT_STRETCH)
|
||||
{
|
||||
thisPitch *= 2;
|
||||
}
|
||||
}
|
||||
|
||||
if(vScreen->bd == DXYV12||vScreen->bd == DXI420)
|
||||
{
|
||||
if(thisPitch < 0)
|
||||
{
|
||||
FrameBuffer->uvStart = (char *) (ptrScrn + abs(thisPitch) + abs(thisPitch) * h/4 + thisPitch/2 );
|
||||
FrameBuffer->uvDstArea = abs((thisPitch * h)/4);
|
||||
FrameBuffer->uvUsedArea = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
FrameBuffer->uvStart = (char *) (ptrScrn + (thisPitch * h));
|
||||
FrameBuffer->uvDstArea = (((thisPitch+1)/2) * (( h+1)/2));
|
||||
FrameBuffer->uvUsedArea = (((thisPitch+1)/2) * FrameBuffer->UVHeight);
|
||||
}
|
||||
|
||||
// Temporary fix for Scott Kludge Kludge Kludge !!!!!!!!!
|
||||
// ptrScrn -= thisPitch; // fixes a bug in assembly code for some reason the buttnutt is adding pitch to Y buffer
|
||||
}
|
||||
|
||||
/* if a blitter hasn't been set up set one up ! */
|
||||
if (vScreen->blitSetup != (void *)-1)
|
||||
((vp5_VSCREEN_FUNC)vScreen->blitSetup)();
|
||||
|
||||
/* if its still not set up return that it failed */
|
||||
if ((vp5BLIT_FUNC)vScreen->blitter == (vp5BLIT_FUNC)-1)
|
||||
return DXL_INVALID_BLIT;
|
||||
|
||||
/* blit the screen */
|
||||
|
||||
VP5_readTSC(&starttsc);
|
||||
if(pbi->Configuration.Interlaced==1 && (vScreen->bd != DXYV12 && vScreen->bd != DXI420))
|
||||
{
|
||||
int ypitch = FrameBuffer->YStride;
|
||||
int uvpitch = FrameBuffer->UVStride;
|
||||
|
||||
FrameBuffer->YStride <<= 1;
|
||||
FrameBuffer->YHeight >>= 1;
|
||||
FrameBuffer->UVStride <<= 1;
|
||||
FrameBuffer->UVHeight >>= 1;
|
||||
|
||||
ptrScrn+=thisPitch;
|
||||
FrameBuffer->YBuffer -= ypitch;
|
||||
FrameBuffer->UBuffer -= uvpitch;
|
||||
FrameBuffer->VBuffer -= uvpitch;
|
||||
((vp5BLIT_FUNC)vScreen->blitter)(ptrScrn, thisPitch*2, (YUV_BUFFER_CONFIG *)(FrameBuffer));
|
||||
|
||||
ptrScrn-=thisPitch;
|
||||
FrameBuffer->YBuffer += ypitch;
|
||||
FrameBuffer->UBuffer += uvpitch;
|
||||
FrameBuffer->VBuffer += uvpitch;
|
||||
((vp5BLIT_FUNC)vScreen->blitter)(ptrScrn, thisPitch*2, (YUV_BUFFER_CONFIG *)(FrameBuffer));
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
((vp5BLIT_FUNC)vScreen->blitter)(ptrScrn, thisPitch, (YUV_BUFFER_CONFIG *)(FrameBuffer));
|
||||
}
|
||||
VP5_readTSC(&endtsc);
|
||||
|
||||
duration = ( endtsc - starttsc ) / (pbi->ProcessorFrequency) ;
|
||||
if( pbi->avgBlitTime == 0)
|
||||
{
|
||||
pbi->avgBlitTime = duration;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
pbi->avgBlitTime = (7*pbi->avgBlitTime + duration)>>3;
|
||||
}
|
||||
|
||||
/* blitter cleanup ?*/
|
||||
if ((vp5BLIT_FUNC)vScreen->blitExit != (vp5BLIT_FUNC)-1)
|
||||
((vp5_VSCREEN_FUNC)vScreen->blitExit)();
|
||||
|
||||
}
|
||||
}
|
||||
return DXL_OK;
|
||||
}
|
||||
|
||||
|
||||
static int vp50_decompress(vp50_XIMAGE_HANDLE src, DXL_VSCREEN_HANDLE vScreen)
|
||||
{
|
||||
|
||||
// if we have a compressed frame decompress it ( otherwise we'll just redo
|
||||
// the scaling and postprocessing from the last frame )
|
||||
if (src->addr)
|
||||
{
|
||||
|
||||
if( src->fSize != 0 && (src->addr[0]>=1 || src->addr[1]>=1 || src->addr[2] >=1))
|
||||
{
|
||||
// decode the frame
|
||||
int retVal= VP5_DecodeFrameToYUV(
|
||||
src->myPBI,
|
||||
(char *)src->addr,
|
||||
src->fSize,
|
||||
src->imWidth,
|
||||
src->imHeight);
|
||||
|
||||
if(retVal != 0 )
|
||||
{
|
||||
if(retVal == -1)
|
||||
return DXL_VERSION_CONFLICT;
|
||||
else
|
||||
return DXL_BAD_DATA;
|
||||
}
|
||||
}
|
||||
}
|
||||
VP5_GetYUVConfig(src->myPBI, (YUV_BUFFER_CONFIG *) &src->FrameBuffer);
|
||||
return DXL_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
close down a decompressor, releasing the wilk decompressor,
|
||||
the xImage (decompressor), and the intermediate vScreen (surface)
|
||||
*/
|
||||
|
||||
static int vp50_xImageDestroy(vp50_XIMAGE_HANDLE xThis)
|
||||
{
|
||||
if (xThis)
|
||||
{
|
||||
if(xThis->owned)
|
||||
VP5_StopDecoder(&(xThis->myPBI));
|
||||
duck_free(xThis);
|
||||
}
|
||||
|
||||
return DXL_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
called during initialization and/or when xImage (decompressor)
|
||||
attributes change, note that nImage and src are actually
|
||||
synonymous and should be cleared out a bit (to say the least!)
|
||||
|
||||
|
||||
!!!!!!
|
||||
This function should be prepared to get data that is NOT of the
|
||||
type native to the decoder, It should do it's best to verify it
|
||||
as valid data and should clean up after itself and return NULL
|
||||
if it doesn't recognize the format of the data
|
||||
*/
|
||||
static DXL_XIMAGE_HANDLE vp50_xImageCreate(unsigned char *data);
|
||||
static DXL_XIMAGE_HANDLE vp50_xImageReCreate(vp50_XIMAGE_HANDLE src,unsigned char *data,
|
||||
int type,enum BITDEPTH bitDepth,int w,int h)
|
||||
{
|
||||
(void) bitDepth;
|
||||
if (type != VP50_FOURCC)
|
||||
return NULL;
|
||||
|
||||
if (src != NULL) /* if an xImage/decompressor already exists, destroy it */
|
||||
vp50_xImageDestroy(src);
|
||||
|
||||
/* create a new xImage, specific to this type of decoder,
|
||||
(see "vp50_XIMAGE" struct above and dxl_main.h) */
|
||||
|
||||
src = (vp50_XIMAGE_HANDLE)duck_calloc(1,sizeof(vp50_XIMAGE),DMEM_GENERAL);
|
||||
|
||||
if (!src)
|
||||
return NULL;
|
||||
|
||||
// duck_memset(nImage,0,sizeof(vp50_XIMAGE));
|
||||
|
||||
/* set up the "vtable" of interface calls */
|
||||
src->create = (DXL_XIMAGE_HANDLE (*)(void *)) vp50_xImageCreate;
|
||||
src->recreate = (DXL_XIMAGE_HANDLE (*)(DXL_XIMAGE_HANDLE,void *,int,int,int,int)) vp50_xImageReCreate;
|
||||
|
||||
src->destroy = (int (*)(DXL_XIMAGE_HANDLE))vp50_xImageDestroy;
|
||||
src->dx = (int (*)(DXL_XIMAGE_HANDLE, DXL_VSCREEN_HANDLE)) vp50_decompress;
|
||||
src->blit = NULL; /* there is no interleaved blitter for vp5x files */
|
||||
src->setParameter = vp50_SetParameter;
|
||||
|
||||
#if !KLUDGE_FOR_NEIL
|
||||
src->internalFormat = (int (*)(DXL_XIMAGE_HANDLE, DXL_VSCREEN_HANDLE)) vp50_GetXImageInternalFormat;
|
||||
#endif
|
||||
src->bdPrefs = bitDepths; /* plug in the list of prefered bit depths */
|
||||
|
||||
src->addr = data;
|
||||
src->dkFlags.inUse = 1;
|
||||
|
||||
src->imWidth = src->w = (short) (w ? w : 320);
|
||||
src->imHeight = src->h = (short) (h ? h : 240);
|
||||
|
||||
src->myFourCC = VP50_FOURCC;
|
||||
|
||||
/* create new PBI */
|
||||
if(!VP5_StartDecoder( &(src->myPBI), src->imWidth, src->imHeight ))
|
||||
{
|
||||
vp50_xImageDestroy(src);
|
||||
src = NULL;
|
||||
}
|
||||
src->owned = 1;
|
||||
|
||||
return (DXL_XIMAGE_HANDLE ) src;
|
||||
}
|
||||
|
||||
/* in this "glue" case, just calls through to the create function */
|
||||
|
||||
static DXL_XIMAGE_HANDLE vp50_xImageCreate(unsigned char *data)
|
||||
{
|
||||
return vp50_xImageReCreate(NULL, data, VP50_FOURCC, (enum BITDEPTH ) 0,0,0);
|
||||
}
|
||||
|
||||
int vp50_Init(void)
|
||||
{
|
||||
|
||||
DXL_RegisterXImage(
|
||||
(DXL_XIMAGE_HANDLE (*)(unsigned char *)) vp50_xImageCreate,
|
||||
VP50_FOURCC,
|
||||
YV12
|
||||
);
|
||||
|
||||
|
||||
/* initialize all the global variables */
|
||||
VP5_VPInitLibrary();
|
||||
|
||||
return DXL_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
main exit routine, called during DXL_ExitVideo()
|
||||
clean up any global information if necessary
|
||||
*/
|
||||
|
||||
int vp50_Exit(void)
|
||||
{
|
||||
VP5_VPDeInitLibrary();
|
||||
|
||||
return DXL_OK;
|
||||
}
|
||||
|
||||
void vp50_SetParameter(DXL_XIMAGE_HANDLE src,int Command, unsigned long Parameter )
|
||||
{
|
||||
if(Command == PBC_SET_PBSTRUCT)
|
||||
{
|
||||
|
||||
if(((vp50_XIMAGE_HANDLE) src)->owned)
|
||||
VP5_StopDecoder(&(((vp50_XIMAGE_HANDLE) src)->myPBI));
|
||||
|
||||
((vp50_XIMAGE_HANDLE) src)->owned = 0;
|
||||
((vp50_XIMAGE_HANDLE) src)->myPBI= (PB_INSTANCE *) Parameter;
|
||||
|
||||
}
|
||||
else
|
||||
VP5_SetPbParam( ((vp50_XIMAGE_HANDLE) src)->myPBI, (PB_COMMAND_TYPE) Command, (UINT32) Parameter );
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
unsigned char* baseAddr;
|
||||
long rowBytes;
|
||||
} YV12_PLANE;
|
||||
|
||||
typedef struct {
|
||||
YV12_PLANE y;
|
||||
YV12_PLANE u;
|
||||
YV12_PLANE v;
|
||||
} YV12_PLANES;
|
||||
|
||||
void GetImageBufs(DXL_XIMAGE_HANDLE x, YV12_PLANES *p)
|
||||
{
|
||||
vp50_XIMAGE_HANDLE xim=(vp50_XIMAGE_HANDLE)x;
|
||||
p->y.baseAddr=(unsigned char *)xim->FrameBuffer.YBuffer;
|
||||
p->u.baseAddr=(unsigned char *)xim->FrameBuffer.UBuffer;
|
||||
p->v.baseAddr=(unsigned char *)xim->FrameBuffer.VBuffer;
|
||||
p->y.rowBytes=xim->FrameBuffer.YStride;
|
||||
p->u.rowBytes=xim->FrameBuffer.UVStride;
|
||||
p->v.rowBytes=xim->FrameBuffer.UVStride;
|
||||
}
|
||||
Reference in New Issue
Block a user