[FFmpeg-devel] [PATCH] rawdec: support AVRn 1:1 raw interlaced mode
Michael Niedermayer
michaelni at gmx.at
Sat Aug 18 04:07:31 CEST 2012
On Sat, Aug 18, 2012 at 04:03:54AM +0200, Michael Niedermayer wrote:
> Fixes Ticket971
>
> Signed-off-by: Michael Niedermayer <michaelni at gmx.at>
> ---
a whitespaceless diff for easy review is below:
@@ -39,6 +39,7 @@ typedef struct RawVideoContext {
unsigned char * buffer; /* block of memory for holding one frame */
int length; /* number of bytes in buffer */
int flip;
+ int interlace;
AVFrame pic; ///< AVCodecContext.coded_frame
int tff;
} RawVideoContext;
@@ -130,6 +131,15 @@ static av_cold int raw_init_decoder(AVCodecContext *avctx)
avctx->codec_tag == MKTAG(3, 0, 0, 0) || avctx->codec_tag == MKTAG('W','R','A','W'))
context->flip=1;
+ if(avctx->extradata_size >= 9 && avctx->extradata[4] < avctx->extradata_size - 9 && !context->buffer && avctx->pix_fmt == PIX_FMT_UYVY422) {
+ context->interlace = !memcmp(avctx->extradata + avctx->extradata[4]+4, "1:1(", 4);
+ if(context->interlace) {
+ context->buffer = av_malloc(context->length);
+ if (!context->buffer)
+ return AVERROR(ENOMEM);
+ }
+ }
+
return 0;
}
@@ -162,7 +172,8 @@ static int raw_decode(AVCodecContext *avctx,
if(context->tff>=0){
frame->interlaced_frame = 1;
frame->top_field_first = context->tff;
- }
+ }else if(context->interlace)
+ frame->interlaced_frame = 1;
if (avctx->width <= 0 || avctx->height <= 0) {
av_log(avctx, AV_LOG_ERROR, "w/h is invalid\n");
@@ -173,6 +184,7 @@ static int raw_decode(AVCodecContext *avctx,
if (context->buffer) {
int i;
uint8_t *dst = context->buffer;
+ if(avctx->pix_fmt == PIX_FMT_PAL8){
buf_size = context->length - AVPALETTE_SIZE;
if (avctx->bits_per_coded_sample == 4){
for(i=0; 2*i+1 < buf_size && i<avpkt->size; i++){
@@ -190,6 +202,22 @@ static int raw_decode(AVCodecContext *avctx,
}
linesize_align = 16;
}
+ } else if(context->interlace && avctx->pix_fmt == PIX_FMT_UYVY422) {
+ int x, y;
+ int true_height = buf_size / (2*avctx->width);
+ av_assert0(avctx->height * avctx->width * 2 == context->length);
+ if (buf_size < context->length) {
+ av_log(avctx, AV_LOG_ERROR, "Invalid buffer size, packet size %d < context length %d\n", buf_size, context->length);
+ return AVERROR(EINVAL);
+ }
+ buf += (true_height - avctx->height)*avctx->width;
+ for(y = 0; y < avctx->height-1; y+=2) {
+ memcpy(dst + (y+1)*2*avctx->width, buf , 2*avctx->width);
+ memcpy(dst + (y+0)*2*avctx->width, buf + avctx->width*true_height+4, 2*avctx->width);
+ buf += 2*avctx->width;
+ }
+ }else
+ av_assert0(0);
buf= dst;
}
[...]
--
Michael GnuPG fingerprint: 9FF2128B147EF6730BADF133611EC787040B0FAB
There will always be a question for which you do not know the correct awnser.
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 198 bytes
Desc: Digital signature
URL: <http://ffmpeg.org/pipermail/ffmpeg-devel/attachments/20120818/a439baae/attachment.asc>
More information about the ffmpeg-devel
mailing list