📄 quant.c
字号:
/******************************************************************** * * * THIS FILE IS PART OF THE OggTheora SOFTWARE CODEC SOURCE CODE. * * USE, DISTRIBUTION AND REPRODUCTION OF THIS LIBRARY SOURCE IS * * GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE * * IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. * * * * THE Theora SOURCE CODE IS COPYRIGHT (C) 2002-2005 * * by the Xiph.Org Foundation http://www.xiph.org/ * * * ******************************************************************** function: last mod: $Id: quant.c 11442 2006-05-27 17:28:08Z giles $ ********************************************************************/#include <stdlib.h>#include <string.h>#include "codec_internal.h"#include "quant_lookup.h"/* the *V1 tables are the originals used by the VP3 codec */static const ogg_uint32_t QThreshTableV1[Q_TABLE_SIZE] = { 500, 450, 400, 370, 340, 310, 285, 265, 245, 225, 210, 195, 185, 180, 170, 160, 150, 145, 135, 130, 125, 115, 110, 107, 100, 96, 93, 89, 85, 82, 75, 74, 70, 68, 64, 60, 57, 56, 52, 50, 49, 45, 44, 43, 40, 38, 37, 35, 33, 32, 30, 29, 28, 25, 24, 22, 21, 19, 18, 17, 15, 13, 12, 10};static const Q_LIST_ENTRY DcScaleFactorTableV1[ Q_TABLE_SIZE ] = { 220, 200, 190, 180, 170, 170, 160, 160, 150, 150, 140, 140, 130, 130, 120, 120, 110, 110, 100, 100, 90, 90, 90, 80, 80, 80, 70, 70, 70, 60, 60, 60, 60, 50, 50, 50, 50, 40, 40, 40, 40, 40, 30, 30, 30, 30, 30, 30, 30, 20, 20, 20, 20, 20, 20, 20, 20, 10, 10, 10, 10, 10, 10, 10};/* dbm -- defined some alternative tables to test header packing */#define NEW_QTABLES 0#if NEW_QTABLESstatic const Q_LIST_ENTRY Y_coeffsV1[64] ={ 8, 16, 16, 16, 20, 20, 20, 20, 16, 16, 16, 16, 20, 20, 20, 20, 16, 16, 16, 16, 22, 22, 22, 22, 16, 16, 16, 16, 22, 22, 22, 22, 20, 20, 22, 22, 24, 24, 24, 24, 20, 20, 22, 22, 24, 24, 24, 24, 20, 20, 22, 22, 24, 24, 24, 24, 20, 20, 22, 22, 24, 24, 24, 24};static const Q_LIST_ENTRY UV_coeffsV1[64] ={ 17, 18, 24, 47, 99, 99, 99, 99, 18, 21, 26, 66, 99, 99, 99, 99, 24, 26, 56, 99, 99, 99, 99, 99, 47, 66, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99};static const Q_LIST_ENTRY Inter_coeffsV1[64] ={ 12, 16, 16, 16, 20, 20, 20, 20, 16, 16, 16, 16, 20, 20, 20, 20, 16, 16, 16, 16, 22, 22, 22, 22, 16, 16, 16, 16, 22, 22, 22, 22, 20, 20, 22, 22, 24, 24, 24, 24, 20, 20, 22, 22, 24, 24, 24, 24, 20, 20, 22, 22, 24, 24, 24, 24, 20, 20, 22, 22, 24, 24, 24, 24};#else /* these are the old VP3 values: */static const Q_LIST_ENTRY Y_coeffsV1[64] ={ 16, 11, 10, 16, 24, 40, 51, 61, 12, 12, 14, 19, 26, 58, 60, 55, 14, 13, 16, 24, 40, 57, 69, 56, 14, 17, 22, 29, 51, 87, 80, 62, 18, 22, 37, 58, 68, 109, 103, 77, 24, 35, 55, 64, 81, 104, 113, 92, 49, 64, 78, 87, 103, 121, 120, 101, 72, 92, 95, 98, 112, 100, 103, 99};static const Q_LIST_ENTRY UV_coeffsV1[64] ={ 17, 18, 24, 47, 99, 99, 99, 99, 18, 21, 26, 66, 99, 99, 99, 99, 24, 26, 56, 99, 99, 99, 99, 99, 47, 66, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99, 99};static const Q_LIST_ENTRY Inter_coeffsV1[64] ={ 16, 16, 16, 20, 24, 28, 32, 40, 16, 16, 20, 24, 28, 32, 40, 48, 16, 20, 24, 28, 32, 40, 48, 64, 20, 24, 28, 32, 40, 48, 64, 64, 24, 28, 32, 40, 48, 64, 64, 64, 28, 32, 40, 48, 64, 64, 64, 96, 32, 40, 48, 64, 64, 64, 96, 128, 40, 48, 64, 64, 64, 96, 128, 128};#endifstatic int _ilog(unsigned int v){ int ret=0; while(v){ ret++; v>>=1; } return(ret);}void WriteQTables(PB_INSTANCE *pbi,oggpack_buffer* opb) { int x, bits; bits=10; oggpackB_write(opb, bits-1, 4); for(x=0; x<64; x++) { oggpackB_write(opb, pbi->QThreshTable[x],bits); } oggpackB_write(opb, bits-1, 4); for(x=0; x<64; x++) { oggpackB_write(opb, pbi->DcScaleFactorTable[x],bits); } oggpackB_write(opb, 3 - 1, 9); /* number of base matricies */ for(x=0; x<64; x++) { oggpackB_write(opb, pbi->Y_coeffs[x],8); } for(x=0; x<64; x++) { oggpackB_write(opb, pbi->U_coeffs[x],8); } for(x=0; x<64; x++) { oggpackB_write(opb, pbi->InterY_coeffs[x],8); } /* table mapping */ oggpackB_write(opb, 0, 2); /* matrix 0 for intra Y */ oggpackB_write(opb, 62, 6); /* used for every q */ oggpackB_write(opb, 0, 2); oggpackB_write(opb, 1, 1); /* next range is explicit */ oggpackB_write(opb, 1, 2); /* matrix 1 for intra U */ oggpackB_write(opb, 62, 6); oggpackB_write(opb, 1, 2); oggpackB_write(opb, 0, 1); /* intra V is the same */ oggpackB_write(opb, 1, 1); /* next range is explicit */ oggpackB_write(opb, 2, 2); /* matrix 2 for inter Y */ oggpackB_write(opb, 62, 6); oggpackB_write(opb, 2, 2); oggpackB_write(opb, 0, 2); /* inter U the same */ oggpackB_write(opb, 0, 2); /* inter V the same */}static int _read_qtable_range(codec_setup_info *ci, oggpack_buffer* opb, int N, int type) { int index, range; int qi = 0; int count = 0; qmat_range_table table[65]; theora_read(opb,_ilog(N-1),&index); /* qi=0 index */ table[count].startqi = 0; table[count++].qmat = ci->qmats + index * Q_TABLE_SIZE; while(qi<63) { theora_read(opb,_ilog(62-qi),&range); /* range to next code q matrix */ range++; if(range<=0) return OC_BADHEADER; qi+=range; theora_read(opb,_ilog(N-1),&index); /* next index */ table[count].startqi = qi; table[count++].qmat = ci->qmats + index * Q_TABLE_SIZE; } ci->range_table[type] = _ogg_malloc(count * sizeof(qmat_range_table)); if (ci->range_table[type] != NULL) { memcpy(ci->range_table[type], table, count * sizeof(qmat_range_table)); return 0; } return OC_FAULT; /* allocation failed */}int ReadQTables(codec_setup_info *ci, oggpack_buffer* opb) { long bits,value; int x,y, N; /* AC scale table */ theora_read(opb,4,&bits); bits++; for(x=0; x<Q_TABLE_SIZE; x++) { theora_read(opb,bits,&value); if(bits<0)return OC_BADHEADER; ci->QThreshTable[x]=value; } /* DC scale table */ theora_read(opb,4,&bits); bits++; for(x=0; x<Q_TABLE_SIZE; x++) { theora_read(opb,bits,&value); if(bits<0)return OC_BADHEADER; ci->DcScaleFactorTable[x]=(Q_LIST_ENTRY)value; } /* base matricies */ theora_read(opb,9,&N); N++; ci->qmats=_ogg_malloc(N*64*sizeof(Q_LIST_ENTRY)); ci->MaxQMatrixIndex = N; for(y=0; y<N; y++) { for(x=0; x<64; x++) { theora_read(opb,8,&value); if(bits<0)return OC_BADHEADER; ci->qmats[(y<<6)+x]=(Q_LIST_ENTRY)value; } } /* table mapping */ for(x=0; x<6; x++) { ci->range_table[x] = NULL; } { int flag, ret; /* intra Y */ if((ret=_read_qtable_range(ci,opb,N,0))<0) return ret; /* intra U */ theora_read(opb,1,&flag); if(flag<0) return OC_BADHEADER; if(flag) { /* explicitly coded */ if((ret=_read_qtable_range(ci,opb,N,1))<0) return ret; } else { /* same as previous */ } /* intra V */ theora_read(opb,1,&flag); if(flag<0) return OC_BADHEADER; if(flag) { /* explicitly coded */ if((ret=_read_qtable_range(ci,opb,N,2))<0) return ret; } else { /* same as previous */ } /* inter Y */ theora_read(opb,1,&flag); if(flag<0) return OC_BADHEADER; if(flag) { /* explicitly coded */ if((ret=_read_qtable_range(ci,opb,N,3))<0) return ret; } else { theora_read(opb,1,&flag); if(flag<0) return OC_BADHEADER; if(flag) { /* same as corresponding intra */ } else { /* same as previous */ } } /* inter U */ theora_read(opb,1,&flag); if(flag<0) return OC_BADHEADER; if(flag) { /* explicitly coded */ if((ret=_read_qtable_range(ci,opb,N,4))<0) return ret; } else { theora_read(opb,1,&flag); if(flag<0) return OC_BADHEADER; if(flag) { /* same as corresponding intra */ } else { /* same as previous */ } } /* inter V */ theora_read(opb,1,&flag); if(flag<0) return OC_BADHEADER; if(flag) { /* explicitly coded */ if((ret=_read_qtable_range(ci,opb,N,5))<0) return ret; } else { theora_read(opb,1,&flag);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -