111 if ((
delta > 0 && *acc > INT64_MAX -
delta) ||
129 default:
return s->pkt_idx;
166 (
AVRational){ 1, ctx->par_in->sample_rate }, what);
173 ctx->time_base_in, what);
194 return FFMAX(nb_samples, 0);
238 if (ts == INT64_MIN) {
240 "in the stream time base\n",
name,
value);
253 b->value =
b->offset;
254 b->pending =
b->relative;
278 if (!
s->start_bound.active)
287 if (
s->start_bound.pending) {
293 if (v >=
s->start_bound.value)
300 if (!
s->trim_packets ||
av_sat_add64(v, span) <=
s->start_bound.value)
302 *head =
s->start_bound.value - v;
317 if (!
s->end_bound.active)
322 if (
s->end_bound.pending) {
347 if (v >=
s->end_bound.value)
350 if (
s->trim_packets) {
358 if (past >
s->end_bound.value)
359 *tail = past -
s->end_bound.value;
371 int64_t tail = 0, anchor, input_head;
372 int trimming = head != 0;
373 uint8_t head_reason = 0, tail_reason = 0, input_reason;
385 input_head =
s->skip_carry;
386 input_reason =
s->skip_reason;
390 input_reason =
size >= 10 ?
AV_RL8(side + 8) : 0;
395 if (input_head >= head) {
397 head_reason = input_reason;
402 if (!keep || (trimming && nb_samples > 0 && head >= nb_samples))
418 trimming |= tail != 0;
422 if (side &&
size >= 8 &&
AV_RL32(side + 4) >= tail) {
424 tail_reason =
size >= 10 ?
AV_RL8(side + 9) : 0;
427 if (trimming && nb_samples > 0 && head >= nb_samples - tail)
437 if (head > UINT32_MAX || tail > UINT32_MAX) {
442 if (!side ||
size < 10) {
450 AV_WL8 (side + 8, head_reason);
451 AV_WL8 (side + 9, tail_reason);
463 "a dropped packet of unknown sample count\n", head);
466 s->skip_carry =
FFMAX(head - consumed, 0);
467 s->skip_reason =
s->skip_carry ? head_reason : 0;
489 if (head >=
pkt->duration - tail)
502 pkt->duration -= head + tail;
512 while (
s->preroll_fifo &&
av_fifo_read(
s->preroll_fifo, &held, 1) >= 0)
558 "packets in range will not be decodable\n",
s->preroll_size);
570 "pts %s, dts %s, keyframe %d\n", which, idx,
av_ts2str(
pts),
578 s->last_pts =
pkt->pts;
579 s->last_dts =
pkt->dts;
582 if (!
s->nb_exported++)
594 s->last_dts,
s->last_key);
628 if (
s->audio && (!ret || ret ==
AVERROR(EAGAIN)))
632 else if (ret ==
AVERROR(EAGAIN) &&
s->preroll_fifo)
697 if (
s->start == INT64_MIN &&
s->end == INT64_MAX) {
703 s->start_type,
s->start_rel,
"start");
708 s->end_type,
s->end_rel,
"end");
714 if (
s->end_bound.axis ==
AXIS_INDEX &&
s->end_bound.relative)
720 if (
ctx->par_in->sample_rate <= 0 ||
ctx->time_base_in.num <= 0 ||
721 ctx->time_base_in.den <= 0) {
723 "side data, which needs a sample rate and a time base\n");
731 if (
s->preroll &&
s->start_bound.active &&
735 if (!
s->preroll_fifo)
745#define OFFSET(x) offsetof(TrimContext, x)
746#define FLAGS (AV_OPT_FLAG_VIDEO_PARAM|AV_OPT_FLAG_AUDIO_PARAM|AV_OPT_FLAG_BSF_PARAM)
748 {
"start",
"time or index marking the start of the accepted range",
OFFSET(start),
750 {
"start_type",
"how to interpret start",
OFFSET(start_type),
755 {
"msec_pt",
"milliseconds, matched against pts", 0,
AV_OPT_TYPE_CONST, { .i64 =
TRIM_MSEC_PT }, 0, 0,
FLAGS, .unit =
"start_type" },
756 {
"msec_dt",
"milliseconds, matched against dts", 0,
AV_OPT_TYPE_CONST, { .i64 =
TRIM_MSEC_DT }, 0, 0,
FLAGS, .unit =
"start_type" },
757 {
"start_rel",
"interpret start relative to the first packet of the stream",
OFFSET(start_rel),
759 {
"end",
"time or index marking the end of the accepted range",
OFFSET(end),
761 {
"end_type",
"how to interpret end",
OFFSET(end_type),
766 {
"msec_pt",
"milliseconds, matched against pts", 0,
AV_OPT_TYPE_CONST, { .i64 =
TRIM_MSEC_PT }, 0, 0,
FLAGS, .unit =
"end_type" },
767 {
"msec_dt",
"milliseconds, matched against dts", 0,
AV_OPT_TYPE_CONST, { .i64 =
TRIM_MSEC_DT }, 0, 0,
FLAGS, .unit =
"end_type" },
770 {
"end_rel",
"interpret end relative to the first exported packet",
OFFSET(end_rel),
772 {
"trim_packets",
"trim packets straddling a boundary instead of exporting them "
773 "untouched or dropping them",
OFFSET(trim_packets),
775 {
"preroll",
"export the packets the first packet in range needs to be decodable, "
776 "flagged for the decoder to drop them after decoding",
OFFSET(preroll),
778 {
"preroll_size",
"maximum number of packets held for preroll",
OFFSET(preroll_size),
784 .class_name =
"trim",
static AVFormatContext * ctx
static av_cold void close(AVCodecParserContext *s)
const FFBitStreamFilter ff_trim_bsf
int ff_bsf_get_packet_ref(AVBSFContext *ctx, AVPacket *pkt)
Called by bitstream filters to get packet for filtering.
void(* flush)(AVBSFContext *ctx)
int(* init)(AVBSFContext *ctx)
@ AV_OPT_TYPE_CONST
Special option type for declaring named constants.
@ AV_OPT_TYPE_INT64
Underlying C type is int64_t.
@ AV_OPT_TYPE_INT
Underlying C type is int.
@ AV_OPT_TYPE_BOOL
Underlying C type is int.
@ AV_PKT_DATA_SKIP_SAMPLES
Recommends skipping the specified number of samples.
void av_packet_free(AVPacket **pkt)
Free the packet, if the packet is reference counted, it will be unreferenced first.
#define AV_PKT_FLAG_DISCARD
Flag is used to discard packets which are required to maintain valid decoder state but are not requir...
void av_packet_unref(AVPacket *pkt)
Wipe the packet.
uint8_t * av_packet_new_side_data(AVPacket *pkt, enum AVPacketSideDataType type, size_t size)
Allocate new information of a packet.
#define AV_PKT_FLAG_KEY
The packet contains a keyframe.
void av_packet_move_ref(AVPacket *dst, AVPacket *src)
Move every field in src to dst and reset src.
uint8_t * av_packet_get_side_data(const AVPacket *pkt, enum AVPacketSideDataType type, size_t *size)
Get side information from packet.
AVPacket * av_packet_alloc(void)
Allocate an AVPacket and set its fields to default values.
#define AVERROR_EOF
End of file.
AVFifo * av_fifo_alloc2(size_t nb_elems, size_t elem_size, unsigned int flags)
Allocate and initialize an AVFifo with a given element size.
void av_fifo_freep2(AVFifo **f)
Free an AVFifo and reset pointer to NULL.
#define AV_FIFO_FLAG_AUTO_GROW
Automatically resize the FIFO on writes, so that the data fits.
size_t av_fifo_can_read(const AVFifo *f)
int av_fifo_write(AVFifo *f, const void *buf, size_t nb_elems)
Write data into a FIFO.
void av_fifo_auto_grow_limit(AVFifo *f, size_t max_elems)
Set the maximum size (in elements) to which the FIFO can be resized automatically.
int av_fifo_read(AVFifo *f, void *buf, size_t nb_elems)
Read data from a FIFO.
#define AV_LOG_WARNING
Something somehow does not look correct.
#define AV_LOG_VERBOSE
Detailed information.
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
const char * av_default_item_name(void *ptr)
Return the context name.
int64_t av_rescale_q(int64_t a, AVRational bq, AVRational cq)
Rescale a 64-bit integer by 2 rational numbers.
#define AV_NOPTS_VALUE
Undefined timestamp value.
#define LIBAVUTIL_VERSION_INT
static void trim_report(AVBSFContext *ctx)
static void bound_reset(TrimBound *b)
static void log_exported_packet(AVBSFContext *ctx, const char *which, int64_t idx, int64_t pts, int64_t dts, int key)
static void trim_close(AVBSFContext *ctx)
static void trim_flush(AVBSFContext *ctx)
static int samples_to_time_base(AVBSFContext *ctx, int64_t *value, const char *what)
static int add_checked(AVBSFContext *ctx, int64_t *acc, int64_t delta, const char *what)
static int convert_checked(AVBSFContext *ctx, int64_t *value, AVRational from, AVRational to, const char *what)
static void preroll_export(AVBSFContext *ctx, AVPacket *pkt)
static int trim_audio(AVBSFContext *ctx, AVPacket *pkt, int64_t head, int keep)
static const struct @121072265223206255134261043041011175177273217055 trim_types[]
static int bound_resolve(AVBSFContext *ctx, TrimBound *b, int64_t ref, const char *name)
static int64_t packet_axis(const TrimContext *s, const AVPacket *pkt, enum TrimAxis axis)
static int bound_init(AVBSFContext *ctx, TrimBound *b, int active, int64_t value, int type, int rel, const char *name)
static int packet_span(AVBSFContext *ctx, const AVPacket *pkt, enum TrimAxis axis, int64_t *span)
static void trim_reset(AVBSFContext *ctx)
static void packet_exported(AVBSFContext *ctx, const AVPacket *pkt)
static const AVClass trim_class
static int time_base_to_samples(AVBSFContext *ctx, int64_t *value, const char *what)
static enum TrimAxis monotonic_axis(enum TrimAxis axis)
static int trim_tail(AVBSFContext *ctx, const AVPacket *pkt, int64_t head, int64_t *tail)
static int trim_shift(AVBSFContext *ctx, AVPacket *pkt, int64_t head)
static const AVOption trim_options[]
static int axis_is_time(enum TrimAxis axis)
static int trim_head(AVBSFContext *ctx, const AVPacket *pkt, int64_t *head)
static void preroll_clear(AVBSFContext *ctx)
static int trim_filter(AVBSFContext *ctx, AVPacket *pkt)
static int64_t packet_skip_consumed(AVBSFContext *ctx, const AVPacket *pkt)
static int trim_init(AVBSFContext *ctx)
static int preroll_hold(AVBSFContext *ctx, AVPacket *pkt)
static int64_t packet_samples(AVBSFContext *ctx, const AVPacket *pkt)
int av_get_audio_frame_duration2(AVCodecParameters *par, int frame_bytes)
The bitstream filter state.
Describe the class of an AVClass context structure.
This structure stores compressed data.
Rational number (pair of numerator and denominator).
int relative
offset is measured from the reference packet
int active
the option was set at all
int64_t offset
option value converted to axis units
int pending
the reference packet has not been seen yet
int64_t value
resolved bound, meaningful once pending is clear
int64_t pkt_idx
packets consumed so far
int64_t nb_exported
packets that left the filter
int64_t out_idx
packets exported so far
int audio
trim through skip samples side data
AVFifo * preroll_fifo
packets held since the last keyframe, NULL when off
int64_t last_pts
the last of them, kept for the closing summary
int64_t skip_carry
samples of head skip left over by dropped packets
AVPacket * pending
in-range packet waiting for the preroll to drain
int preroll_full
the group overflowed, so hold nothing until the next one
uint8_t skip_reason
reason that head skip came with
void(* filter)(uint8_t *src, ptrdiff_t stride, int qscale)
static int ref[MAX_W *MAX_W]
timestamp utils, mostly useful for debugging/logging purposes
#define av_ts2str(ts)
Convenience macro, the return value should be used only directly in function arguments but never stan...