FFmpeg technical
Jump to navigation
Jump to search
Demuxer stuff
How to use demuxer with raw data
Write a parser. There are two main function - parse and split. parse is used to reconstruct precisely one frame from raw packets, split is used for extracting extradata from the same stream.
Parser declarations will look like this:
typedef struct MyParseContext{ ParseContext pc; /* always include this first */ another data }; AVParser some_parser = { { CODEC_ID_1 [CODEC_ID_2, ...] }, sizeof (MyParseContext), NULL, /* usually there is no need in parser_open */ my_parse, ff_parse_close, /* again, use standard close function */ my_split, };
And here is the code for some parser which splits frame by some markers:
static int xxx_find_frame_end(XXXParseContext *pc1, const uint8_t *buf, int buf_size) { int start_found, i; uint32_t state; ParseContext *pc = &pc1->pc; start_found= pc->frame_start_found; state= pc->state; i=0; if(!start_found){ for(i=0; i<buf_size; i++){ state= (state<<8) | buf[i]; if(state == MARKER){ start_found=1; break; } } } if(start_found){ for(; i<buf_size; i++){ state= (state<<8) | buf[i]; if(state == MARKER){ pc->frame_start_found= 0; pc->state= -1; return i-3; } } } pc->frame_start_found= start_found; pc->state= state; return END_NOT_FOUND; }
static int xxx_parse(AVCodecParserContext *s, AVCodecContext *avctx, uint8_t **poutbuf, int *poutbuf_size, const uint8_t *buf, int buf_size) { XXXParseContext *pc1 = s->priv_data; ParseContext *pc = &pc1->pc; int next; if(s->flags & PARSER_FLAG_COMPLETE_FRAMES){ next= buf_size; }else{ next= xxx_find_frame_end(pc1, buf, buf_size); if (ff_combine_frame(pc, next, (uint8_t **)&buf, &buf_size) < 0) { *poutbuf = NULL; *poutbuf_size = 0; return buf_size; } } *poutbuf = (uint8_t *)buf; *poutbuf_size = buf_size; return next; }