|
|
|
|
@ -14,6 +14,8 @@
|
|
|
|
|
#include "notify.h"
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#define DEFAULT_AVIO_BUFSIZE 4096
|
|
|
|
|
|
|
|
|
|
//static int output_codec_id;
|
|
|
|
|
static codec_def_t *output_codec;
|
|
|
|
|
static const char *output_file_format;
|
|
|
|
|
@ -253,6 +255,20 @@ output_t *output_new_ext(metafile_t *mf, const char *type, const char *kind, con
|
|
|
|
|
return ret;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
int output_avio_write(void *opaque, const uint8_t *buf, int buf_size) {
|
|
|
|
|
output_t *o = opaque;
|
|
|
|
|
ssize_t written = fwrite(buf, buf_size, 1, o->fp);
|
|
|
|
|
if (written == 1)
|
|
|
|
|
return buf_size;
|
|
|
|
|
return AVERROR(errno);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
int64_t output_avio_seek(void *opaque, int64_t offset, int whence) {
|
|
|
|
|
output_t *o = opaque;
|
|
|
|
|
fseek(o->fp, offset, whence);
|
|
|
|
|
return ftell(o->fp);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
int output_config(output_t *output, const format_t *requested_format, format_t *actual_format) {
|
|
|
|
|
const char *err;
|
|
|
|
|
int av_ret = 0;
|
|
|
|
|
@ -332,10 +348,27 @@ int output_config(output_t *output, const format_t *requested_format, format_t *
|
|
|
|
|
|
|
|
|
|
got_fn:
|
|
|
|
|
output->filename = full_fn;
|
|
|
|
|
err = "failed to open avio";
|
|
|
|
|
av_ret = avio_open(&output->fmtctx->pb, full_fn, AVIO_FLAG_WRITE);
|
|
|
|
|
if (av_ret < 0)
|
|
|
|
|
|
|
|
|
|
err = "failed to open output file";
|
|
|
|
|
output->fp = fopen(full_fn, "wb");
|
|
|
|
|
if (!output->fp)
|
|
|
|
|
goto err;
|
|
|
|
|
|
|
|
|
|
err = "failed to alloc avio buffer";
|
|
|
|
|
void *avio_buf = av_malloc(DEFAULT_AVIO_BUFSIZE);
|
|
|
|
|
if (!avio_buf)
|
|
|
|
|
goto err;
|
|
|
|
|
|
|
|
|
|
output->avioctx = avio_alloc_context(avio_buf, DEFAULT_AVIO_BUFSIZE, 1, output,
|
|
|
|
|
NULL, output_avio_write, output_avio_seek);
|
|
|
|
|
err = "failed to alloc AVIOContext";
|
|
|
|
|
if (!output->avioctx) {
|
|
|
|
|
av_freep(&avio_buf);
|
|
|
|
|
goto err;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
output->fmtctx->pb = output->avioctx;
|
|
|
|
|
|
|
|
|
|
err = "failed to write header";
|
|
|
|
|
av_ret = avformat_write_header(output->fmtctx, NULL);
|
|
|
|
|
if (av_ret)
|
|
|
|
|
@ -380,10 +413,18 @@ static bool output_shutdown(output_t *output) {
|
|
|
|
|
ilog(LOG_INFO, "Closing output media file '%s'", output->filename);
|
|
|
|
|
|
|
|
|
|
bool ret = false;
|
|
|
|
|
if (output->fmtctx->pb) {
|
|
|
|
|
if (output->fmtctx->pb)
|
|
|
|
|
av_write_trailer(output->fmtctx);
|
|
|
|
|
avio_closep(&output->fmtctx->pb);
|
|
|
|
|
ret = true;
|
|
|
|
|
if (output->fp) {
|
|
|
|
|
if (ftell(output->fp))
|
|
|
|
|
ret = true;
|
|
|
|
|
fclose(output->fp);
|
|
|
|
|
output->fp = NULL;
|
|
|
|
|
}
|
|
|
|
|
if (output->avioctx) {
|
|
|
|
|
if (output->avioctx->buffer)
|
|
|
|
|
av_freep(&output->avioctx->buffer);
|
|
|
|
|
av_freep(&output->avioctx);
|
|
|
|
|
}
|
|
|
|
|
avformat_free_context(output->fmtctx);
|
|
|
|
|
|
|
|
|
|
|