2 * SBG (SBaGen) file format decoder
3 * Copyright (c) 2011 Nicolas George
5 * This file is part of FFmpeg.
7 * FFmpeg is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * FFmpeg is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with FFmpeg; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
25 #include "libavutil/intreadwrite.h"
26 #include "libavutil/log.h"
27 #include "libavutil/opt.h"
28 #include "libavutil/time_internal.h"
32 #define SBG_SCALE (1 << 16)
33 #define DAY (24 * 60 * 60)
34 #define DAY_TS ((int64_t)DAY * AV_TIME_BASE)
55 int8_t in, out, slide;
67 /* bell: freq constant, ampl decreases exponentially, can be approx lin */
69 struct sbg_timestamp {
71 char type; /* 0 for relative, 'N' for now, 'T' for absolute */
74 struct sbg_script_definition {
77 int elements, nb_elements;
78 char type; /* 'S' or 'B' */
81 struct sbg_script_synth {
85 enum sbg_synth_type type;
91 struct sbg_script_tseq {
92 struct sbg_timestamp ts;
99 struct sbg_script_event {
101 int64_t ts_int, ts_trans, ts_next;
102 int elements, nb_elements;
103 struct sbg_fade fade;
107 struct sbg_script_definition *def;
108 struct sbg_script_synth *synth;
109 struct sbg_script_tseq *tseq;
110 struct sbg_script_tseq *block_tseq;
111 struct sbg_script_event *events;
118 int64_t opt_fade_time;
119 int64_t opt_duration;
122 uint8_t opt_start_at_first;
123 uint8_t opt_end_at_last;
130 struct sbg_script scs;
131 struct sbg_timestamp current_time;
133 int nb_def_max, nb_synth_max, nb_tseq_max, nb_block_tseq_max;
138 enum ws_interval_type {
139 WS_SINE = MKTAG('S','I','N','E'),
140 WS_NOISE = MKTAG('N','O','I','S'),
145 enum ws_interval_type type;
152 struct ws_intervals {
153 struct ws_interval *inter;
158 static void *alloc_array_elem(void **array, size_t elsize,
159 int *size, int *max_size)
163 if (*size == *max_size) {
164 int m = FFMAX(32, FFMIN(*max_size, INT_MAX / 2) * 2);
167 *array = av_realloc_f(*array, m, elsize);
172 ret = (char *)*array + elsize * *size;
173 memset(ret, 0, elsize);
178 static int str_to_time(const char *str, int64_t *rtime)
180 const char *cur = str;
185 if (*cur < '0' || *cur > '9')
187 hours = strtol(cur, &end, 10);
188 if (end == cur || *end != ':' || end[1] < '0' || end[1] > '9')
191 minutes = strtol(cur, &end, 10);
196 seconds = strtod(cur + 1, &end);
200 *rtime = (hours * 3600LL + minutes * 60LL + seconds) * AV_TIME_BASE;
204 static inline int is_space(char c)
206 return c == ' ' || c == '\t' || c == '\r';
209 static inline int scale_double(void *log, double d, double m, int *r)
212 if (m < INT_MIN || m >= INT_MAX) {
214 av_log(log, AV_LOG_ERROR, "%g is too large\n", d);
215 return AVERROR(EDOM);
221 static int lex_space(struct sbg_parser *p)
225 while (p->cursor < p->end && is_space(*p->cursor))
227 return p->cursor > c;
230 static int lex_char(struct sbg_parser *p, char c)
232 int r = p->cursor < p->end && *p->cursor == c;
238 static int lex_double(struct sbg_parser *p, double *r)
243 if (p->cursor == p->end || is_space(*p->cursor) || *p->cursor == '\n')
245 d = strtod(p->cursor, &end);
246 if (end > p->cursor) {
254 static int lex_fixed(struct sbg_parser *p, const char *t, int l)
256 if (p->end - p->cursor < l || memcmp(p->cursor, t, l))
262 static int lex_line_end(struct sbg_parser *p)
264 if (p->cursor < p->end && *p->cursor == '#') {
266 while (p->cursor < p->end && *p->cursor != '\n')
269 if (p->cursor == p->end)
270 /* simulate final LF for files lacking it */
272 if (*p->cursor != '\n')
280 static int lex_wsword(struct sbg_parser *p, struct sbg_string *rs)
282 char *s = p->cursor, *c = s;
284 if (s == p->end || *s == '\n')
286 while (c < p->end && *c != '\n' && !is_space(*c))
289 rs->e = p->cursor = c;
294 static int lex_name(struct sbg_parser *p, struct sbg_string *rs)
296 char *s = p->cursor, *c = s;
298 while (c < p->end && ((*c >= 'a' && *c <= 'z') || (*c >= 'A' && *c <= 'Z')
299 || (*c >= '0' && *c <= '9') || *c == '_' || *c == '-'))
304 rs->e = p->cursor = c;
308 static int lex_time(struct sbg_parser *p, int64_t *rt)
310 int r = str_to_time(p->cursor, rt);
315 #define FORWARD_ERROR(c) \
319 return errcode ? errcode : AVERROR_INVALIDDATA; \
322 static int parse_immediate(struct sbg_parser *p)
324 snprintf(p->err_msg, sizeof(p->err_msg),
325 "immediate sequences not yet implemented");
326 return AVERROR_PATCHWELCOME;
329 static int parse_preprogrammed(struct sbg_parser *p)
331 snprintf(p->err_msg, sizeof(p->err_msg),
332 "preprogrammed sequences not yet implemented");
333 return AVERROR_PATCHWELCOME;
336 static int parse_optarg(struct sbg_parser *p, char o, struct sbg_string *r)
338 if (!lex_wsword(p, r)) {
339 snprintf(p->err_msg, sizeof(p->err_msg),
340 "option '%c' requires an argument", o);
341 return AVERROR_INVALIDDATA;
346 static int parse_options(struct sbg_parser *p)
348 struct sbg_string ostr, oarg;
354 if (p->cursor == p->end || *p->cursor != '-')
356 while (lex_char(p, '-') && lex_wsword(p, &ostr)) {
357 for (; ostr.s < ostr.e; ostr.s++) {
361 p->scs.opt_start_at_first = 1;
364 p->scs.opt_end_at_last = 1;
373 FORWARD_ERROR(parse_optarg(p, opt, &oarg));
374 v = strtod(oarg.s, &tptr);
375 if (oarg.e != tptr) {
376 snprintf(p->err_msg, sizeof(p->err_msg),
377 "syntax error for option -F");
378 return AVERROR_INVALIDDATA;
380 p->scs.opt_fade_time = v * AV_TIME_BASE / 1000;
383 FORWARD_ERROR(parse_optarg(p, opt, &oarg));
384 r = str_to_time(oarg.s, &p->scs.opt_duration);
385 if (oarg.e != oarg.s + r) {
386 snprintf(p->err_msg, sizeof(p->err_msg),
387 "syntax error for option -L");
388 return AVERROR_INVALIDDATA;
392 FORWARD_ERROR(parse_optarg(p, opt, &oarg));
393 r = str_to_time(oarg.s, &p->scs.start_ts);
394 if (oarg.e != oarg.s + r) {
395 snprintf(p->err_msg, sizeof(p->err_msg),
396 "syntax error for option -T");
397 return AVERROR_INVALIDDATA;
401 FORWARD_ERROR(parse_optarg(p, opt, &oarg));
402 tptr = av_malloc(oarg.e - oarg.s + 1);
404 return AVERROR(ENOMEM);
405 memcpy(tptr, oarg.s, oarg.e - oarg.s);
406 tptr[oarg.e - oarg.s] = 0;
407 av_free(p->scs.opt_mix);
408 p->scs.opt_mix = tptr;
411 FORWARD_ERROR(parse_optarg(p, opt, &oarg));
412 v = strtod(oarg.s, &tptr);
413 if (oarg.e != tptr) {
414 snprintf(p->err_msg, sizeof(p->err_msg),
415 "syntax error for option -q");
416 return AVERROR_INVALIDDATA;
419 snprintf(p->err_msg, sizeof(p->err_msg),
420 "speed factor other than 1 not supported");
421 return AVERROR_PATCHWELCOME;
425 FORWARD_ERROR(parse_optarg(p, opt, &oarg));
426 r = strtol(oarg.s, &tptr, 10);
427 if (oarg.e != tptr) {
428 snprintf(p->err_msg, sizeof(p->err_msg),
429 "syntax error for option -r");
430 return AVERROR_INVALIDDATA;
433 snprintf(p->err_msg, sizeof(p->err_msg),
434 "invalid sample rate");
435 return AVERROR_PATCHWELCOME;
437 p->scs.sample_rate = r;
440 snprintf(p->err_msg, sizeof(p->err_msg),
441 "unknown option: '%c'", *ostr.s);
442 return AVERROR_INVALIDDATA;
448 return parse_immediate(p);
450 return parse_preprogrammed(p);
452 if (!lex_line_end(p))
453 return AVERROR_INVALIDDATA;
459 static int parse_timestamp(struct sbg_parser *p,
460 struct sbg_timestamp *rts, int64_t *rrel)
462 int64_t abs = 0, rel = 0, dt;
466 if (lex_fixed(p, "NOW", 3)) {
470 r = lex_time(p, &abs);
474 while (lex_char(p, '+')) {
475 if (!lex_time(p, &dt))
476 return AVERROR_INVALIDDATA;
477 if (av_sat_add64(rel, dt) - dt != rel)
478 return AVERROR_INVALIDDATA;
484 return AVERROR_INVALIDDATA;
492 static int parse_fade(struct sbg_parser *p, struct sbg_fade *fr)
494 struct sbg_fade f = {0};
496 if (lex_char(p, '<'))
497 f.in = SBG_FADE_SILENCE;
498 else if (lex_char(p, '-'))
499 f.in = SBG_FADE_SAME;
500 else if (lex_char(p, '='))
501 f.in = SBG_FADE_ADAPT;
504 if (lex_char(p, '>'))
505 f.out = SBG_FADE_SILENCE;
506 else if (lex_char(p, '-'))
507 f.out = SBG_FADE_SAME;
508 else if (lex_char(p, '='))
509 f.out = SBG_FADE_ADAPT;
511 return AVERROR_INVALIDDATA;
516 static int parse_time_sequence(struct sbg_parser *p, int inblock)
518 struct sbg_timestamp ts;
521 struct sbg_fade fade = { SBG_FADE_SAME, SBG_FADE_SAME, 0 };
522 struct sbg_string name;
523 struct sbg_script_tseq *tseq;
525 r = parse_timestamp(p, &ts, &rel_ts);
532 return AVERROR_INVALIDDATA;
533 p->current_time.type = ts.type;
534 p->current_time.t = ts.t;
535 } else if(!inblock && !p->current_time.type) {
536 snprintf(p->err_msg, sizeof(p->err_msg),
537 "relative time without previous absolute time");
538 return AVERROR_INVALIDDATA;
540 ts.type = p->current_time.type;
541 ts.t = p->current_time.t + rel_ts;
542 r = parse_fade(p, &fade);
546 if (!lex_name(p, &name))
547 return AVERROR_INVALIDDATA;
549 if (lex_fixed(p, "->", 2)) {
550 fade.slide = SBG_FADE_ADAPT;
553 if (!lex_line_end(p))
554 return AVERROR_INVALIDDATA;
556 alloc_array_elem((void **)&p->scs.block_tseq, sizeof(*tseq),
557 &p->nb_block_tseq, &p->nb_block_tseq_max) :
558 alloc_array_elem((void **)&p->scs.tseq, sizeof(*tseq),
559 &p->scs.nb_tseq, &p->nb_tseq_max);
561 return AVERROR(ENOMEM);
564 tseq->name_len = name.e - name.s;
569 static int parse_wave_def(struct sbg_parser *p, int wavenum)
571 snprintf(p->err_msg, sizeof(p->err_msg),
572 "waveform definitions not yet implemented");
573 return AVERROR_PATCHWELCOME;
576 static int parse_block_def(struct sbg_parser *p,
577 struct sbg_script_definition *def)
582 if (!lex_line_end(p))
583 return AVERROR_INVALIDDATA;
584 tseq = p->nb_block_tseq;
586 r = parse_time_sequence(p, 1);
592 if (!lex_char(p, '}'))
593 return AVERROR_INVALIDDATA;
595 if (!lex_line_end(p))
596 return AVERROR_INVALIDDATA;
598 def->elements = tseq;
599 def->nb_elements = p->nb_block_tseq - tseq;
600 if (!def->nb_elements)
601 return AVERROR_INVALIDDATA;
605 static int parse_volume(struct sbg_parser *p, int *vol)
609 if (!lex_char(p, '/'))
611 if (!lex_double(p, &v))
612 return AVERROR_INVALIDDATA;
613 if (scale_double(p->log, v, 0.01, vol))
614 return AVERROR(ERANGE);
618 static int parse_synth_channel_sine(struct sbg_parser *p,
619 struct sbg_script_synth *synth)
621 double carrierf, beatf;
622 int carrier, beat, vol;
624 if (!lex_double(p, &carrierf))
626 if (!lex_double(p, &beatf))
628 FORWARD_ERROR(parse_volume(p, &vol));
629 if (scale_double(p->log, carrierf, 1, &carrier) < 0 ||
630 scale_double(p->log, beatf, 1, &beat) < 0)
631 return AVERROR(EDOM);
632 synth->type = SBG_TYPE_SINE;
633 synth->carrier = carrier;
639 static int parse_synth_channel_pink(struct sbg_parser *p,
640 struct sbg_script_synth *synth)
644 if (!lex_fixed(p, "pink", 4))
646 FORWARD_ERROR(parse_volume(p, &vol));
647 synth->type = SBG_TYPE_NOISE;
652 static int parse_synth_channel_bell(struct sbg_parser *p,
653 struct sbg_script_synth *synth)
658 if (!lex_fixed(p, "bell", 4))
660 if (!lex_double(p, &carrierf))
661 return AVERROR_INVALIDDATA;
662 FORWARD_ERROR(parse_volume(p, &vol));
663 if (scale_double(p->log, carrierf, 1, &carrier) < 0)
664 return AVERROR(EDOM);
665 synth->type = SBG_TYPE_BELL;
666 synth->carrier = carrier;
671 static int parse_synth_channel_mix(struct sbg_parser *p,
672 struct sbg_script_synth *synth)
676 if (!lex_fixed(p, "mix", 3))
678 FORWARD_ERROR(parse_volume(p, &vol));
679 synth->type = SBG_TYPE_MIX;
684 static int parse_synth_channel_spin(struct sbg_parser *p,
685 struct sbg_script_synth *synth)
687 double carrierf, beatf;
688 int carrier, beat, vol;
690 if (!lex_fixed(p, "spin:", 5))
692 if (!lex_double(p, &carrierf))
693 return AVERROR_INVALIDDATA;
694 if (!lex_double(p, &beatf))
695 return AVERROR_INVALIDDATA;
696 FORWARD_ERROR(parse_volume(p, &vol));
697 if (scale_double(p->log, carrierf, 1, &carrier) < 0 ||
698 scale_double(p->log, beatf, 1, &beat) < 0)
699 return AVERROR(EDOM);
700 synth->type = SBG_TYPE_SPIN;
701 synth->carrier = carrier;
707 static int parse_synth_channel(struct sbg_parser *p)
710 struct sbg_script_synth *synth;
712 synth = alloc_array_elem((void **)&p->scs.synth, sizeof(*synth),
713 &p->scs.nb_synth, &p->nb_synth_max);
715 return AVERROR(ENOMEM);
716 r = lex_char(p, '-');
718 r = parse_synth_channel_pink(p, synth);
720 r = parse_synth_channel_bell(p, synth);
722 r = parse_synth_channel_mix(p, synth);
724 r = parse_synth_channel_spin(p, synth);
725 /* Unimplemented: wave%d:%f%f/vol (carrier, beat) */
727 r = parse_synth_channel_sine(p, synth);
733 static int parse_synth_def(struct sbg_parser *p,
734 struct sbg_script_definition *def)
738 synth = p->scs.nb_synth;
740 r = parse_synth_channel(p);
743 if (!r || !lex_space(p))
747 if (synth == p->scs.nb_synth)
748 return AVERROR_INVALIDDATA;
749 if (!lex_line_end(p))
750 return AVERROR_INVALIDDATA;
752 def->elements = synth;
753 def->nb_elements = p->scs.nb_synth - synth;
757 static int parse_named_def(struct sbg_parser *p)
759 char *cursor_save = p->cursor;
760 struct sbg_string name;
761 struct sbg_script_definition *def;
763 if (!lex_name(p, &name) || !lex_char(p, ':') || !lex_space(p)) {
764 p->cursor = cursor_save;
767 if (name.e - name.s == 6 && !memcmp(name.s, "wave", 4) &&
768 name.s[4] >= '0' && name.s[4] <= '9' &&
769 name.s[5] >= '0' && name.s[5] <= '9') {
770 int wavenum = (name.s[4] - '0') * 10 + (name.s[5] - '0');
771 return parse_wave_def(p, wavenum);
773 def = alloc_array_elem((void **)&p->scs.def, sizeof(*def),
774 &p->scs.nb_def, &p->nb_def_max);
776 return AVERROR(ENOMEM);
778 def->name_len = name.e - name.s;
779 if (lex_char(p, '{'))
780 return parse_block_def(p, def);
781 return parse_synth_def(p, def);
784 static void free_script(struct sbg_script *s)
789 av_freep(&s->block_tseq);
790 av_freep(&s->events);
791 av_freep(&s->opt_mix);
794 static int parse_script(void *log, char *script, int script_len,
795 struct sbg_script *rscript)
797 struct sbg_parser sp = {
800 .end = script + script_len,
806 .start_ts = AV_NOPTS_VALUE,
807 .sample_rate = 44100,
808 .opt_fade_time = 60 * AV_TIME_BASE,
814 while (sp.cursor < sp.end) {
815 r = parse_options(&sp);
818 if (!r && !lex_line_end(&sp))
821 while (sp.cursor < sp.end) {
822 r = parse_named_def(&sp);
824 r = parse_time_sequence(&sp, 0);
826 r = lex_line_end(&sp) ? 1 : AVERROR_INVALIDDATA;
833 free_script(&sp.scs);
835 if (r == AVERROR_INVALIDDATA)
836 snprintf(sp.err_msg, sizeof(sp.err_msg), "syntax error");
837 if (log && *sp.err_msg) {
838 const char *ctx = sp.cursor;
839 const char *ectx = av_x_if_null(memchr(ctx, '\n', sp.end - sp.cursor),
841 int lctx = ectx - ctx;
842 const char *quote = "\"";
843 if (lctx > 0 && ctx[lctx - 1] == '\r')
846 ctx = "the end of line";
850 av_log(log, AV_LOG_ERROR, "Error line %d: %s near %s%.*s%s.\n",
851 sp.line_no, sp.err_msg, quote, lctx, ctx, quote);
856 static int read_whole_file(AVIOContext *io, int max_size, char **rbuf)
859 int size = 0, bufsize = 0, r;
862 if (bufsize - size < 1024) {
863 bufsize = FFMIN(FFMAX(2 * bufsize, 8192), max_size);
864 if (bufsize - size < 2) {
865 size = AVERROR(EFBIG);
868 buf = av_realloc_f(buf, bufsize, 1);
870 size = AVERROR(ENOMEM);
874 r = avio_read(io, buf, bufsize - size - 1);
875 if (r == AVERROR_EOF)
889 static void expand_timestamps(void *log, struct sbg_script *s)
892 int64_t now, cur_ts, delta = 0;
894 for (i = 0; i < s->nb_tseq; i++)
895 nb_rel += s->tseq[i].ts.type == 'N';
896 if (nb_rel == s->nb_tseq) {
897 /* All ts are relative to NOW: consider NOW = 0 */
899 if (s->start_ts != AV_NOPTS_VALUE)
900 av_log(log, AV_LOG_WARNING,
901 "Start time ignored in a purely relative script.\n");
902 } else if (nb_rel == 0 && s->start_ts != AV_NOPTS_VALUE ||
903 s->opt_start_at_first) {
904 /* All ts are absolute and start time is specified */
905 if (s->start_ts == AV_NOPTS_VALUE)
906 s->start_ts = s->tseq[0].ts.t;
909 /* Mixed relative/absolute ts: expand */
911 struct tm *tm, tmpbuf;
913 av_log(log, AV_LOG_WARNING,
914 "Scripts with mixed absolute and relative timestamps can give "
915 "unexpected results (pause, seeking, time zone change).\n");
918 tm = localtime_r(&now0, &tmpbuf);
919 now = tm ? tm->tm_hour * 3600 + tm->tm_min * 60 + tm->tm_sec :
921 av_log(log, AV_LOG_INFO, "Using %02d:%02d:%02d as NOW.\n",
922 (int)(now / 3600), (int)(now / 60) % 60, (int)now % 60);
924 for (i = 0; i < s->nb_tseq; i++) {
925 if (s->tseq[i].ts.type == 'N') {
926 s->tseq[i].ts.t += now;
927 s->tseq[i].ts.type = 'T'; /* not necessary */
931 if (s->start_ts == AV_NOPTS_VALUE)
932 s->start_ts = (s->opt_start_at_first && s->tseq) ? s->tseq[0].ts.t : now;
933 s->end_ts = s->opt_duration ? s->start_ts + s->opt_duration :
934 AV_NOPTS_VALUE; /* may be overridden later by -E option */
936 for (i = 0; i < s->nb_tseq; i++) {
937 if (s->tseq[i].ts.t + delta < cur_ts)
939 cur_ts = s->tseq[i].ts.t += delta;
943 static int expand_tseq(void *log, struct sbg_script *s, int *nb_ev_max,
944 int64_t t0, struct sbg_script_tseq *tseq)
947 struct sbg_script_definition *def;
948 struct sbg_script_tseq *be;
949 struct sbg_script_event *ev;
952 av_log(log, AV_LOG_ERROR, "Recursion loop on \"%.*s\"\n",
953 tseq->name_len, tseq->name);
954 return AVERROR(EINVAL);
957 for (i = 0; i < s->nb_def; i++) {
958 if (s->def[i].name_len == tseq->name_len &&
959 !memcmp(s->def[i].name, tseq->name, tseq->name_len))
962 if (i >= s->nb_def) {
963 av_log(log, AV_LOG_ERROR, "Tone-set \"%.*s\" not defined\n",
964 tseq->name_len, tseq->name);
965 return AVERROR(EINVAL);
968 if (def->type == 'B') {
969 be = s->block_tseq + def->elements;
970 for (i = 0; i < def->nb_elements; i++) {
971 r = expand_tseq(log, s, nb_ev_max, t0, &be[i]);
976 ev = alloc_array_elem((void **)&s->events, sizeof(*ev),
977 &s->nb_events, nb_ev_max);
979 return AVERROR(ENOMEM);
981 ev->elements = def->elements;
982 ev->nb_elements = def->nb_elements;
983 ev->fade = tseq->fade;
989 static int expand_script(void *log, struct sbg_script *s)
991 int i, r, nb_events_max = 0;
993 expand_timestamps(log, s);
994 for (i = 0; i < s->nb_tseq; i++) {
995 r = expand_tseq(log, s, &nb_events_max, 0, &s->tseq[i]);
1000 av_log(log, AV_LOG_ERROR, "No events in script\n");
1001 return AVERROR_INVALIDDATA;
1003 if (s->opt_end_at_last)
1004 s->end_ts = s->events[s->nb_events - 1].ts;
1008 static int add_interval(struct ws_intervals *inter,
1009 enum ws_interval_type type, uint32_t channels, int ref,
1010 int64_t ts1, int32_t f1, int32_t a1,
1011 int64_t ts2, int32_t f2, int32_t a2)
1013 struct ws_interval *i, *ri;
1016 ri = &inter->inter[ref];
1017 /* ref and new intervals are constant, identical and adjacent */
1018 if (ri->type == type && ri->channels == channels &&
1019 ri->f1 == ri->f2 && ri->f2 == f1 && f1 == f2 &&
1020 ri->a1 == ri->a2 && ri->a2 == a1 && a1 == a2 &&
1026 i = alloc_array_elem((void **)&inter->inter, sizeof(*i),
1027 &inter->nb_inter, &inter->max_inter);
1029 return AVERROR(ENOMEM);
1033 i->channels = channels;
1038 i->phi = ref >= 0 ? ref | 0x80000000 : 0;
1039 return i - inter->inter;
1042 static int add_bell(struct ws_intervals *inter, struct sbg_script *s,
1043 int64_t ts1, int64_t ts2, int32_t f, int32_t a)
1045 /* SBaGen uses an exponential decrease every 50ms.
1046 We approximate it with piecewise affine segments. */
1047 int32_t cpoints[][2] = {
1057 int64_t dt = s->sample_rate / 20, ts3 = ts1, ts4;
1058 for (i = 0; i < FF_ARRAY_ELEMS(cpoints); i++) {
1059 ts4 = FFMIN(ts2, ts1 + cpoints[i][0] * dt);
1060 r = add_interval(inter, WS_SINE, 3, -1,
1061 ts3, f, a, ts4, f, cpoints[i][1]);
1070 static int generate_interval(void *log, struct sbg_script *s,
1071 struct ws_intervals *inter,
1072 int64_t ts1, int64_t ts2,
1073 struct sbg_script_synth *s1,
1074 struct sbg_script_synth *s2,
1079 if (ts2 <= ts1 || (s1->vol == 0 && s2->vol == 0))
1085 if (s1->beat == 0 && s2->beat == 0) {
1086 r = add_interval(inter, WS_SINE, 3, s1->ref.l,
1087 ts1, s1->carrier, s1->vol,
1088 ts2, s2->carrier, s2->vol);
1091 s2->ref.l = s2->ref.r = r;
1093 r = add_interval(inter, WS_SINE, 1, s1->ref.l,
1094 ts1, s1->carrier + s1->beat / 2, s1->vol,
1095 ts2, s2->carrier + s2->beat / 2, s2->vol);
1099 r = add_interval(inter, WS_SINE, 2, s1->ref.r,
1100 ts1, s1->carrier - s1->beat / 2, s1->vol,
1101 ts2, s2->carrier - s2->beat / 2, s2->vol);
1109 if (transition == 2) {
1110 r = add_bell(inter, s, ts1, ts2, s1->carrier, s2->vol);
1117 av_log(log, AV_LOG_WARNING, "Spinning noise not implemented, "
1118 "using pink noise instead.\n");
1120 case SBG_TYPE_NOISE:
1121 /* SBaGen's pink noise generator uses:
1122 - 1 band of white noise, mean square: 1/3;
1123 - 9 bands of subsampled white noise with linear
1124 interpolation, mean square: 2/3 each;
1125 with 1/10 weight each: the total mean square is 7/300.
1126 Our pink noise generator uses 8 bands of white noise with
1127 rectangular subsampling: the total mean square is 1/24.
1128 Therefore, to match SBaGen's volume, we must multiply vol by
1129 sqrt((7/300) / (1/24)) = sqrt(14/25) =~ 0.748
1131 r = add_interval(inter, WS_NOISE, 3, s1->ref.l,
1132 ts1, 0, s1->vol - s1->vol / 4,
1133 ts2, 0, s2->vol - s2->vol / 4);
1136 s2->ref.l = s2->ref.r = r;
1140 /* Unimplemented: silence; warning present elsewhere */
1142 av_log(log, AV_LOG_ERROR,
1143 "Type %d is not implemented\n", s1->type);
1144 return AVERROR_PATCHWELCOME;
1149 static int generate_plateau(void *log, struct sbg_script *s,
1150 struct ws_intervals *inter,
1151 struct sbg_script_event *ev1)
1153 int64_t ts1 = ev1->ts_int, ts2 = ev1->ts_trans;
1155 struct sbg_script_synth *s1;
1157 for (i = 0; i < ev1->nb_elements; i++) {
1158 s1 = &s->synth[ev1->elements + i];
1159 r = generate_interval(log, s, inter, ts1, ts2, s1, s1, 0);
1168 ts1 ts2 ts1 tsmid ts2
1173 ''''....____ ''....''
1175 compatible transition incompatible transition
1178 static int generate_transition(void *log, struct sbg_script *s,
1179 struct ws_intervals *inter,
1180 struct sbg_script_event *ev1,
1181 struct sbg_script_event *ev2)
1183 int64_t ts1 = ev1->ts_trans, ts2 = ev1->ts_next;
1184 /* (ts1 + ts2) / 2 without overflow */
1185 int64_t tsmid = (ts1 >> 1) + (ts2 >> 1) + (ts1 & ts2 & 1);
1186 enum sbg_fade_type type = ev1->fade.slide | (ev1->fade.out & ev2->fade.in);
1187 int nb_elements = FFMAX(ev1->nb_elements, ev2->nb_elements);
1188 struct sbg_script_synth *s1, *s2, s1mod, s2mod, smid;
1191 for (pass = 0; pass < 2; pass++) {
1192 /* pass = 0 -> compatible and first half of incompatible
1193 pass = 1 -> second half of incompatible
1194 Using two passes like that ensures that the intervals are generated
1195 in increasing order according to their start timestamp.
1196 Otherwise it would be necessary to sort them
1197 while keeping the mutual references.
1199 for (i = 0; i < nb_elements; i++) {
1200 s1 = i < ev1->nb_elements ? &s->synth[ev1->elements + i] : &s1mod;
1201 s2 = i < ev2->nb_elements ? &s->synth[ev2->elements + i] : &s2mod;
1202 s1mod = s1 != &s1mod ? *s1 : (struct sbg_script_synth){ 0 };
1203 s2mod = s2 != &s2mod ? *s2 : (struct sbg_script_synth){ 0 };
1204 if (ev1->fade.slide) {
1205 /* for slides, and only for slides, silence ("-") is equivalent
1206 to anything with volume 0 */
1207 if (s1mod.type == SBG_TYPE_NONE) {
1210 } else if (s2mod.type == SBG_TYPE_NONE) {
1215 if (s1mod.type == s2mod.type &&
1216 s1mod.type != SBG_TYPE_BELL &&
1217 (type == SBG_FADE_ADAPT ||
1218 (s1mod.carrier == s2mod.carrier &&
1219 s1mod.beat == s2mod.beat))) {
1220 /* compatible: single transition */
1222 r = generate_interval(log, s, inter,
1223 ts1, ts2, &s1mod, &s2mod, 3);
1226 s2->ref = s2mod.ref;
1229 /* incompatible: silence at midpoint */
1233 r = generate_interval(log, s, inter,
1234 ts1, tsmid, &s1mod, &smid, 1);
1240 r = generate_interval(log, s, inter,
1241 tsmid, ts2, &smid, &s2mod, 2);
1244 s2->ref = s2mod.ref;
1253 ev1 trats ev2 intts endts ev3
1258 '''....________________....''' '''...._______________
1260 \_________/\______________/\_________/\______________/\_________/\_____________/
1261 tr x->1 int1 tr 1->2 int2 tr 2->3 int3
1264 static int generate_intervals(void *log, struct sbg_script *s, int sample_rate,
1265 struct ws_intervals *inter)
1267 int64_t trans_time = s->opt_fade_time / 2;
1268 struct sbg_script_event ev0, *ev1, *ev2;
1272 /* SBaGen handles the time before and after the extremal events,
1273 and the corresponding transitions, as if the sequence were cyclic
1274 with a 24-hours period. */
1275 period = s->events[s->nb_events - 1].ts - s->events[0].ts;
1276 period = (period + (DAY_TS - 1)) / DAY_TS * DAY_TS;
1277 period = FFMAX(period, DAY_TS);
1279 /* Prepare timestamps for transitions */
1280 for (i = 0; i < s->nb_events; i++) {
1281 ev1 = &s->events[i];
1282 ev2 = &s->events[(i + 1) % s->nb_events];
1283 ev1->ts_int = ev1->ts;
1284 ev1->ts_trans = ev1->fade.slide ? ev1->ts
1285 : ev2->ts + (ev1 < ev2 ? 0 : period);
1287 for (i = 0; i < s->nb_events; i++) {
1288 ev1 = &s->events[i];
1289 ev2 = &s->events[(i + 1) % s->nb_events];
1290 if (!ev1->fade.slide) {
1291 ev1->ts_trans = FFMAX(ev1->ts_int, ev1->ts_trans - trans_time);
1292 ev2->ts_int = FFMIN(ev2->ts_trans, ev2->ts_int + trans_time);
1294 ev1->ts_next = ev2->ts_int + (ev1 < ev2 ? 0 : period);
1297 /* Pseudo event before the first one */
1298 ev0 = s->events[s->nb_events - 1];
1299 ev0.ts_int -= period;
1300 ev0.ts_trans -= period;
1301 ev0.ts_next -= period;
1303 /* Convert timestamps */
1304 for (i = -1; i < s->nb_events; i++) {
1305 ev1 = i < 0 ? &ev0 : &s->events[i];
1306 ev1->ts_int = av_rescale(ev1->ts_int, sample_rate, AV_TIME_BASE);
1307 ev1->ts_trans = av_rescale(ev1->ts_trans, sample_rate, AV_TIME_BASE);
1308 ev1->ts_next = av_rescale(ev1->ts_next, sample_rate, AV_TIME_BASE);
1311 /* Generate intervals */
1312 for (i = 0; i < s->nb_synth; i++)
1313 s->synth[i].ref.l = s->synth[i].ref.r = -1;
1314 for (i = -1; i < s->nb_events; i++) {
1315 ev1 = i < 0 ? &ev0 : &s->events[i];
1316 ev2 = &s->events[(i + 1) % s->nb_events];
1317 r = generate_plateau(log, s, inter, ev1);
1320 r = generate_transition(log, s, inter, ev1, ev2);
1324 if (!inter->nb_inter)
1325 av_log(log, AV_LOG_WARNING, "Completely silent script.\n");
1329 static int encode_intervals(struct sbg_script *s, AVCodecParameters *par,
1330 struct ws_intervals *inter)
1332 int i, edata_size = 4, ret;
1335 for (i = 0; i < inter->nb_inter; i++) {
1336 edata_size += inter->inter[i].type == WS_SINE ? 44 :
1337 inter->inter[i].type == WS_NOISE ? 32 : 0;
1339 return AVERROR(ENOMEM);
1341 if ((ret = ff_alloc_extradata(par, edata_size)) < 0)
1343 edata = par->extradata;
1345 #define ADD_EDATA32(v) do { AV_WL32(edata, (v)); edata += 4; } while(0)
1346 #define ADD_EDATA64(v) do { AV_WL64(edata, (v)); edata += 8; } while(0)
1347 ADD_EDATA32(inter->nb_inter);
1348 for (i = 0; i < inter->nb_inter; i++) {
1349 ADD_EDATA64(inter->inter[i].ts1);
1350 ADD_EDATA64(inter->inter[i].ts2);
1351 ADD_EDATA32(inter->inter[i].type);
1352 ADD_EDATA32(inter->inter[i].channels);
1353 switch (inter->inter[i].type) {
1355 ADD_EDATA32(inter->inter[i].f1);
1356 ADD_EDATA32(inter->inter[i].f2);
1357 ADD_EDATA32(inter->inter[i].a1);
1358 ADD_EDATA32(inter->inter[i].a2);
1359 ADD_EDATA32(inter->inter[i].phi);
1362 ADD_EDATA32(inter->inter[i].a1);
1363 ADD_EDATA32(inter->inter[i].a2);
1367 if (edata != par->extradata + edata_size)
1372 static av_cold int sbg_read_probe(const AVProbeData *p)
1375 struct sbg_script script = { 0 };
1377 r = parse_script(NULL, p->buf, p->buf_size, &script);
1378 score = r < 0 || !script.nb_def || !script.nb_tseq ? 0 :
1379 AVPROBE_SCORE_MAX / 3;
1380 free_script(&script);
1384 static av_cold int sbg_read_header(AVFormatContext *avf)
1386 struct sbg_demuxer *sbg = avf->priv_data;
1389 struct sbg_script script = { 0 };
1391 struct ws_intervals inter = { 0 };
1393 r = read_whole_file(avf->pb, sbg->max_file_size, &buf);
1396 r = parse_script(avf, buf, r, &script);
1399 if (!sbg->sample_rate)
1400 sbg->sample_rate = script.sample_rate;
1402 script.sample_rate = sbg->sample_rate;
1403 if (!sbg->frame_size)
1404 sbg->frame_size = FFMAX(1, sbg->sample_rate / 10);
1406 av_log(avf, AV_LOG_WARNING, "Mix feature not implemented: "
1407 "-m is ignored and mix channels will be silent.\n");
1408 r = expand_script(avf, &script);
1412 r = generate_intervals(avf, &script, sbg->sample_rate, &inter);
1416 st = avformat_new_stream(avf, NULL);
1418 return AVERROR(ENOMEM);
1419 st->codecpar->codec_type = AVMEDIA_TYPE_AUDIO;
1420 st->codecpar->codec_id = AV_CODEC_ID_FFWAVESYNTH;
1421 st->codecpar->channels = 2;
1422 st->codecpar->channel_layout = AV_CH_LAYOUT_STEREO;
1423 st->codecpar->sample_rate = sbg->sample_rate;
1424 st->codecpar->frame_size = sbg->frame_size;
1425 avpriv_set_pts_info(st, 64, 1, st->codecpar->sample_rate);
1426 st->probe_packets = 0;
1427 st->start_time = av_rescale(script.start_ts,
1428 sbg->sample_rate, AV_TIME_BASE);
1429 st->duration = script.end_ts == AV_NOPTS_VALUE ? AV_NOPTS_VALUE :
1430 av_rescale(script.end_ts - script.start_ts,
1431 sbg->sample_rate, AV_TIME_BASE);
1432 st->cur_dts = st->start_time;
1433 r = encode_intervals(&script, st->codecpar, &inter);
1437 av_free(inter.inter);
1438 free_script(&script);
1442 av_free(inter.inter);
1443 free_script(&script);
1448 static int sbg_read_packet(AVFormatContext *avf, AVPacket *packet)
1453 ts = avf->streams[0]->cur_dts;
1454 end_ts = ts + avf->streams[0]->codecpar->frame_size;
1455 if (avf->streams[0]->duration != AV_NOPTS_VALUE)
1456 end_ts = FFMIN(avf->streams[0]->start_time + avf->streams[0]->duration,
1460 if ((ret = av_new_packet(packet, 12)) < 0)
1462 packet->dts = packet->pts = ts;
1463 packet->duration = end_ts - ts;
1464 AV_WL64(packet->data + 0, ts);
1465 AV_WL32(packet->data + 8, packet->duration);
1466 return packet->size;
1469 static int sbg_read_seek2(AVFormatContext *avf, int stream_index,
1470 int64_t min_ts, int64_t ts, int64_t max_ts, int flags)
1472 if (flags || stream_index > 0)
1473 return AVERROR(EINVAL);
1474 if (stream_index < 0)
1475 ts = av_rescale_q(ts, AV_TIME_BASE_Q, avf->streams[0]->time_base);
1476 avf->streams[0]->cur_dts = ts;
1480 static int sbg_read_seek(AVFormatContext *avf, int stream_index,
1481 int64_t ts, int flags)
1483 return sbg_read_seek2(avf, stream_index, ts, ts, ts, 0);
1486 static const AVOption sbg_options[] = {
1487 { "sample_rate", "", offsetof(struct sbg_demuxer, sample_rate),
1488 AV_OPT_TYPE_INT, { .i64 = 0 }, 0, INT_MAX,
1489 AV_OPT_FLAG_DECODING_PARAM },
1490 { "frame_size", "", offsetof(struct sbg_demuxer, frame_size),
1491 AV_OPT_TYPE_INT, { .i64 = 0 }, 0, INT_MAX,
1492 AV_OPT_FLAG_DECODING_PARAM },
1493 { "max_file_size", "", offsetof(struct sbg_demuxer, max_file_size),
1494 AV_OPT_TYPE_INT, { .i64 = 5000000 }, 0, INT_MAX,
1495 AV_OPT_FLAG_DECODING_PARAM },
1499 static const AVClass sbg_demuxer_class = {
1500 .class_name = "sbg_demuxer",
1501 .item_name = av_default_item_name,
1502 .option = sbg_options,
1503 .version = LIBAVUTIL_VERSION_INT,
1506 AVInputFormat ff_sbg_demuxer = {
1508 .long_name = NULL_IF_CONFIG_SMALL("SBaGen binaural beats script"),
1509 .priv_data_size = sizeof(struct sbg_demuxer),
1510 .read_probe = sbg_read_probe,
1511 .read_header = sbg_read_header,
1512 .read_packet = sbg_read_packet,
1513 .read_seek = sbg_read_seek,
1514 .read_seek2 = sbg_read_seek2,
1515 .extensions = "sbg",
1516 .priv_class = &sbg_demuxer_class,