static int aiff_write_trailer(AVFormatContext *s) { ByteIOContext *pb = s->pb; AIFFOutputContext *aiff = s->priv_data; AVCodecContext *enc = s->streams[0]->codec; /* Chunks sizes must be even */ int64_t file_size, end_size; end_size = file_size = url_ftell(pb); if (file_size & 1) { put_byte(pb, 0); end_size++; } if (!url_is_streamed(s->pb)) { /* File length */ url_fseek(pb, aiff->form, SEEK_SET); put_be32(pb, file_size - aiff->form - 4); /* Number of sample frames */ url_fseek(pb, aiff->frames, SEEK_SET); put_be32(pb, (file_size-aiff->ssnd-12)/enc->block_align); /* Sound Data chunk size */ url_fseek(pb, aiff->ssnd, SEEK_SET); put_be32(pb, file_size - aiff->ssnd - 4); /* return to the end */ url_fseek(pb, end_size, SEEK_SET); put_flush_packet(pb); } return 0; }
static int asf_write_trailer(AVFormatContext *s) { ASFContext *asf = s->priv_data; int64_t file_size,data_size; /* flush the current packet */ if (asf->pb.buf_ptr > asf->pb.buffer) flush_packet(s); /* write index */ data_size = url_ftell(s->pb); if ((!asf->is_streamed) && (asf->nb_index_count != 0)) { asf_write_index(s, asf->index_ptr, asf->maximum_packet, asf->nb_index_count); } put_flush_packet(s->pb); if (asf->is_streamed || url_is_streamed(s->pb)) { put_chunk(s, 0x4524, 0, 0); /* end of stream */ } else { /* rewrite an updated header */ file_size = url_ftell(s->pb); url_fseek(s->pb, 0, SEEK_SET); asf_write_header1(s, file_size, data_size - asf->data_offset); } put_flush_packet(s->pb); av_free(asf->index_ptr); return 0; }
static int wv_read_header(AVFormatContext *s, AVFormatParameters *ap) { ByteIOContext *pb = s->pb; WVContext *wc = s->priv_data; AVStream *st; wc->block_parsed = 0; if(wv_read_block_header(s, pb, 0) < 0) return -1; /* now we are ready: build format streams */ st = av_new_stream(s, 0); if (!st) return -1; st->codec->codec_type = AVMEDIA_TYPE_AUDIO; st->codec->codec_id = CODEC_ID_WAVPACK; st->codec->channels = wc->chan; st->codec->channel_layout = wc->chmask; st->codec->sample_rate = wc->rate; st->codec->bits_per_coded_sample = wc->bpp; av_set_pts_info(st, 64, 1, wc->rate); st->start_time = 0; st->duration = wc->samples; if(!url_is_streamed(s->pb)) { int64_t cur = url_ftell(s->pb); ff_ape_parse_tag(s); if(!av_metadata_get(s->metadata, "", NULL, AV_METADATA_IGNORE_SUFFIX)) ff_id3v1_read(s); url_fseek(s->pb, cur, SEEK_SET); } return 0; }
static int wav_write_trailer(AVFormatContext *s) { ByteIOContext *pb = s->pb; WAVContext *wav = s->priv_data; int64_t file_size; put_flush_packet(pb); if (!url_is_streamed(s->pb)) { ff_end_tag(pb, wav->data); /* update file size */ file_size = url_ftell(pb); url_fseek(pb, 4, SEEK_SET); put_le32(pb, (uint32_t)(file_size - 8)); url_fseek(pb, file_size, SEEK_SET); put_flush_packet(pb); if(s->streams[0]->codec->codec_tag != 0x01) { /* Update num_samps in fact chunk */ int number_of_samples; number_of_samples = av_rescale(wav->maxpts - wav->minpts + wav->last_duration, s->streams[0]->codec->sample_rate * (int64_t)s->streams[0]->time_base.num, s->streams[0]->time_base.den); url_fseek(pb, wav->data-12, SEEK_SET); put_le32(pb, number_of_samples); url_fseek(pb, file_size, SEEK_SET); put_flush_packet(pb); } } return 0; }
static int swf_write_trailer(AVFormatContext *s) { SWFContext *swf = s->priv_data; ByteIOContext *pb = s->pb; AVCodecContext *enc, *video_enc; int file_size, i; video_enc = NULL; for(i=0;i<s->nb_streams;i++) { enc = s->streams[i]->codec; if (enc->codec_type == CODEC_TYPE_VIDEO) video_enc = enc; else av_fifo_free(&swf->audio_fifo); } put_swf_tag(s, TAG_END); put_swf_end_tag(s); put_flush_packet(s->pb); /* patch file size and number of frames if not streamed */ if (!url_is_streamed(s->pb) && video_enc) { file_size = url_ftell(pb); url_fseek(pb, 4, SEEK_SET); put_le32(pb, file_size); url_fseek(pb, swf->duration_pos, SEEK_SET); put_le16(pb, swf->video_frame_number); url_fseek(pb, swf->vframes_pos, SEEK_SET); put_le16(pb, swf->video_frame_number); url_fseek(pb, file_size, SEEK_SET); } return 0; }
static int rm_write_trailer(AVFormatContext *s) { RMMuxContext *rm = s->priv_data; int data_size, index_pos, i; ByteIOContext *pb = s->pb; if (!url_is_streamed(s->pb)) { /* end of file: finish to write header */ index_pos = url_fseek(pb, 0, SEEK_CUR); data_size = index_pos - rm->data_pos; /* FIXME: write index */ /* undocumented end header */ put_be32(pb, 0); put_be32(pb, 0); url_fseek(pb, 0, SEEK_SET); for(i=0;i<s->nb_streams;i++) rm->streams[i].total_frames = rm->streams[i].nb_frames; rv10_write_header(s, data_size, 0); } else { /* undocumented end header */ put_be32(pb, 0); put_be32(pb, 0); } put_flush_packet(pb); return 0; }
static int read_header(AVFormatContext *avctx, AVFormatParameters *ap) { TtyDemuxContext *s = avctx->priv_data; AVStream *st = av_new_stream(avctx, 0); if (!st) return AVERROR(ENOMEM); st->codec->codec_tag = 0; st->codec->codec_type = AVMEDIA_TYPE_VIDEO; st->codec->codec_id = CODEC_ID_ANSI; if (ap->width) st->codec->width = ap->width; if (ap->height) st->codec->height = ap->height; if (!ap->time_base.num) { av_set_pts_info(st, 60, 1, 25); } else { av_set_pts_info(st, 60, ap->time_base.num, ap->time_base.den); } /* simulate tty display speed */ s->chars_per_frame = FFMAX(av_q2d(st->time_base) * (ap->sample_rate ? ap->sample_rate : LINE_RATE), 1); if (!url_is_streamed(avctx->pb)) { s->fsize = url_fsize(avctx->pb); st->duration = (s->fsize + s->chars_per_frame - 1) / s->chars_per_frame; if (ff_sauce_read(avctx, &s->fsize, 0, 0) < 0) efi_read(avctx, s->fsize - 51); url_fseek(avctx->pb, 0, SEEK_SET); } return 0; }
/* raw input */ int ff_raw_read_header(AVFormatContext *s, AVFormatParameters *ap) { AVStream *st; enum CodecID id; st = av_new_stream(s, 0); if (!st) return AVERROR(ENOMEM); id = s->iformat->value; if (id == CODEC_ID_RAWVIDEO) { st->codec->codec_type = AVMEDIA_TYPE_VIDEO; } else { st->codec->codec_type = AVMEDIA_TYPE_AUDIO; } st->codec->codec_id = id; switch(st->codec->codec_type) { case AVMEDIA_TYPE_AUDIO: st->codec->sample_rate = ap->sample_rate; if(ap->channels) st->codec->channels = ap->channels; else st->codec->channels = 1; st->codec->bits_per_coded_sample = av_get_bits_per_sample(st->codec->codec_id); assert(st->codec->bits_per_coded_sample > 0); st->codec->block_align = st->codec->bits_per_coded_sample*st->codec->channels/8; av_set_pts_info(st, 64, 1, st->codec->sample_rate); break; case AVMEDIA_TYPE_VIDEO: if(ap->time_base.num) av_set_pts_info(st, 64, ap->time_base.num, ap->time_base.den); else av_set_pts_info(st, 64, 1, 25); st->r_frame_rate.num = st->time_base.den; st->r_frame_rate.den = st->time_base.num; st->codec->width = ap->width; st->codec->height = ap->height; st->codec->pix_fmt = ap->pix_fmt; if(st->codec->codec_id == CODEC_ID_RAWVIDEO && st->codec->pix_fmt != PIX_FMT_NONE && !url_is_streamed(s->pb)) { int frame_size = avpicture_get_size(st->codec->pix_fmt, st->codec->width, st->codec->height); if (frame_size < 0) { av_log(s, AV_LOG_ERROR, "could not get frame size\n"); return -1; } if (url_fsize(s->pb) % frame_size) av_log(s, AV_LOG_WARNING, "partial file\n"); st->nb_frames = url_fsize(s->pb) / frame_size; st->duration = st->nb_frames; } if(st->codec->pix_fmt == PIX_FMT_NONE) st->codec->pix_fmt= PIX_FMT_YUV420P; break; default: return -1; } return 0; }
static int avi_write_ix(AVFormatContext *s) { ByteIOContext *pb = s->pb; AVIContext *avi = s->priv_data; char tag[5]; char ix_tag[] = "ix00"; int i, j; assert(!url_is_streamed(pb)); if (avi->riff_id > AVI_MASTER_INDEX_SIZE) return -1; for (i=0;i<s->nb_streams;i++) { AVIStream *avist= s->streams[i]->priv_data; int64_t ix, pos; avi_stream2fourcc(&tag[0], i, s->streams[i]->codec->codec_type); ix_tag[3] = '0' + i; /* Writing AVI OpenDML leaf index chunk */ ix = url_ftell(pb); put_tag(pb, &ix_tag[0]); /* ix?? */ put_le32(pb, avist->indexes.entry * 8 + 24); /* chunk size */ put_le16(pb, 2); /* wLongsPerEntry */ put_byte(pb, 0); /* bIndexSubType (0 == frame index) */ put_byte(pb, 1); /* bIndexType (1 == AVI_INDEX_OF_CHUNKS) */ put_le32(pb, avist->indexes.entry); /* nEntriesInUse */ put_tag(pb, &tag[0]); /* dwChunkId */ put_le64(pb, avi->movi_list);/* qwBaseOffset */ put_le32(pb, 0); /* dwReserved_3 (must be 0) */ for (j=0; j<avist->indexes.entry; j++) { AVIIentry* ie = avi_get_ientry(&avist->indexes, j); put_le32(pb, ie->pos + 8); put_le32(pb, ((uint32_t)ie->len & ~0x80000000) | (ie->flags & 0x10 ? 0 : 0x80000000)); } put_flush_packet(pb); pos = url_ftell(pb); /* Updating one entry in the AVI OpenDML master index */ url_fseek(pb, avist->indexes.indx_start - 8, SEEK_SET); put_tag(pb, "indx"); /* enabling this entry */ url_fskip(pb, 8); put_le32(pb, avi->riff_id); /* nEntriesInUse */ url_fskip(pb, 16*avi->riff_id); put_le64(pb, ix); /* qwOffset */ put_le32(pb, pos - ix); /* dwSize */ put_le32(pb, avist->indexes.entry); /* dwDuration */ url_fseek(pb, pos, SEEK_SET); } return 0; }
static int avi_write_trailer(AVFormatContext *s) { AVIContext *avi = s->priv_data; ByteIOContext *pb = s->pb; int res = 0; int i, j, n, nb_frames; int64_t file_size; if (!url_is_streamed(pb)){ if (avi->riff_id == 1) { ff_end_tag(pb, avi->movi_list); res = avi_write_idx1(s); ff_end_tag(pb, avi->riff_start); } else { avi_write_ix(s); ff_end_tag(pb, avi->movi_list); ff_end_tag(pb, avi->riff_start); file_size = url_ftell(pb); url_fseek(pb, avi->odml_list - 8, SEEK_SET); put_tag(pb, "LIST"); /* Making this AVI OpenDML one */ url_fskip(pb, 16); for (n=nb_frames=0;n<s->nb_streams;n++) { AVCodecContext *stream = s->streams[n]->codec; AVIStream *avist= s->streams[n]->priv_data; if (stream->codec_type == AVMEDIA_TYPE_VIDEO) { if (nb_frames < avist->packet_count) nb_frames = avist->packet_count; } else { if (stream->codec_id == CODEC_ID_MP2 || stream->codec_id == CODEC_ID_MP3) { nb_frames += avist->packet_count; } } } put_le32(pb, nb_frames); url_fseek(pb, file_size, SEEK_SET); avi_write_counters(s, avi->riff_id); } } put_flush_packet(pb); for (i=0; i<s->nb_streams; i++) { AVIStream *avist= s->streams[i]->priv_data; for (j=0; j<avist->indexes.ents_allocated/AVI_INDEX_CLUSTER_SIZE; j++) av_free(avist->indexes.cluster[j]); av_freep(&avist->indexes.cluster); avist->indexes.ents_allocated = avist->indexes.entry = 0; } return res; }
static int vc1test_write_trailer(AVFormatContext *s) { RCVContext *ctx = s->priv_data; AVIOContext *pb = s->pb; if (!url_is_streamed(s->pb)) { avio_seek(pb, 0, SEEK_SET); avio_wl24(pb, ctx->frames); put_flush_packet(pb); } return 0; }
static int mp3_read_header(AVFormatContext *s, AVFormatParameters *ap) { AVStream *st; uint8_t buf[ID3v1_TAG_SIZE]; int len, ret, filesize; offset_t off; st = av_new_stream(s, 0); if (!st) return AVERROR(ENOMEM); st->codec->codec_type = CODEC_TYPE_AUDIO; st->codec->codec_id = CODEC_ID_MP3; st->need_parsing = AVSTREAM_PARSE_FULL; st->start_time = 0; /* try to get the TAG */ if (!url_is_streamed(s->pb)) { /* XXX: change that */ filesize = url_fsize(s->pb); if (filesize > 128) { url_fseek(s->pb, filesize - 128, SEEK_SET); ret = get_buffer(s->pb, buf, ID3v1_TAG_SIZE); if (ret == ID3v1_TAG_SIZE) { id3v1_parse_tag(s, buf); } url_fseek(s->pb, 0, SEEK_SET); } } /* if ID3v2 header found, skip it */ ret = get_buffer(s->pb, buf, ID3v2_HEADER_SIZE); if (ret != ID3v2_HEADER_SIZE) return -1; if (id3v2_match(buf)) { /* parse ID3v2 header */ len = ((buf[6] & 0x7f) << 21) | ((buf[7] & 0x7f) << 14) | ((buf[8] & 0x7f) << 7) | (buf[9] & 0x7f); id3v2_parse(s, len, buf[3], buf[5]); } else { url_fseek(s->pb, 0, SEEK_SET); } off = url_ftell(s->pb); mp3_parse_vbr_tags(s, st, off); url_fseek(s->pb, off, SEEK_SET); /* the parameters will be extracted from the compressed bitstream */ return 0; }
static int mpc_read_header(AVFormatContext *s, AVFormatParameters *ap) { MPCContext *c = s->priv_data; AVStream *st; if(get_le24(s->pb) != MKTAG('M', 'P', '+', 0)){ av_log(s, AV_LOG_ERROR, "Not a Musepack file\n"); return -1; } c->ver = get_byte(s->pb); if(c->ver != 0x07 && c->ver != 0x17){ av_log(s, AV_LOG_ERROR, "Can demux Musepack SV7, got version %02X\n", c->ver); return -1; } c->fcount = get_le32(s->pb); if((int64_t)c->fcount * sizeof(MPCFrame) >= UINT_MAX){ av_log(s, AV_LOG_ERROR, "Too many frames, seeking is not possible\n"); return -1; } c->frames = av_malloc(c->fcount * sizeof(MPCFrame)); c->curframe = 0; c->lastframe = -1; c->curbits = 8; c->frames_noted = 0; st = av_new_stream(s, 0); if (!st) return AVERROR(ENOMEM); st->codec->codec_type = AVMEDIA_TYPE_AUDIO; st->codec->codec_id = CODEC_ID_MUSEPACK7; st->codec->channels = 2; st->codec->bits_per_coded_sample = 16; st->codec->extradata_size = 16; st->codec->extradata = av_mallocz(st->codec->extradata_size+FF_INPUT_BUFFER_PADDING_SIZE); get_buffer(s->pb, st->codec->extradata, 16); st->codec->sample_rate = mpc_rate[st->codec->extradata[2] & 3]; av_set_pts_info(st, 32, MPC_FRAMESIZE, st->codec->sample_rate); /* scan for seekpoints */ st->start_time = 0; st->duration = c->fcount; /* try to read APE tags */ if (!url_is_streamed(s->pb)) { int64_t pos = url_ftell(s->pb); ff_ape_parse_tag(s); if (!av_metadata_get(s->metadata, "", NULL, AV_METADATA_IGNORE_SUFFIX)) ff_id3v1_read(s); url_fseek(s->pb, pos, SEEK_SET); } return 0; }
static int r3d_read_header(AVFormatContext *s, AVFormatParameters *ap) { R3DContext *r3d = s->priv_data; Atom atom; int ret; if (read_atom(s, &atom) < 0) { av_log(s, AV_LOG_ERROR, "error reading atom\n"); return -1; } if (atom.tag == MKTAG('R','E','D','1')) { if ((ret = r3d_read_red1(s)) < 0) { av_log(s, AV_LOG_ERROR, "error parsing 'red1' atom\n"); return ret; } } else { av_log(s, AV_LOG_ERROR, "could not find 'red1' atom\n"); return -1; } s->data_offset = url_ftell(s->pb); dprintf(s, "data offset %#llx\n", s->data_offset); if (url_is_streamed(s->pb)) return 0; // find REOB/REOF/REOS to load index url_fseek(s->pb, url_fsize(s->pb)-48-8, SEEK_SET); if (read_atom(s, &atom) < 0) av_log(s, AV_LOG_ERROR, "error reading end atom\n"); if (atom.tag != MKTAG('R','E','O','B') && atom.tag != MKTAG('R','E','O','F') && atom.tag != MKTAG('R','E','O','S')) goto out; r3d_read_reos(s); if (r3d->rdvo_offset) { url_fseek(s->pb, r3d->rdvo_offset, SEEK_SET); if (read_atom(s, &atom) < 0) av_log(s, AV_LOG_ERROR, "error reading 'rdvo' atom\n"); if (atom.tag == MKTAG('R','D','V','O')) { if (r3d_read_rdvo(s, &atom) < 0) av_log(s, AV_LOG_ERROR, "error parsing 'rdvo' atom\n"); } } out: url_fseek(s->pb, s->data_offset, SEEK_SET); return 0; }
static int avi_write_idx1(AVFormatContext *s) { ByteIOContext *pb = s->pb; AVIContext *avi = s->priv_data; int64_t idx_chunk; int i; char tag[5]; if (!url_is_streamed(pb)) { AVIStream *avist; AVIIentry* ie = 0, *tie; int empty, stream_id = -1; idx_chunk = ff_start_tag(pb, "idx1"); for(i=0; i<s->nb_streams; i++){ avist= s->streams[i]->priv_data; avist->entry=0; } do { empty = 1; for (i=0; i<s->nb_streams; i++) { avist= s->streams[i]->priv_data; if (avist->indexes.entry <= avist->entry) continue; tie = avi_get_ientry(&avist->indexes, avist->entry); if (empty || tie->pos < ie->pos) { ie = tie; stream_id = i; } empty = 0; } if (!empty) { avist= s->streams[stream_id]->priv_data; avi_stream2fourcc(&tag[0], stream_id, s->streams[stream_id]->codec->codec_type); put_tag(pb, &tag[0]); put_le32(pb, ie->flags); put_le32(pb, ie->pos); put_le32(pb, ie->len); avist->entry++; } } while (!empty); ff_end_tag(pb, idx_chunk); avi_write_counters(s, avi->riff_id); } return 0; }
static int read_seek(AVFormatContext *s, int stream_index, int64_t timestamp, int flags) { BinkDemuxContext *bink = s->priv_data; AVStream *vst = s->streams[0]; if (url_is_streamed(s->pb)) return -1; /* seek to the first frame */ avio_seek(s->pb, vst->index_entries[0].pos, SEEK_SET); bink->video_pts = 0; memset(bink->audio_pts, 0, sizeof(bink->audio_pts)); bink->current_track = -1; return 0; }
static int au_write_trailer(AVFormatContext *s) { ByteIOContext *pb = s->pb; offset_t file_size; if (!url_is_streamed(s->pb)) { /* update file size */ file_size = url_ftell(pb); url_fseek(pb, 8, SEEK_SET); put_be32(pb, (uint32_t)(file_size - 24)); url_fseek(pb, file_size, SEEK_SET); put_flush_packet(pb); } return 0; }
void ff_id3v1_read(AVFormatContext *s) { int ret, filesize; uint8_t buf[ID3v1_TAG_SIZE]; if (!url_is_streamed(s->pb)) { /* XXX: change that */ filesize = url_fsize(s->pb); if (filesize > 128) { avio_seek(s->pb, filesize - 128, SEEK_SET); ret = avio_read(s->pb, buf, ID3v1_TAG_SIZE); if (ret == ID3v1_TAG_SIZE) { parse_tag(s, buf); } avio_seek(s->pb, 0, SEEK_SET); } } }
static int avi_write_idx1(AVFormatContext *s) { ByteIOContext *pb = &s->pb; AVIContext *avi = s->priv_data; offset_t idx_chunk; int i; char tag[5]; if (!url_is_streamed(pb)) { AVIIentry* ie = 0, *tie; int entry[MAX_STREAMS]; int empty, stream_id = -1; idx_chunk = start_tag(pb, "idx1"); memset(&entry[0], 0, sizeof(entry)); do { empty = 1; for (i=0; i<s->nb_streams; i++) { if (avi->indexes[i].entry <= entry[i]) continue; tie = avi_get_ientry(&avi->indexes[i], entry[i]); if (empty || tie->pos < ie->pos) { ie = tie; stream_id = i; } empty = 0; } if (!empty) { avi_stream2fourcc(&tag[0], stream_id, s->streams[stream_id]->codec->codec_type); put_tag(pb, &tag[0]); put_le32(pb, ie->flags); put_le32(pb, ie->pos); put_le32(pb, ie->len); entry[stream_id]++; } } while (!empty); end_tag(pb, idx_chunk); avi_write_counters(s, avi->riff_id); } return 0; }
static int sox_write_trailer(AVFormatContext *s) { SoXContext *sox = s->priv_data; AVIOContext *pb = s->pb; AVCodecContext *enc = s->streams[0]->codec; if (!url_is_streamed(s->pb)) { /* update number of samples */ int64_t file_size = avio_tell(pb); int64_t num_samples = (file_size - sox->header_size - 4LL) >> 2LL; avio_seek(pb, 8, SEEK_SET); if (enc->codec_id == CODEC_ID_PCM_S32LE) { avio_wl64(pb, num_samples); } else avio_wb64(pb, num_samples); avio_seek(pb, file_size, SEEK_SET); avio_flush(pb); }
static int sox_write_trailer(AVFormatContext *s) { SoXContext *sox = s->priv_data; ByteIOContext *pb = s->pb; AVCodecContext *enc = s->streams[0]->codec; if (!url_is_streamed(s->pb)) { /* update number of samples */ int64_t file_size = url_ftell(pb); int64_t num_samples = (file_size - sox->header_size - 4LL) >> 2LL; url_fseek(pb, 8, SEEK_SET); if (enc->codec_id == CODEC_ID_PCM_S32LE) { put_le64(pb, num_samples); } else put_be64(pb, num_samples); url_fseek(pb, file_size, SEEK_SET); put_flush_packet(pb); }
static int read_header(AVFormatContext *s, AVFormatParameters *ap) { FilmstripDemuxContext *film = s->priv_data; ByteIOContext *pb = s->pb; AVStream *st; if (url_is_streamed(s->pb)) return AVERROR(EIO); url_fseek(pb, url_fsize(pb) - 36, SEEK_SET); if (get_be32(pb) != RAND_TAG) { av_log(s, AV_LOG_ERROR, "magic number not found"); return AVERROR_INVALIDDATA; } st = av_new_stream(s, 0); if (!st) return AVERROR(ENOMEM); st->nb_frames = get_be32(pb); if (get_be16(pb) != 0) { av_log_ask_for_sample(s, "unsupported packing method\n"); return AVERROR_INVALIDDATA; } url_fskip(pb, 2); st->codec->codec_type = AVMEDIA_TYPE_VIDEO; st->codec->codec_id = CODEC_ID_RAWVIDEO; st->codec->pix_fmt = PIX_FMT_RGBA; st->codec->codec_tag = 0; /* no fourcc */ st->codec->width = get_be16(pb); st->codec->height = get_be16(pb); film->leading = get_be16(pb); av_set_pts_info(st, 64, 1, get_be16(pb)); url_fseek(pb, 0, SEEK_SET); return 0; }
static int rso_write_header(AVFormatContext *s) { ByteIOContext *pb = s->pb; AVCodecContext *enc = s->streams[0]->codec; if (!enc->codec_tag) return AVERROR_INVALIDDATA; if (enc->channels != 1) { av_log(s, AV_LOG_ERROR, "RSO only supports mono\n"); return AVERROR_INVALIDDATA; } if (url_is_streamed(s->pb)) { av_log(s, AV_LOG_ERROR, "muxer does not support non seekable output\n"); return AVERROR_INVALIDDATA; } /* XXX: find legal sample rates (if any) */ if (enc->sample_rate >= 1u<<16) { av_log(s, AV_LOG_ERROR, "Sample rate must be < 65536\n"); return AVERROR_INVALIDDATA; } if (enc->codec_id == CODEC_ID_ADPCM_IMA_WAV) { av_log(s, AV_LOG_ERROR, "ADPCM in RSO not implemented\n"); return AVERROR_PATCHWELCOME; } /* format header */ put_be16(pb, enc->codec_tag); /* codec ID */ put_be16(pb, 0); /* data size, will be written at EOF */ put_be16(pb, enc->sample_rate); put_be16(pb, 0x0000); /* play mode ? (0x0000 = don't loop) */ put_flush_packet(pb); return 0; }
static int flac_write_trailer(struct AVFormatContext *s) { ByteIOContext *pb = s->pb; uint8_t *streaminfo; enum FLACExtradataFormat format; int64_t file_size; if (!ff_flac_is_extradata_valid(s->streams[0]->codec, &format, &streaminfo)) return -1; if (!url_is_streamed(pb)) { /* rewrite the STREAMINFO header block data */ file_size = url_ftell(pb); url_fseek(pb, 8, SEEK_SET); put_buffer(pb, streaminfo, FLAC_STREAMINFO_SIZE); url_fseek(pb, file_size, SEEK_SET); put_flush_packet(pb); } else { av_log(s, AV_LOG_WARNING, "unable to rewrite FLAC header.\n"); } return 0; }
static int ffm_write_trailer(AVFormatContext *s) { ByteIOContext *pb = s->pb; FFMContext *ffm = s->priv_data; /* flush packets */ if (ffm->packet_ptr > ffm->packet) flush_packet(s); put_flush_packet(pb); if (!url_is_streamed(pb)) { int64_t size; /* update the write offset */ size = url_ftell(pb); url_fseek(pb, 8, SEEK_SET); put_be64(pb, size); put_flush_packet(pb); } return 0; }
static int mmf_write_trailer(AVFormatContext *s) { ByteIOContext *pb = s->pb; MMFContext *mmf = s->priv_data; int64_t pos, size; int gatetime; if (!url_is_streamed(s->pb)) { /* Fill in length fields */ end_tag_be(pb, mmf->awapos); end_tag_be(pb, mmf->atrpos); end_tag_be(pb, 8); pos = url_ftell(pb); size = pos - mmf->awapos; /* Fill Atsq chunk */ url_fseek(pb, mmf->atsqpos, SEEK_SET); /* "play wav" */ put_byte(pb, 0); /* start time */ put_byte(pb, 1); /* (channel << 6) | wavenum */ gatetime = size * 500 / s->streams[0]->codec->sample_rate; put_varlength(pb, gatetime); /* duration */ /* "nop" */ put_varlength(pb, gatetime); /* start time */ put_buffer(pb, "\xff\x00", 2); /* nop */ /* "end of sequence" */ put_buffer(pb, "\x00\x00\x00\x00", 4); url_fseek(pb, pos, SEEK_SET); put_flush_packet(pb); } return 0; }
static int wav_write_header(AVFormatContext *s) { WAVContext *wav = s->priv_data; ByteIOContext *pb = s->pb; int64_t fmt, fact; put_tag(pb, "RIFF"); put_le32(pb, 0); /* file length */ put_tag(pb, "WAVE"); /* format header */ fmt = ff_start_tag(pb, "fmt "); if (ff_put_wav_header(pb, s->streams[0]->codec) < 0) { av_log(s, AV_LOG_ERROR, "%s codec not supported in WAVE format\n", s->streams[0]->codec->codec ? s->streams[0]->codec->codec->name : "NONE"); av_free(wav); return -1; } ff_end_tag(pb, fmt); if (s->streams[0]->codec->codec_tag != 0x01 /* hence for all other than PCM */ && !url_is_streamed(s->pb)) { fact = ff_start_tag(pb, "fact"); put_le32(pb, 0); ff_end_tag(pb, fact); } av_set_pts_info(s->streams[0], 64, 1, s->streams[0]->codec->sample_rate); wav->maxpts = wav->last_duration = 0; wav->minpts = INT64_MAX; /* data header */ wav->data = ff_start_tag(pb, "data"); put_flush_packet(pb); return 0; }
static int rm_write_trailer(AVFormatContext *s) { RMContext *rm = s->priv_data; int data_size, index_pos, i; ByteIOContext *pb = s->pb; if (!url_is_streamed(s->pb)) { /* end of file: finish to write header */ index_pos = url_fseek(pb, 0, SEEK_CUR); data_size = index_pos - rm->data_pos; /* index */ put_tag(pb, "INDX"); put_be32(pb, 10 + 10 * s->nb_streams); put_be16(pb, 0); for(i=0;i<s->nb_streams;i++) { put_be32(pb, 0); /* zero indexes */ put_be16(pb, i); /* stream number */ put_be32(pb, 0); /* next index */ } /* undocumented end header */ put_be32(pb, 0); put_be32(pb, 0); url_fseek(pb, 0, SEEK_SET); for(i=0;i<s->nb_streams;i++) rm->streams[i].total_frames = rm->streams[i].nb_frames; rv10_write_header(s, data_size, index_pos); } else { /* undocumented end header */ put_be32(pb, 0); put_be32(pb, 0); } put_flush_packet(pb); return 0; }
static int wav_write_header(AVFormatContext *s) { WAVContext *wav = s->priv_data; ByteIOContext *pb = &s->pb; offset_t fmt, fact; put_tag(pb, "RIFF"); put_le32(pb, 0); /* file length */ put_tag(pb, "WAVE"); /* format header */ fmt = start_tag(pb, "fmt "); if (put_wav_header(pb, s->streams[0]->codec) < 0) { av_free(wav); return -1; } end_tag(pb, fmt); if(s->streams[0]->codec->codec_tag != 0x01 /* hence for all other than PCM */ && !url_is_streamed(&s->pb)) { fact = start_tag(pb, "fact"); put_le32(pb, 0); end_tag(pb, fact); } av_set_pts_info(s->streams[0], 64, 1, s->streams[0]->codec->sample_rate); wav->maxpts = wav->last_duration = 0; wav->minpts = INT64_MAX; /* data header */ wav->data = start_tag(pb, "data"); put_flush_packet(pb); return 0; }
static int read_header(AVFormatContext *s, AVFormatParameters *ap) { ByteIOContext *pb = s->pb; CaffContext *caf = s->priv_data; AVStream *st; uint32_t tag = 0; int found_data, ret; int64_t size; url_fskip(pb, 8); /* magic, version, file flags */ /* audio description chunk */ if (get_be32(pb) != MKBETAG('d','e','s','c')) { av_log(s, AV_LOG_ERROR, "desc chunk not present\n"); return AVERROR_INVALIDDATA; } size = get_be64(pb); if (size != 32) return AVERROR_INVALIDDATA; ret = read_desc_chunk(s); if (ret) return ret; st = s->streams[0]; /* parse each chunk */ found_data = 0; while (!url_feof(pb)) { /* stop at data chunk if seeking is not supported or data chunk size is unknown */ if (found_data && (caf->data_size < 0 || url_is_streamed(pb))) break; tag = get_be32(pb); size = get_be64(pb); if (url_feof(pb)) break; switch (tag) { case MKBETAG('d','a','t','a'): url_fskip(pb, 4); /* edit count */ caf->data_start = url_ftell(pb); caf->data_size = size < 0 ? -1 : size - 4; if (caf->data_size > 0 && !url_is_streamed(pb)) url_fskip(pb, caf->data_size); found_data = 1; break; /* magic cookie chunk */ case MKBETAG('k','u','k','i'): if (read_kuki_chunk(s, size)) return AVERROR_INVALIDDATA; break; /* packet table chunk */ case MKBETAG('p','a','k','t'): if (read_pakt_chunk(s, size)) return AVERROR_INVALIDDATA; break; case MKBETAG('i','n','f','o'): read_info_chunk(s, size); break; default: #define _(x) ((x) >= ' ' ? (x) : ' ') av_log(s, AV_LOG_WARNING, "skipping CAF chunk: %08X (%c%c%c%c)\n", tag, _(tag>>24), _((tag>>16)&0xFF), _((tag>>8)&0xFF), _(tag&0xFF)); #undef _ case MKBETAG('f','r','e','e'): if (size < 0) return AVERROR_INVALIDDATA; url_fskip(pb, size); break; } } if (!found_data) return AVERROR_INVALIDDATA; if (caf->bytes_per_packet > 0 && caf->frames_per_packet > 0) { if (caf->data_size > 0) st->nb_frames = (caf->data_size / caf->bytes_per_packet) * caf->frames_per_packet; } else if (st->nb_index_entries) { st->codec->bit_rate = st->codec->sample_rate * caf->data_size * 8 / st->duration; } else { av_log(s, AV_LOG_ERROR, "Missing packet table. It is required when " "block size or frame size are variable.\n"); return AVERROR_INVALIDDATA; } s->file_size = url_fsize(pb); s->file_size = FFMAX(0, s->file_size); av_set_pts_info(st, 64, 1, st->codec->sample_rate); st->start_time = 0; /* position the stream at the start of data */ if (caf->data_size >= 0) url_fseek(pb, caf->data_start, SEEK_SET); return 0; }