@ -24,6 +24,12 @@
# include "avcodec.h"
typedef struct RawVideoContext {
unsigned char * buffer ; /* block of memory for holding one frame */
unsigned char * p ; /* current position in buffer */
int length ; /* number of bytes in buffer */
AVFrame pic ; ///< AVCodecContext.coded_frame
} RawVideoContext ;
typedef struct PixleFormatTag {
int pix_fmt ;
@ -31,8 +37,19 @@ typedef struct PixleFormatTag {
} PixelFormatTag ;
const PixelFormatTag pixelFormatTags [ ] = {
{ PIX_FMT_YUV422 , MKTAG ( ' Y ' , ' 4 ' , ' 2 ' , ' 2 ' ) } ,
{ PIX_FMT_YUV420P , MKTAG ( ' I ' , ' 4 ' , ' 2 ' , ' 0 ' ) } ,
{ PIX_FMT_YUV420P , MKTAG ( ' I ' , ' 4 ' , ' 2 ' , ' 0 ' ) } , /* Planar formats */
{ PIX_FMT_YUV420P , MKTAG ( ' I ' , ' Y ' , ' U ' , ' V ' ) } ,
{ PIX_FMT_YUV410P , MKTAG ( ' Y ' , ' U ' , ' V ' , ' 9 ' ) } ,
{ PIX_FMT_YUV411P , MKTAG ( ' Y ' , ' 4 ' , ' 1 ' , ' B ' ) } ,
{ PIX_FMT_YUV422P , MKTAG ( ' Y ' , ' 4 ' , ' 2 ' , ' B ' ) } ,
{ PIX_FMT_GRAY8 , MKTAG ( ' Y ' , ' 8 ' , ' 0 ' , ' 0 ' ) } ,
{ PIX_FMT_GRAY8 , MKTAG ( ' ' , ' ' , ' Y ' , ' 8 ' ) } ,
{ PIX_FMT_YUV422 , MKTAG ( ' Y ' , ' 4 ' , ' 2 ' , ' 2 ' ) } , /* Packed formats */
{ PIX_FMT_YUV422 , MKTAG ( ' U ' , ' Y ' , ' V ' , ' Y ' ) } ,
{ PIX_FMT_GRAY8 , MKTAG ( ' G ' , ' R ' , ' E ' , ' Y ' ) } ,
{ - 1 , 0 } ,
} ;
@ -47,35 +64,37 @@ static int findPixelFormat(unsigned int fourcc)
return PIX_FMT_YUV420P ;
}
static unsigned int findFourCC ( int fmt )
{
const PixelFormatTag * tags = pixelFormatTags ;
while ( tags - > pix_fmt > = 0 ) {
if ( tags - > pix_fmt = = fmt )
return tags - > fourcc ;
tags + + ;
}
return 0 ;
}
typedef struct RawVideoContext {
unsigned char * buffer ; /* block of memory for holding one frame */
unsigned char * p ; /* current position in buffer */
int length ; /* number of bytes in buffer */
AVFrame pic ; ///< AVCodecContext.coded_frame
} RawVideoContext ;
/* RAW Decoder Implementation */
static int raw_init ( AVCodecContext * avctx )
static int raw_init_decoder ( AVCodecContext * avctx )
{
RawVideoContext * context = avctx - > priv_data ;
if ( avctx - > codec_tag ) {
avctx - > pix_fmt = findPixelFormat ( avctx - > codec_tag ) ;
}
context - > length = avpicture_get_size ( avctx - > pix_fmt , avctx - > width , avctx - > height ) ;
context - > buffer = av_malloc ( context - > length ) ;
context - > p = context - > buffer ;
context - > pic . pict_type = FF_I_TYPE ;
context - > pic . key_frame = 1 ;
if ( avctx - > codec_tag )
avctx - > pix_fmt = findPixelFormat ( avctx - > codec_tag ) ;
context - > length = avpicture_get_size ( avctx - > pix_fmt , avctx - > width , avctx - > height ) ;
context - > buffer = av_malloc ( context - > length ) ;
context - > p = context - > buffer ;
context - > pic . pict_type = FF_I_TYPE ;
context - > pic . key_frame = 1 ;
avctx - > coded_frame = & context - > pic ;
if ( ! context - > buffer ) {
if ( ! context - > buffer )
return - 1 ;
}
return 0 ;
}
@ -110,102 +129,48 @@ static int raw_decode(AVCodecContext *avctx,
return bytesNeeded ;
}
static int raw_close ( AVCodecContext * avctx )
static int raw_close_decoder ( AVCodecContext * avctx )
{
RawVideoContext * context = avctx - > priv_data ;
av_freep ( & context - > buffer ) ;
return 0 ;
}
av_freep ( & context - > buffer ) ;
/* RAW Encoder Implementation */
static int raw_init_encoder ( AVCodecContext * avctx )
{
avctx - > coded_frame = ( AVPicture * ) avctx - > priv_data ;
avctx - > coded_frame - > pict_type = FF_I_TYPE ;
avctx - > coded_frame - > key_frame = 1 ;
avctx - > codec_tag = findFourCC ( avctx - > pix_fmt ) ;
return 0 ;
}
static int raw_encode ( AVCodecContext * avctx ,
unsigned char * frame , int buf_size , void * data )
{
AVPicture * picture = data ;
unsigned char * src ;
unsigned char * dest = frame ;
int i , j ;
int w = avctx - > width ;
int h = avctx - > height ;
int size = avpicture_get_size ( avctx - > pix_fmt , w , h ) ;
if ( size > buf_size ) {
return - 1 ;
}
switch ( avctx - > pix_fmt ) {
case PIX_FMT_YUV420P :
for ( i = 0 ; i < 3 ; i + + ) {
if ( i = = 1 ) {
w > > = 1 ;
h > > = 1 ;
}
src = picture - > data [ i ] ;
for ( j = 0 ; j < h ; j + + ) {
memcpy ( dest , src , w ) ;
dest + = w ;
src + = picture - > linesize [ i ] ;
}
}
break ;
case PIX_FMT_YUV422P :
for ( i = 0 ; i < 3 ; i + + ) {
if ( i = = 1 ) {
w > > = 1 ;
}
src = picture - > data [ i ] ;
for ( j = 0 ; j < h ; j + + ) {
memcpy ( dest , src , w ) ;
dest + = w ;
src + = picture - > linesize [ i ] ;
}
}
break ;
case PIX_FMT_YUV444P :
for ( i = 0 ; i < 3 ; i + + ) {
src = picture - > data [ i ] ;
for ( j = 0 ; j < h ; j + + ) {
memcpy ( dest , src , w ) ;
dest + = w ;
src + = picture - > linesize [ i ] ;
}
}
break ;
case PIX_FMT_YUV422 :
src = picture - > data [ 0 ] ;
for ( j = 0 ; j < h ; j + + ) {
memcpy ( dest , src , w * 2 ) ;
dest + = w * 2 ;
src + = picture - > linesize [ 0 ] ;
}
break ;
case PIX_FMT_RGB24 :
case PIX_FMT_BGR24 :
src = picture - > data [ 0 ] ;
for ( j = 0 ; j < h ; j + + ) {
memcpy ( dest , src , w * 3 ) ;
dest + = w * 3 ;
src + = picture - > linesize [ 0 ] ;
}
break ;
default :
return - 1 ;
}
return size ;
return avpicture_layout ( ( AVPicture * ) data , avctx - > pix_fmt , avctx - > width ,
avctx - > height , frame , buf_size ) ;
}
AVCodec rawvideo_encoder = {
" rawvideo " ,
CODEC_TYPE_VIDEO ,
CODEC_ID_RAWVIDEO ,
sizeof ( AVFrame ) ,
raw_init_encoder ,
raw_encode ,
} ;
AVCodec rawvideo_codec = {
AVCodec rawvideo_decoder = {
" rawvideo " ,
CODEC_TYPE_VIDEO ,
CODEC_ID_RAWVIDEO ,
sizeof ( RawVideoContext ) ,
raw_init ,
raw_encode ,
raw_close ,
raw_init_decoder ,
NULL ,
raw_close_decoder ,
raw_decode ,
} ;