📄 main.c
字号:
/*!
************************************************************************
*
*
* The library contain AVC H.264 baseline codec,which can process video
* less than 12 minutes.
*
* (C) Copyright 2007 by Tonald DL
* All rights reserved
*
* Date: 2007-08-11
* Version: 070811A
* Contact Personal: Tonald DL
* Email: dhcodec@hotmail.com
*
************************************************************************
*/
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <assert.h>
#ifdef _WIN32
#if (_MSC_VER >= 900 )
#define WIN32_LEAN_AND_MEAN 1
#define INC_OLE2
#define NOSERVICE
#endif
#include <windows.h>
#include <stdio.h>
#endif
#include "..\common\S264_SYNTAX.h"
#include "sd_pci64.h"
#define SQUARE(x) (((int)(x))*((int)(x)))
/*!
************************************************************************
*
*
*
************************************************************************
*/
void WaitToken_S264(PCI64_HANDLE* pPCI_DM6437,S264_PCI_SYNTAX* pS264_PCI_SYNTAX)
{
int TokenOwner;
INT32 Error;
do{
Sleep(10);
Error = PCI64_MemRead32(*pPCI_DM6437,
S264_PCI_SYNTAX_ADDR_BASE,
(sizeof(S264_PCI_SYNTAX)>>2),
(UINT32*)pS264_PCI_SYNTAX);
assert(!Error);
TokenOwner=pS264_PCI_SYNTAX->TokenOwner;
}while(TokenOwner!=S264_PCI_OWNER_PC);
}
/*!
************************************************************************
*
*
*
************************************************************************
*/
void PassToken_S264(PCI64_HANDLE* pPCI_DM6437,S264_PCI_SYNTAX* pS264_PCI_SYNTAX)
{
INT32 Error;
pS264_PCI_SYNTAX->TokenOwner=S264_PCI_OWNER_DM6437;
Error = PCI64_MemWrite32(*pPCI_DM6437,
S264_PCI_SYNTAX_ADDR_BASE,
(sizeof(S264_PCI_SYNTAX)>>2),
(UINT32*)pS264_PCI_SYNTAX);
assert(!Error);
}
/*!
************************************************************************
*
*
*
************************************************************************
*/
void WriteCMD_S264(PCI64_HANDLE* pPCI_DM6437,S264_PCI_SYNTAX* pS264_PCI_SYNTAX)
{
INT32 Error;
Error = PCI64_MemWrite32(*pPCI_DM6437,
S264_PCI_DATA_ADDR_BASE,
(pS264_PCI_SYNTAX->BufWordLen),
(UINT32*)pS264_PCI_SYNTAX->BufAddr);
assert(!Error);
Error = PCI64_MemWrite32(*pPCI_DM6437,
S264_PCI_SYNTAX_ADDR_BASE,
(sizeof(S264_PCI_SYNTAX)>>2),
(UINT32*)pS264_PCI_SYNTAX);
assert(!Error);
}
/*!
************************************************************************
*
*
*
************************************************************************
*/
void ReadCMD_S264(PCI64_HANDLE* pPCI_DM6437,S264_PCI_SYNTAX* pS264_PCI_SYNTAX)
{
INT32 Error;
Error=PCI64_MemRead32(*pPCI_DM6437,
S264_PCI_DATA_ADDR_BASE,
(pS264_PCI_SYNTAX->BufWordLen),
(UINT32*)pS264_PCI_SYNTAX->BufAddr);
assert(!Error);
}
/*!
************************************************************************
*
*
*
************************************************************************
*/
void main(int argc, char **argv)
{
PCI64_HANDLE PCI_DM6437;
INT32 Error;
S264_PCI_SYNTAX SYNTAX_DM6437;
ENCFRAME_PROP ENCINPUT;
char *filein_path,*fileout_path,*fileout_rec;
FILE *file_in,*file_264,*file_rec;
unsigned char *porg,*prec_dm6437,*pstream_dm6437;
byte *paddr_src,*paddr_dst;
int i,k,framesize,ysize,uvsize,framenum1,framenum2,bytenum,OperationCode;
int ENC_TIMER,TOTAL_BITS,DSPMIPS,DSPBITLEN;
int FRAME2RUN;
int diff_y,diff_u,diff_v;
float snr_y,snr_u,snr_v,snr_ya,snr_ua,snr_va,mips_f,mips_a;
file_in=NULL;
file_264=NULL;
file_rec=NULL;
porg=NULL;
prec_dm6437=NULL;
pstream_dm6437=NULL;
PCI_DM6437=NULL;
snr_ya=0;
snr_ua=0;
snr_va=0;
mips_a=0;
if(argc==9)
{
i=1;
filein_path=argv[i++];
fileout_path=argv[i++];
fileout_rec=argv[i++];
FRAME2RUN=atoi(argv[i++]);
ENCINPUT.VideoQuality=atoi(argv[i++]);
ENCINPUT.IntraPeriod=atoi(argv[i++]);
ENCINPUT.ImageWidth=atoi(argv[i++]);
ENCINPUT.ImageHeight=atoi(argv[i++]);
//generate new stream, set it to NEW_SEQ;
ENCINPUT.FrameType=NEW_SEQ;
//calculate the Y and UV component size. Also calculate the whole frame size.
ysize=ENCINPUT.ImageWidth*ENCINPUT.ImageHeight;
uvsize=ysize>>2;
framesize=ysize*3/2;
//open the YUV420 file.
file_in=fopen(filein_path,"rb");
if(file_in==NULL)
{
printf("input file path error!\n");
goto EXIT_MAIN;
}
//open the output 264 file.
file_264=fopen(fileout_path,"wb");
if(file_264==NULL)
{
printf("out file path error!\n");
goto EXIT_MAIN;
}
//open the output yuv file.
file_rec=fopen(fileout_rec,"wb");
if(file_rec==NULL)
{
printf("out file path error!\n");
goto EXIT_MAIN;
}
porg=malloc(framesize);
prec_dm6437=malloc(framesize);
pstream_dm6437=malloc(framesize);
//confirm DM6437 is opened.
printf("Open PCI DM6437...\n");
do{
Sleep(50);
Error = PCI64_Open( 0, &PCI_DM6437 );
}while(Error);
//Setup encoder parameters
printf("Setup PCI DM6437 Codec...\n");
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_PARA;
SYNTAX_DM6437.BufAddr=(void*)&ENCINPUT;
SYNTAX_DM6437.BufWordLen=(sizeof(ENCINPUT)>>2);
WriteCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
////////////////////////////////////////////////////////////////////////////////////////
//ENC frame
////////////////////////////////////////////////////////////////////////////////////////
printf("\n-----------------------------------------------------------------------\n");
printf( " Image format : %dx%d\n",ENCINPUT.ImageWidth,ENCINPUT.ImageHeight);
printf(" QP. : %d \n" ,ENCINPUT.VideoQuality);
printf(" File Name. : %s\n",filein_path);
printf(" Frame Number. : %d\n",FRAME2RUN);
printf(" InterPeriod. : %d\n",ENCINPUT.IntraPeriod);
printf("-----------------------------------------------------------------------\n");
ENC_TIMER=0;
TOTAL_BITS=0;
//also compute the encoder speed
for(framenum1=0;framenum1<FRAME2RUN;framenum1++)
{
//get one frame pixels into buffer porg
bytenum=fread(porg,1,framesize,file_in);
if(bytenum!=framesize)
{
printf("Error While Read File !\n");
goto EXIT_MAIN;
}
//pass data to DSP Internal Memory
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_YUV420_IN_START;
SYNTAX_DM6437.BufAddr=NULL;
SYNTAX_DM6437.BufWordLen=0;
WriteCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
bytenum=framesize;
paddr_src=porg;
do{
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
if(bytenum>=S264_PCI_DATA_BYTE_LEN)
{
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_YUV420_IN_PROC;
SYNTAX_DM6437.BufAddr=(void*)paddr_src;
SYNTAX_DM6437.BufWordLen=S264_PCI_DATA_WORD_LEN;
bytenum-=(SYNTAX_DM6437.BufWordLen<<2);
paddr_src+=(SYNTAX_DM6437.BufWordLen<<2);
}
else
{
assert((bytenum&0x3)==0);
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_YUV420_IN_PROC;
SYNTAX_DM6437.BufAddr=(void*)paddr_src;
SYNTAX_DM6437.BufWordLen=(bytenum>>2);
bytenum-=(SYNTAX_DM6437.BufWordLen<<2);
paddr_src+=(SYNTAX_DM6437.BufWordLen<<2);
}
assert(SYNTAX_DM6437.BufWordLen<=S264_PCI_DATA_WORD_LEN);
WriteCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
}while(bytenum>0);
//pass data to DSP Internal Memory
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_YUV420_IN_END;
SYNTAX_DM6437.BufAddr=NULL;
SYNTAX_DM6437.BufWordLen=0;
WriteCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
//Get YUV420 Data from DSP
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_YUV420_OUT_START;
SYNTAX_DM6437.BufAddr=NULL;
SYNTAX_DM6437.BufWordLen=0;
WriteCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
paddr_dst=prec_dm6437;
do{
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
OperationCode=SYNTAX_DM6437.OpCode;
SYNTAX_DM6437.BufAddr=paddr_dst;
paddr_dst+=(SYNTAX_DM6437.BufWordLen<<2);
if(OperationCode!=S264_PCI_OP_ENC_YUV420_OUT_END)
ReadCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
}while(OperationCode!=S264_PCI_OP_ENC_YUV420_OUT_END);
//Get Bits Data from DSP
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_BITS_OUT_START;
SYNTAX_DM6437.BufAddr=NULL;
SYNTAX_DM6437.BufWordLen=0;
WriteCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.BufAddr=&DSPBITLEN;
SYNTAX_DM6437.BufWordLen=1;
ReadCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
paddr_dst=pstream_dm6437;
do{
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
OperationCode=SYNTAX_DM6437.OpCode;
SYNTAX_DM6437.BufAddr=paddr_dst;
paddr_dst+=(SYNTAX_DM6437.BufWordLen<<2);
SYNTAX_DM6437.BufWordLen;
if(OperationCode!=S264_PCI_OP_ENC_BITS_OUT_END)
ReadCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
}while(OperationCode!=S264_PCI_OP_ENC_BITS_OUT_END);
//Get MIPS from DSP
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_MIPS_OUT;
SYNTAX_DM6437.BufAddr=NULL;
SYNTAX_DM6437.BufWordLen=0;
WriteCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.BufAddr=&DSPMIPS;
SYNTAX_DM6437.BufWordLen=1;
ReadCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
////////////////////////////////////////////////////////////////////////////////////////
//Get PSNR
////////////////////////////////////////////////////////////////////////////////////////
diff_y = 0;
diff_u= 0;
diff_v= 0;
k=0;
for(i=0;i<ysize;i++,k++)
diff_y+= SQUARE(porg[k] - prec_dm6437[k]);
for(i=0;i<uvsize;i++,k++)
diff_u += SQUARE(porg[k] - prec_dm6437[k]);
for(i=0;i<uvsize;i++,k++)
diff_v += SQUARE(porg[k] - prec_dm6437[k]);
snr_y=(float)(10*log10(65025*(double)((double)ysize/diff_y)));
snr_u=(float)(10*log10(65025*(double)((double)uvsize/diff_u)));
snr_v=(float)(10*log10(65025*(double)((double)uvsize/diff_v)));
snr_ya+=snr_y;
snr_ua+=snr_u;
snr_va+=snr_v;
////////////////////////////////////////////////////////////////////////////////////////
//End PSNR
////////////////////////////////////////////////////////////////////////////////////////
//calculate the bits length
TOTAL_BITS+=DSPBITLEN*8;
//calculate the mips
mips_f=((double)DSPMIPS*65536.0/1000000.0)+1;
mips_a+=mips_f;
printf("[%4d] [%10d] [%4d] [%2.3f]\n",framenum1,DSPBITLEN*8,(int)mips_f,snr_y);
//write the bits to 264 file.
fwrite(pstream_dm6437,1,DSPBITLEN,file_264);
fwrite(prec_dm6437,1,framesize,file_rec);
};
EXIT_MAIN:
printf("\n-----------------------------------------------------------------------\n");
printf(" Image format : %dx%d\n",ENCINPUT.ImageWidth,ENCINPUT.ImageHeight);
printf(" QP : %d\n" ,ENCINPUT.VideoQuality);
printf(" Bit rate at 30fps (kbit/s) : %5.2f\n",((float)TOTAL_BITS*30.0*0.001)/((float) framenum1));
printf(" Average Speed(mips/frame) : %2.3f\n",mips_a/((float) framenum1));
printf(" Average Y PSNR : %2.3f\n",snr_ya/((float) framenum1));
printf("-----------------------------------------------------------------------\n");
if(file_in)
fclose(file_in);
if(file_264)
fclose(file_264);
if(file_rec)
fclose(file_rec);
if(prec_dm6437)
free(prec_dm6437);
if(pstream_dm6437)
free(pstream_dm6437);
//Clean Up DSP, make it wait for next video
WaitToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
SYNTAX_DM6437.OpCode=S264_PCI_OP_ENC_CLEANUP;
SYNTAX_DM6437.BufAddr=NULL;
SYNTAX_DM6437.BufWordLen=0;
WriteCMD_S264(&PCI_DM6437,&SYNTAX_DM6437);
PassToken_S264(&PCI_DM6437,&SYNTAX_DM6437);
//close DM6437 handler
printf("Close PCI DM6437...\n");
if(PCI_DM6437)
PCI64_Close( PCI_DM6437 );
}
else
{
printf("Encode:\n");
printf("S264 foreman_cif300.yuv foreman.264 foreman_rec.yuv Test.log 30 28 30 3 352 288\n");
exit(-1);
}
return;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -