} else {
if (pos == ffm->write_index) {
/* exactly at the end of stream */
- return AVERROR(EAGAIN);
+ if (ffm->server_attached)
+ return AVERROR(EAGAIN);
+ else
+ return AVERROR_INVALIDDATA;
} else if (pos < ffm->write_index) {
avail_size = ffm->write_index - pos;
} else {
avail_size = (avail_size / ffm->packet_size) * (ffm->packet_size - FFM_HEADER_SIZE) + len;
if (size <= avail_size)
return 1;
- else
+ else if (ffm->server_attached)
return AVERROR(EAGAIN);
+ else
+ return AVERROR_INVALIDDATA;
}
-static int ffm_resync(AVFormatContext *s, int state)
+static int ffm_resync(AVFormatContext *s, uint32_t state)
{
av_log(s, AV_LOG_ERROR, "resyncing\n");
while (state != PACKET_ID) {
{
FFMContext *ffm = s->priv_data;
AVIOContext *pb = s->pb;
- int len, fill_size, size1, frame_offset, id;
+ int len, fill_size, size1, frame_offset;
+ uint32_t id;
int64_t last_pos = -1;
size1 = size;
len = size;
if (len == 0) {
if (avio_tell(pb) == ffm->file_size)
- avio_seek(pb, ffm->packet_size, SEEK_SET);
+ if (ffm->server_attached)
+ avio_seek(pb, ffm->packet_size, SEEK_SET);
+ else
+ return AVERROR_EOF;
retry_read:
if (pb->buffer_size != ffm->packet_size) {
int64_t tell = avio_tell(pb);
AVStream *st;
AVIOContext *pb = s->pb;
AVCodecContext *codec;
+ const AVCodecDescriptor *codec_desc;
int ret;
int f_main = 0, f_cprv = -1, f_stvi = -1, f_stau = -1;
AVCodec *enc;
codec = st->codec;
/* generic info */
codec->codec_id = avio_rb32(pb);
+ codec_desc = avcodec_descriptor_get(codec->codec_id);
+ if (!codec_desc) {
+ av_log(s, AV_LOG_ERROR, "Invalid codec id: %d\n", codec->codec_id);
+ codec->codec_id = AV_CODEC_ID_NONE;
+ goto fail;
+ }
codec->codec_type = avio_r8(pb);
+ if (codec->codec_type != codec_desc->type) {
+ av_log(s, AV_LOG_ERROR, "Codec type mismatch: expected %d, found %d\n",
+ codec_desc->type, codec->codec_type);
+ codec->codec_id = AV_CODEC_ID_NONE;
+ codec->codec_type = AVMEDIA_TYPE_UNKNOWN;
+ goto fail;
+ }
codec->bit_rate = avio_rb32(pb);
codec->flags = avio_rb32(pb);
codec->flags2 = avio_rb32(pb);
}
break;
case MKBETAG('S', '2', 'V', 'I'):
- if (f_stvi++) {
+ if (f_stvi++ || !size) {
ret = AVERROR(EINVAL);
goto fail;
}
goto fail;
break;
case MKBETAG('S', '2', 'A', 'U'):
- if (f_stau++) {
+ if (f_stau++ || !size) {
ret = AVERROR(EINVAL);
goto fail;
}
AVStream *st;
AVIOContext *pb = s->pb;
AVCodecContext *codec;
+ const AVCodecDescriptor *codec_desc;
int i, nb_streams;
uint32_t tag;
codec = st->codec;
/* generic info */
codec->codec_id = avio_rb32(pb);
+ codec_desc = avcodec_descriptor_get(codec->codec_id);
+ if (!codec_desc) {
+ av_log(s, AV_LOG_ERROR, "Invalid codec id: %d\n", codec->codec_id);
+ codec->codec_id = AV_CODEC_ID_NONE;
+ goto fail;
+ }
codec->codec_type = avio_r8(pb); /* codec_type */
+ if (codec->codec_type != codec_desc->type) {
+ av_log(s, AV_LOG_ERROR, "Codec type mismatch: expected %d, found %d\n",
+ codec_desc->type, codec->codec_type);
+ codec->codec_id = AV_CODEC_ID_NONE;
+ codec->codec_type = AVMEDIA_TYPE_UNKNOWN;
+ goto fail;
+ }
codec->bit_rate = avio_rb32(pb);
codec->flags = avio_rb32(pb);
codec->flags2 = avio_rb32(pb);