FFmpeg
flac_parser.c
Go to the documentation of this file.
1 /*
2  * FLAC parser
3  * Copyright (c) 2010 Michael Chinen
4  *
5  * This file is part of FFmpeg.
6  *
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.
11  *
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.
16  *
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
20  */
21 
22 /**
23  * @file
24  * FLAC parser
25  *
26  * The FLAC parser buffers input until FLAC_MIN_HEADERS has been found.
27  * Each time it finds and verifies a CRC-8 header it sees which of the
28  * FLAC_MAX_SEQUENTIAL_HEADERS that came before it have a valid CRC-16 footer
29  * that ends at the newly found header.
30  * Headers are scored by FLAC_HEADER_BASE_SCORE plus the max of its crc-verified
31  * children, penalized by changes in sample rate, frame number, etc.
32  * The parser returns the frame with the highest score.
33  **/
34 
35 #include "libavutil/attributes.h"
36 #include "libavutil/crc.h"
37 #include "libavutil/fifo.h"
38 #include "bytestream.h"
39 #include "parser.h"
40 #include "flac.h"
41 
42 /** maximum number of adjacent headers that compare CRCs against each other */
43 #define FLAC_MAX_SEQUENTIAL_HEADERS 4
44 /** minimum number of headers buffered and checked before returning frames */
45 #define FLAC_MIN_HEADERS 10
46 /** estimate for average size of a FLAC frame */
47 #define FLAC_AVG_FRAME_SIZE 8192
48 
49 /** scoring settings for score_header */
50 #define FLAC_HEADER_BASE_SCORE 10
51 #define FLAC_HEADER_CHANGED_PENALTY 7
52 #define FLAC_HEADER_CRC_FAIL_PENALTY 50
53 #define FLAC_HEADER_NOT_PENALIZED_YET 100000
54 #define FLAC_HEADER_NOT_SCORED_YET -100000
55 
56 /** largest possible size of flac header */
57 #define MAX_FRAME_HEADER_SIZE 16
58 #define MAX_FRAME_VERIFY_SIZE (MAX_FRAME_HEADER_SIZE + 1)
59 
60 typedef struct FLACHeaderMarker {
61  int offset; /**< byte offset from start of FLACParseContext->buffer */
62  int link_penalty[FLAC_MAX_SEQUENTIAL_HEADERS]; /**< array of local scores
63  between this header and the one at a distance equal
64  array position */
65  int max_score; /**< maximum score found after checking each child that
66  has a valid CRC */
67  FLACFrameInfo fi; /**< decoded frame header info */
68  struct FLACHeaderMarker *next; /**< next CRC-8 verified header that
69  immediately follows this one in
70  the bytestream */
71  struct FLACHeaderMarker *best_child; /**< following frame header with
72  which this frame has the best
73  score with */
75 
76 typedef struct FLACParseContext {
77  AVCodecParserContext *pc; /**< parent context */
78  AVCodecContext *avctx; /**< codec context pointer for logging */
79  FLACHeaderMarker *headers; /**< linked-list that starts at the first
80  CRC-8 verified header within buffer */
81  FLACHeaderMarker *best_header; /**< highest scoring header within buffer */
82  int nb_headers_found; /**< number of headers found in the last
83  flac_parse() call */
84  int nb_headers_buffered; /**< number of headers that are buffered */
85  int best_header_valid; /**< flag set when the parser returns junk;
86  if set return best_header next time */
87  AVFifoBuffer *fifo_buf; /**< buffer to store all data until headers
88  can be verified */
89  int end_padded; /**< specifies if fifo_buf's end is padded */
90  uint8_t *wrap_buf; /**< general fifo read buffer when wrapped */
91  int wrap_buf_allocated_size; /**< actual allocated size of the buffer */
92  FLACFrameInfo last_fi; /**< last decoded frame header info */
93  int last_fi_valid; /**< set if last_fi is valid */
95 
96 static int frame_header_is_valid(AVCodecContext *avctx, const uint8_t *buf,
97  FLACFrameInfo *fi)
98 {
99  GetBitContext gb;
100  uint8_t subframe_type;
101 
102  // header plus one byte from first subframe
103  init_get_bits(&gb, buf, MAX_FRAME_VERIFY_SIZE * 8);
104  if (ff_flac_decode_frame_header(avctx, &gb, fi, 127)) {
105  return 0;
106  }
107  // subframe zero bit
108  if (get_bits1(&gb) != 0) {
109  return 0;
110  }
111  // subframe type
112  // 000000 : SUBFRAME_CONSTANT
113  // 000001 : SUBFRAME_VERBATIM
114  // 00001x : reserved
115  // 0001xx : reserved
116  // 001xxx : if(xxx <= 4) SUBFRAME_FIXED, xxx=order ; else reserved
117  // 01xxxx : reserved
118  // 1xxxxx : SUBFRAME_LPC, xxxxx=order-1
119  subframe_type = get_bits(&gb, 6);
120  if (!(subframe_type == 0 ||
121  subframe_type == 1 ||
122  ((subframe_type >= 8) && (subframe_type <= 12)) ||
123  (subframe_type >= 32))) {
124  return 0;
125  }
126 
127  return 1;
128 }
129 
130 /**
131  * Non-destructive fast fifo pointer fetching
132  * Returns a pointer from the specified offset.
133  * If possible the pointer points within the fifo buffer.
134  * Otherwise (if it would cause a wrap around,) a pointer to a user-specified
135  * buffer is used.
136  * The pointer can be NULL. In any case it will be reallocated to hold the size.
137  * If the returned pointer will be used after subsequent calls to flac_fifo_read_wrap
138  * then the subsequent calls should pass in a different wrap_buf so as to not
139  * overwrite the contents of the previous wrap_buf.
140  * This function is based on av_fifo_generic_read, which is why there is a comment
141  * about a memory barrier for SMP.
142  */
143 static uint8_t *flac_fifo_read_wrap(FLACParseContext *fpc, int offset, int len,
144  uint8_t **wrap_buf, int *allocated_size)
145 {
146  AVFifoBuffer *f = fpc->fifo_buf;
147  uint8_t *start = f->rptr + offset;
148  uint8_t *tmp_buf;
149 
150  if (start >= f->end)
151  start -= f->end - f->buffer;
152  if (f->end - start >= len)
153  return start;
154 
155  tmp_buf = av_fast_realloc(*wrap_buf, allocated_size, len);
156 
157  if (!tmp_buf) {
158  av_log(fpc->avctx, AV_LOG_ERROR,
159  "couldn't reallocate wrap buffer of size %d", len);
160  return NULL;
161  }
162  *wrap_buf = tmp_buf;
163  do {
164  int seg_len = FFMIN(f->end - start, len);
165  memcpy(tmp_buf, start, seg_len);
166  tmp_buf = (uint8_t*)tmp_buf + seg_len;
167 // memory barrier needed for SMP here in theory
168 
169  start += seg_len - (f->end - f->buffer);
170  len -= seg_len;
171  } while (len > 0);
172 
173  return *wrap_buf;
174 }
175 
176 /**
177  * Return a pointer in the fifo buffer where the offset starts at until
178  * the wrap point or end of request.
179  * len will contain the valid length of the returned buffer.
180  * A second call to flac_fifo_read (with new offset and len) should be called
181  * to get the post-wrap buf if the returned len is less than the requested.
182  **/
183 static uint8_t *flac_fifo_read(FLACParseContext *fpc, int offset, int *len)
184 {
185  AVFifoBuffer *f = fpc->fifo_buf;
186  uint8_t *start = f->rptr + offset;
187 
188  if (start >= f->end)
189  start -= f->end - f->buffer;
190  *len = FFMIN(*len, f->end - start);
191  return start;
192 }
193 
195 {
196  FLACFrameInfo fi;
197  uint8_t *header_buf;
198  int size = 0;
199  header_buf = flac_fifo_read_wrap(fpc, offset,
201  &fpc->wrap_buf,
203  if (frame_header_is_valid(fpc->avctx, header_buf, &fi)) {
204  FLACHeaderMarker **end_handle = &fpc->headers;
205  int i;
206 
207  size = 0;
208  while (*end_handle) {
209  end_handle = &(*end_handle)->next;
210  size++;
211  }
212 
213  *end_handle = av_mallocz(sizeof(**end_handle));
214  if (!*end_handle) {
215  av_log(fpc->avctx, AV_LOG_ERROR,
216  "couldn't allocate FLACHeaderMarker\n");
217  return AVERROR(ENOMEM);
218  }
219  (*end_handle)->fi = fi;
220  (*end_handle)->offset = offset;
221 
222  for (i = 0; i < FLAC_MAX_SEQUENTIAL_HEADERS; i++)
223  (*end_handle)->link_penalty[i] = FLAC_HEADER_NOT_PENALIZED_YET;
224 
225  fpc->nb_headers_found++;
226  size++;
227  }
228  return size;
229 }
230 
231 static int find_headers_search(FLACParseContext *fpc, uint8_t *buf,
232  int buf_size, int search_start)
233 {
234  int size = 0, mod_offset = (buf_size - 1) % 4, i, j;
235  uint32_t x;
236 
237  for (i = 0; i < mod_offset; i++) {
238  if ((AV_RB16(buf + i) & 0xFFFE) == 0xFFF8) {
239  int ret = find_headers_search_validate(fpc, search_start + i);
240  size = FFMAX(size, ret);
241  }
242  }
243 
244  for (; i < buf_size - 1; i += 4) {
245  x = AV_RN32(buf + i);
246  if (((x & ~(x + 0x01010101)) & 0x80808080)) {
247  for (j = 0; j < 4; j++) {
248  if ((AV_RB16(buf + i + j) & 0xFFFE) == 0xFFF8) {
249  int ret = find_headers_search_validate(fpc, search_start + i + j);
250  size = FFMAX(size, ret);
251  }
252  }
253  }
254  }
255  return size;
256 }
257 
258 static int find_new_headers(FLACParseContext *fpc, int search_start)
259 {
260  FLACHeaderMarker *end;
261  int search_end, size = 0, read_len, temp;
262  uint8_t *buf;
263  fpc->nb_headers_found = 0;
264 
265  /* Search for a new header of at most 16 bytes. */
266  search_end = av_fifo_size(fpc->fifo_buf) - (MAX_FRAME_HEADER_SIZE - 1);
267  read_len = search_end - search_start + 1;
268  buf = flac_fifo_read(fpc, search_start, &read_len);
269  size = find_headers_search(fpc, buf, read_len, search_start);
270  search_start += read_len - 1;
271 
272  /* If fifo end was hit do the wrap around. */
273  if (search_start != search_end) {
274  uint8_t wrap[2];
275 
276  wrap[0] = buf[read_len - 1];
277  /* search_start + 1 is the post-wrap offset in the fifo. */
278  read_len = search_end - (search_start + 1) + 1;
279 
280  buf = flac_fifo_read(fpc, search_start + 1, &read_len);
281  wrap[1] = buf[0];
282 
283  if ((AV_RB16(wrap) & 0xFFFE) == 0xFFF8) {
284  temp = find_headers_search_validate(fpc, search_start);
285  size = FFMAX(size, temp);
286  }
287  search_start++;
288 
289  /* Continue to do the last half of the wrap. */
290  temp = find_headers_search(fpc, buf, read_len, search_start);
291  size = FFMAX(size, temp);
292  search_start += read_len - 1;
293  }
294 
295  /* Return the size even if no new headers were found. */
296  if (!size && fpc->headers)
297  for (end = fpc->headers; end; end = end->next)
298  size++;
299  return size;
300 }
301 
303  FLACFrameInfo *header_fi,
304  FLACFrameInfo *child_fi,
305  int log_level_offset)
306 {
307  int deduction = 0;
308  if (child_fi->samplerate != header_fi->samplerate) {
309  deduction += FLAC_HEADER_CHANGED_PENALTY;
310  av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset,
311  "sample rate change detected in adjacent frames\n");
312  }
313  if (child_fi->bps != header_fi->bps) {
314  deduction += FLAC_HEADER_CHANGED_PENALTY;
315  av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset,
316  "bits per sample change detected in adjacent frames\n");
317  }
318  if (child_fi->is_var_size != header_fi->is_var_size) {
319  /* Changing blocking strategy not allowed per the spec */
320  deduction += FLAC_HEADER_BASE_SCORE;
321  av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset,
322  "blocking strategy change detected in adjacent frames\n");
323  }
324  if (child_fi->channels != header_fi->channels) {
325  deduction += FLAC_HEADER_CHANGED_PENALTY;
326  av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset,
327  "number of channels change detected in adjacent frames\n");
328  }
329  return deduction;
330 }
331 
334  FLACHeaderMarker *child,
335  int log_level_offset)
336 {
337  FLACFrameInfo *header_fi = &header->fi, *child_fi = &child->fi;
338  int deduction, deduction_expected = 0, i;
339  deduction = check_header_fi_mismatch(fpc, header_fi, child_fi,
340  log_level_offset);
341  /* Check sample and frame numbers. */
342  if ((child_fi->frame_or_sample_num - header_fi->frame_or_sample_num
343  != header_fi->blocksize) &&
344  (child_fi->frame_or_sample_num
345  != header_fi->frame_or_sample_num + 1)) {
346  FLACHeaderMarker *curr;
347  int64_t expected_frame_num, expected_sample_num;
348  /* If there are frames in the middle we expect this deduction,
349  as they are probably valid and this one follows it */
350 
351  expected_frame_num = expected_sample_num = header_fi->frame_or_sample_num;
352  curr = header;
353  while (curr != child) {
354  /* Ignore frames that failed all crc checks */
355  for (i = 0; i < FLAC_MAX_SEQUENTIAL_HEADERS; i++) {
357  expected_frame_num++;
358  expected_sample_num += curr->fi.blocksize;
359  break;
360  }
361  }
362  curr = curr->next;
363  }
364 
365  if (expected_frame_num == child_fi->frame_or_sample_num ||
366  expected_sample_num == child_fi->frame_or_sample_num)
367  deduction_expected = deduction ? 0 : 1;
368 
369  deduction += FLAC_HEADER_CHANGED_PENALTY;
370  av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset,
371  "sample/frame number mismatch in adjacent frames\n");
372  }
373 
374  /* If we have suspicious headers, check the CRC between them */
375  if (deduction && !deduction_expected) {
376  FLACHeaderMarker *curr;
377  int read_len;
378  uint8_t *buf;
379  uint32_t crc = 1;
380  int inverted_test = 0;
381 
382  /* Since CRC is expensive only do it if we haven't yet.
383  This assumes a CRC penalty is greater than all other check penalties */
384  curr = header->next;
385  for (i = 0; i < FLAC_MAX_SEQUENTIAL_HEADERS && curr != child; i++)
386  curr = curr->next;
387 
388  if (header->link_penalty[i] < FLAC_HEADER_CRC_FAIL_PENALTY ||
389  header->link_penalty[i] == FLAC_HEADER_NOT_PENALIZED_YET) {
390  FLACHeaderMarker *start, *end;
391 
392  /* Although overlapping chains are scored, the crc should never
393  have to be computed twice for a single byte. */
394  start = header;
395  end = child;
396  if (i > 0 &&
397  header->link_penalty[i - 1] >= FLAC_HEADER_CRC_FAIL_PENALTY) {
398  while (start->next != child)
399  start = start->next;
400  inverted_test = 1;
401  } else if (i > 0 &&
402  header->next->link_penalty[i-1] >=
404  end = header->next;
405  inverted_test = 1;
406  }
407 
408  read_len = end->offset - start->offset;
409  buf = flac_fifo_read(fpc, start->offset, &read_len);
410  crc = av_crc(av_crc_get_table(AV_CRC_16_ANSI), 0, buf, read_len);
411  read_len = (end->offset - start->offset) - read_len;
412 
413  if (read_len) {
414  buf = flac_fifo_read(fpc, end->offset - read_len, &read_len);
415  crc = av_crc(av_crc_get_table(AV_CRC_16_ANSI), crc, buf, read_len);
416  }
417  }
418 
419  if (!crc ^ !inverted_test) {
420  deduction += FLAC_HEADER_CRC_FAIL_PENALTY;
421  av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset,
422  "crc check failed from offset %i (frame %"PRId64") to %i (frame %"PRId64")\n",
423  header->offset, header_fi->frame_or_sample_num,
424  child->offset, child_fi->frame_or_sample_num);
425  }
426  }
427  return deduction;
428 }
429 
430 /**
431  * Score a header.
432  *
433  * Give FLAC_HEADER_BASE_SCORE points to a frame for existing.
434  * If it has children, (subsequent frames of which the preceding CRC footer
435  * validates against this one,) then take the maximum score of the children,
436  * with a penalty of FLAC_HEADER_CHANGED_PENALTY applied for each change to
437  * bps, sample rate, channels, but not decorrelation mode, or blocksize,
438  * because it can change often.
439  **/
441 {
442  FLACHeaderMarker *child;
443  int dist = 0;
444  int child_score;
445  int base_score = FLAC_HEADER_BASE_SCORE;
446  if (header->max_score != FLAC_HEADER_NOT_SCORED_YET)
447  return header->max_score;
448 
449  /* Modify the base score with changes from the last output header */
450  if (fpc->last_fi_valid) {
451  /* Silence the log since this will be repeated if selected */
452  base_score -= check_header_fi_mismatch(fpc, &fpc->last_fi, &header->fi,
453  AV_LOG_DEBUG);
454  }
455 
456  header->max_score = base_score;
457 
458  /* Check and compute the children's scores. */
459  child = header->next;
460  for (dist = 0; dist < FLAC_MAX_SEQUENTIAL_HEADERS && child; dist++) {
461  /* Look at the child's frame header info and penalize suspicious
462  changes between the headers. */
463  if (header->link_penalty[dist] == FLAC_HEADER_NOT_PENALIZED_YET) {
464  header->link_penalty[dist] = check_header_mismatch(fpc, header,
465  child, AV_LOG_DEBUG);
466  }
467  child_score = score_header(fpc, child) - header->link_penalty[dist];
468 
469  if (FLAC_HEADER_BASE_SCORE + child_score > header->max_score) {
470  /* Keep the child because the frame scoring is dynamic. */
471  header->best_child = child;
472  header->max_score = base_score + child_score;
473  }
474  child = child->next;
475  }
476 
477  return header->max_score;
478 }
479 
481 {
482  FLACHeaderMarker *curr;
483  int best_score = 0;//FLAC_HEADER_NOT_SCORED_YET;
484  /* First pass to clear all old scores. */
485  for (curr = fpc->headers; curr; curr = curr->next)
487 
488  /* Do a second pass to score them all. */
489  for (curr = fpc->headers; curr; curr = curr->next) {
490  if (score_header(fpc, curr) > best_score) {
491  fpc->best_header = curr;
492  best_score = curr->max_score;
493  }
494  }
495 }
496 
497 static int get_best_header(FLACParseContext *fpc, const uint8_t **poutbuf,
498  int *poutbuf_size)
499 {
501  FLACHeaderMarker *child = header->best_child;
502  if (!child) {
503  *poutbuf_size = av_fifo_size(fpc->fifo_buf) - header->offset;
504  } else {
505  *poutbuf_size = child->offset - header->offset;
506 
507  /* If the child has suspicious changes, log them */
508  check_header_mismatch(fpc, header, child, 0);
509  }
510 
511  if (header->fi.channels != fpc->avctx->channels ||
512  !fpc->avctx->channel_layout) {
513  fpc->avctx->channels = header->fi.channels;
515  }
516  fpc->avctx->sample_rate = header->fi.samplerate;
517  fpc->pc->duration = header->fi.blocksize;
518  *poutbuf = flac_fifo_read_wrap(fpc, header->offset, *poutbuf_size,
519  &fpc->wrap_buf,
521 
522 
523  if (fpc->pc->flags & PARSER_FLAG_USE_CODEC_TS) {
524  if (header->fi.is_var_size)
525  fpc->pc->pts = header->fi.frame_or_sample_num;
526  else if (header->best_child)
527  fpc->pc->pts = header->fi.frame_or_sample_num * header->fi.blocksize;
528  }
529 
530  fpc->best_header_valid = 0;
531  fpc->last_fi_valid = 1;
532  fpc->last_fi = header->fi;
533 
534  /* Return the negative overread index so the client can compute pos.
535  This should be the amount overread to the beginning of the child */
536  if (child)
537  return child->offset - av_fifo_size(fpc->fifo_buf);
538  return 0;
539 }
540 
542  const uint8_t **poutbuf, int *poutbuf_size,
543  const uint8_t *buf, int buf_size)
544 {
545  FLACParseContext *fpc = s->priv_data;
546  FLACHeaderMarker *curr;
547  int nb_headers;
548  const uint8_t *read_end = buf;
549  const uint8_t *read_start = buf;
550 
551  if (s->flags & PARSER_FLAG_COMPLETE_FRAMES) {
552  FLACFrameInfo fi;
553  if (frame_header_is_valid(avctx, buf, &fi)) {
554  s->duration = fi.blocksize;
555  if (!avctx->sample_rate)
556  avctx->sample_rate = fi.samplerate;
557  if (fpc->pc->flags & PARSER_FLAG_USE_CODEC_TS) {
558  fpc->pc->pts = fi.frame_or_sample_num;
559  if (!fi.is_var_size)
560  fpc->pc->pts *= fi.blocksize;
561  }
562  }
563  *poutbuf = buf;
564  *poutbuf_size = buf_size;
565  return buf_size;
566  }
567 
568  fpc->avctx = avctx;
569  if (fpc->best_header_valid)
570  return get_best_header(fpc, poutbuf, poutbuf_size);
571 
572  /* If a best_header was found last call remove it with the buffer data. */
573  if (fpc->best_header && fpc->best_header->best_child) {
575  FLACHeaderMarker *best_child = fpc->best_header->best_child;
576 
577  /* Remove headers in list until the end of the best_header. */
578  for (curr = fpc->headers; curr != best_child; curr = temp) {
579  if (curr != fpc->best_header) {
580  av_log(avctx, AV_LOG_DEBUG,
581  "dropping low score %i frame header from offset %i to %i\n",
582  curr->max_score, curr->offset, curr->next->offset);
583  }
584  temp = curr->next;
585  av_free(curr);
586  fpc->nb_headers_buffered--;
587  }
588  /* Release returned data from ring buffer. */
589  av_fifo_drain(fpc->fifo_buf, best_child->offset);
590 
591  /* Fix the offset for the headers remaining to match the new buffer. */
592  for (curr = best_child->next; curr; curr = curr->next)
593  curr->offset -= best_child->offset;
594 
595  best_child->offset = 0;
596  fpc->headers = best_child;
598  fpc->best_header = best_child;
599  return get_best_header(fpc, poutbuf, poutbuf_size);
600  }
601  fpc->best_header = NULL;
602  } else if (fpc->best_header) {
603  /* No end frame no need to delete the buffer; probably eof */
605 
606  for (curr = fpc->headers; curr != fpc->best_header; curr = temp) {
607  temp = curr->next;
608  av_free(curr);
609  fpc->nb_headers_buffered--;
610  }
611  fpc->headers = fpc->best_header->next;
612  av_freep(&fpc->best_header);
613  fpc->nb_headers_buffered--;
614  }
615 
616  /* Find and score new headers. */
617  /* buf_size is zero when flushing, so check for this since we do */
618  /* not want to try to read more input once we have found the end. */
619  /* Also note that buf can't be NULL. */
620  while ((buf_size && read_end < buf + buf_size &&
622  || (!buf_size && !fpc->end_padded)) {
623  int start_offset;
624 
625  /* Pad the end once if EOF, to check the final region for headers. */
626  if (!buf_size) {
627  fpc->end_padded = 1;
628  read_end = read_start + MAX_FRAME_HEADER_SIZE;
629  } else {
630  /* The maximum read size is the upper-bound of what the parser
631  needs to have the required number of frames buffered */
632  int nb_desired = FLAC_MIN_HEADERS - fpc->nb_headers_buffered + 1;
633  read_end = read_end + FFMIN(buf + buf_size - read_end,
634  nb_desired * FLAC_AVG_FRAME_SIZE);
635  }
636 
637  if (!av_fifo_space(fpc->fifo_buf) &&
639  fpc->nb_headers_buffered * 20) {
640  /* There is less than one valid flac header buffered for 20 headers
641  * buffered. Therefore the fifo is most likely filled with invalid
642  * data and the input is not a flac file. */
643  goto handle_error;
644  }
645 
646  /* Fill the buffer. */
647  if ( av_fifo_space(fpc->fifo_buf) < read_end - read_start
648  && av_fifo_realloc2(fpc->fifo_buf, (read_end - read_start) + 2*av_fifo_size(fpc->fifo_buf)) < 0) {
649  av_log(avctx, AV_LOG_ERROR,
650  "couldn't reallocate buffer of size %"PTRDIFF_SPECIFIER"\n",
651  (read_end - read_start) + av_fifo_size(fpc->fifo_buf));
652  goto handle_error;
653  }
654 
655  if (buf_size) {
656  av_fifo_generic_write(fpc->fifo_buf, (void*) read_start,
657  read_end - read_start, NULL);
658  } else {
659  int8_t pad[MAX_FRAME_HEADER_SIZE] = { 0 };
660  av_fifo_generic_write(fpc->fifo_buf, pad, sizeof(pad), NULL);
661  }
662 
663  /* Tag headers and update sequences. */
664  start_offset = av_fifo_size(fpc->fifo_buf) -
665  ((read_end - read_start) + (MAX_FRAME_HEADER_SIZE - 1));
666  start_offset = FFMAX(0, start_offset);
667  nb_headers = find_new_headers(fpc, start_offset);
668 
669  if (nb_headers < 0) {
670  av_log(avctx, AV_LOG_ERROR,
671  "find_new_headers couldn't allocate FLAC header\n");
672  goto handle_error;
673  }
674 
675  fpc->nb_headers_buffered = nb_headers;
676  /* Wait till FLAC_MIN_HEADERS to output a valid frame. */
677  if (!fpc->end_padded && fpc->nb_headers_buffered < FLAC_MIN_HEADERS) {
678  if (read_end < buf + buf_size) {
679  read_start = read_end;
680  continue;
681  } else {
682  goto handle_error;
683  }
684  }
685 
686  /* If headers found, update the scores since we have longer chains. */
687  if (fpc->end_padded || fpc->nb_headers_found)
688  score_sequences(fpc);
689 
690  /* restore the state pre-padding */
691  if (fpc->end_padded) {
692  int warp = fpc->fifo_buf->wptr - fpc->fifo_buf->buffer < MAX_FRAME_HEADER_SIZE;
693  /* HACK: drain the tail of the fifo */
696  if (warp) {
697  fpc->fifo_buf->wptr += fpc->fifo_buf->end -
698  fpc->fifo_buf->buffer;
699  }
700  read_start = read_end = NULL;
701  }
702  }
703 
704  for (curr = fpc->headers; curr; curr = curr->next) {
705  if (!fpc->best_header || curr->max_score > fpc->best_header->max_score) {
706  fpc->best_header = curr;
707  }
708  }
709 
710  if (fpc->best_header && fpc->best_header->max_score <= 0) {
711  // Only accept a bad header if there is no other option to continue
712  if (!buf_size || read_end != buf || fpc->nb_headers_buffered < FLAC_MIN_HEADERS)
713  fpc->best_header = NULL;
714  }
715 
716  if (fpc->best_header) {
717  fpc->best_header_valid = 1;
718  if (fpc->best_header->offset > 0) {
719  /* Output a junk frame. */
720  av_log(avctx, AV_LOG_DEBUG, "Junk frame till offset %i\n",
721  fpc->best_header->offset);
722 
723  /* Set duration to 0. It is unknown or invalid in a junk frame. */
724  s->duration = 0;
725  *poutbuf_size = fpc->best_header->offset;
726  *poutbuf = flac_fifo_read_wrap(fpc, 0, *poutbuf_size,
727  &fpc->wrap_buf,
729  return buf_size ? (read_end - buf) : (fpc->best_header->offset -
730  av_fifo_size(fpc->fifo_buf));
731  }
732  if (!buf_size)
733  return get_best_header(fpc, poutbuf, poutbuf_size);
734  }
735 
736 handle_error:
737  *poutbuf = NULL;
738  *poutbuf_size = 0;
739  return buf_size ? read_end - buf : 0;
740 }
741 
743 {
744  FLACParseContext *fpc = c->priv_data;
745  fpc->pc = c;
746  /* There will generally be FLAC_MIN_HEADERS buffered in the fifo before
747  it drains. This is allocated early to avoid slow reallocation. */
749  if (!fpc->fifo_buf) {
750  av_log(fpc->avctx, AV_LOG_ERROR,
751  "couldn't allocate fifo_buf\n");
752  return AVERROR(ENOMEM);
753  }
754  return 0;
755 }
756 
758 {
759  FLACParseContext *fpc = c->priv_data;
760  FLACHeaderMarker *curr = fpc->headers, *temp;
761 
762  while (curr) {
763  temp = curr->next;
764  av_free(curr);
765  curr = temp;
766  }
767  fpc->headers = NULL;
768  av_fifo_freep(&fpc->fifo_buf);
769  av_freep(&fpc->wrap_buf);
770 }
771 
774  .priv_data_size = sizeof(FLACParseContext),
775  .parser_init = flac_parse_init,
776  .parser_parse = flac_parse,
777  .parser_close = flac_parse_close,
778 };
FLACParseContext
Definition: flac_parser.c:76
FLACParseContext::headers
FLACHeaderMarker * headers
linked-list that starts at the first CRC-8 verified header within buffer
Definition: flac_parser.c:79
FLAC_HEADER_BASE_SCORE
#define FLAC_HEADER_BASE_SCORE
scoring settings for score_header
Definition: flac_parser.c:50
frame_header_is_valid
static int frame_header_is_valid(AVCodecContext *avctx, const uint8_t *buf, FLACFrameInfo *fi)
Definition: flac_parser.c:96
AV_LOG_WARNING
#define AV_LOG_WARNING
Something somehow does not look correct.
Definition: log.h:186
check_header_fi_mismatch
static int check_header_fi_mismatch(FLACParseContext *fpc, FLACFrameInfo *header_fi, FLACFrameInfo *child_fi, int log_level_offset)
Definition: flac_parser.c:302
FLACParseContext::nb_headers_buffered
int nb_headers_buffered
number of headers that are buffered
Definition: flac_parser.c:84
AVCodecParserContext::pts
int64_t pts
Definition: avcodec.h:2794
find_new_headers
static int find_new_headers(FLACParseContext *fpc, int search_start)
Definition: flac_parser.c:258
FLACHeaderMarker
Definition: flac_parser.c:60
AVERROR
Filter the word “frame” indicates either a video frame or a group of audio as stored in an AVFrame structure Format for each input and each output the list of supported formats For video that means pixel format For audio that means channel sample they are references to shared objects When the negotiation mechanism computes the intersection of the formats supported at each end of a all references to both lists are replaced with a reference to the intersection And when a single format is eventually chosen for a link amongst the remaining all references to the list are updated That means that if a filter requires that its input and output have the same format amongst a supported all it has to do is use a reference to the same list of formats query_formats can leave some formats unset and return AVERROR(EAGAIN) to cause the negotiation mechanism toagain later. That can be used by filters with complex requirements to use the format negotiated on one link to set the formats supported on another. Frame references ownership and permissions
AVCodecContext::channel_layout
uint64_t channel_layout
Audio channel layout.
Definition: avcodec.h:1043
av_fifo_generic_write
int av_fifo_generic_write(AVFifoBuffer *f, void *src, int size, int(*func)(void *, void *, int))
Feed data from a user-supplied callback to an AVFifoBuffer.
Definition: fifo.c:122
AVCodecContext::sample_rate
int sample_rate
samples per second
Definition: avcodec.h:992
AVCodecParserContext::duration
int duration
Duration of the current frame.
Definition: avcodec.h:2889
AVFifoBuffer::wptr
uint8_t * wptr
Definition: fifo.h:33
FLACParseContext::wrap_buf
uint8_t * wrap_buf
general fifo read buffer when wrapped
Definition: flac_parser.c:90
FLACHeaderMarker::best_child
struct FLACHeaderMarker * best_child
following frame header with which this frame has the best score with
Definition: flac_parser.c:71
FLACFrameInfo::frame_or_sample_num
int64_t frame_or_sample_num
frame number or sample number
Definition: flac.h:88
FLACFrameInfo::is_var_size
int is_var_size
specifies if the stream uses variable block sizes or a fixed block size; also determines the meaning ...
Definition: flac.h:89
score_sequences
static void score_sequences(FLACParseContext *fpc)
Definition: flac_parser.c:480
ff_flac_decode_frame_header
int ff_flac_decode_frame_header(AVCodecContext *avctx, GetBitContext *gb, FLACFrameInfo *fi, int log_level_offset)
Validate and decode a frame header.
Definition: flac.c:50
AV_CODEC_ID_FLAC
@ AV_CODEC_ID_FLAC
Definition: codec_id.h:435
FFMAX
#define FFMAX(a, b)
Definition: macros.h:47
FLAC_HEADER_CHANGED_PENALTY
#define FLAC_HEADER_CHANGED_PENALTY
Definition: flac_parser.c:51
FLAC_MAX_SEQUENTIAL_HEADERS
#define FLAC_MAX_SEQUENTIAL_HEADERS
maximum number of adjacent headers that compare CRCs against each other
Definition: flac_parser.c:43
init_get_bits
static int init_get_bits(GetBitContext *s, const uint8_t *buffer, int bit_size)
Initialize GetBitContext.
Definition: get_bits.h:660
FLACParseContext::wrap_buf_allocated_size
int wrap_buf_allocated_size
actual allocated size of the buffer
Definition: flac_parser.c:91
av_fifo_drain
void av_fifo_drain(AVFifoBuffer *f, int size)
Discard data from the FIFO.
Definition: fifo.c:233
AVFifoBuffer
Definition: fifo.h:31
crc.h
flac_fifo_read_wrap
static uint8_t * flac_fifo_read_wrap(FLACParseContext *fpc, int offset, int len, uint8_t **wrap_buf, int *allocated_size)
Non-destructive fast fifo pointer fetching Returns a pointer from the specified offset.
Definition: flac_parser.c:143
get_bits
static unsigned int get_bits(GetBitContext *s, int n)
Read 1-25 bits.
Definition: get_bits.h:380
fifo.h
ff_flac_parser
const AVCodecParser ff_flac_parser
Definition: flac_parser.c:772
wrap
#define wrap(func)
Definition: neontest.h:65
FLACParseContext::fifo_buf
AVFifoBuffer * fifo_buf
buffer to store all data until headers can be verified
Definition: flac_parser.c:87
GetBitContext
Definition: get_bits.h:62
FLACParseContext::best_header_valid
int best_header_valid
flag set when the parser returns junk; if set return best_header next time
Definition: flac_parser.c:85
flac_fifo_read
static uint8_t * flac_fifo_read(FLACParseContext *fpc, int offset, int *len)
Return a pointer in the fifo buffer where the offset starts at until the wrap point or end of request...
Definition: flac_parser.c:183
get_best_header
static int get_best_header(FLACParseContext *fpc, const uint8_t **poutbuf, int *poutbuf_size)
Definition: flac_parser.c:497
AV_LOG_ERROR
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition: log.h:180
av_fifo_space
int av_fifo_space(const AVFifoBuffer *f)
Return the amount of space in bytes in the AVFifoBuffer, that is the amount of data you can write int...
Definition: fifo.c:82
av_cold
#define av_cold
Definition: attributes.h:90
FLACHeaderMarker::next
struct FLACHeaderMarker * next
next CRC-8 verified header that immediately follows this one in the bytestream
Definition: flac_parser.c:68
av_fast_realloc
void * av_fast_realloc(void *ptr, unsigned int *size, size_t min_size)
Reallocate the given buffer if it is not large enough, otherwise do nothing.
Definition: mem.c:504
FLAC_AVG_FRAME_SIZE
#define FLAC_AVG_FRAME_SIZE
estimate for average size of a FLAC frame
Definition: flac_parser.c:47
s
#define s(width, name)
Definition: cbs_vp9.c:257
AV_LOG_DEBUG
#define AV_LOG_DEBUG
Stuff which is only useful for libav* developers.
Definition: log.h:201
FLACParseContext::last_fi_valid
int last_fi_valid
set if last_fi is valid
Definition: flac_parser.c:93
FLACParseContext::avctx
AVCodecContext * avctx
codec context pointer for logging
Definition: flac_parser.c:78
find_headers_search_validate
static int find_headers_search_validate(FLACParseContext *fpc, int offset)
Definition: flac_parser.c:194
FLACParseContext::pc
AVCodecParserContext * pc
parent context
Definition: flac_parser.c:77
av_fifo_realloc2
int av_fifo_realloc2(AVFifoBuffer *f, unsigned int new_size)
Resize an AVFifoBuffer.
Definition: fifo.c:87
f
#define f(width, name)
Definition: cbs_vp9.c:255
if
if(ret)
Definition: filter_design.txt:179
AV_CRC_16_ANSI
@ AV_CRC_16_ANSI
Definition: crc.h:50
score_header
static int score_header(FLACParseContext *fpc, FLACHeaderMarker *header)
Score a header.
Definition: flac_parser.c:440
PTRDIFF_SPECIFIER
#define PTRDIFF_SPECIFIER
Definition: internal.h:192
NULL
#define NULL
Definition: coverity.c:32
FLACFrameInfo::blocksize
FLACCOMMONINFO int blocksize
block size of the frame
Definition: flac.h:86
flac_parse
static int flac_parse(AVCodecParserContext *s, AVCodecContext *avctx, const uint8_t **poutbuf, int *poutbuf_size, const uint8_t *buf, int buf_size)
Definition: flac_parser.c:541
find_headers_search
static int find_headers_search(FLACParseContext *fpc, uint8_t *buf, int buf_size, int search_start)
Definition: flac_parser.c:231
get_bits1
static unsigned int get_bits1(GetBitContext *s)
Definition: get_bits.h:499
AV_RN32
#define AV_RN32(p)
Definition: intreadwrite.h:364
AVFifoBuffer::end
uint8_t * end
Definition: fifo.h:33
ff_flac_set_channel_layout
void ff_flac_set_channel_layout(AVCodecContext *avctx)
Definition: flac.c:196
AVCodecParserContext::flags
int flags
Definition: avcodec.h:2808
FLACFrameInfo
Definition: flac.h:84
FLAC_HEADER_CRC_FAIL_PENALTY
#define FLAC_HEADER_CRC_FAIL_PENALTY
Definition: flac_parser.c:52
c
Undefined Behavior In the C some operations are like signed integer dereferencing freed accessing outside allocated Undefined Behavior must not occur in a C it is not safe even if the output of undefined operations is unused The unsafety may seem nit picking but Optimizing compilers have in fact optimized code on the assumption that no undefined Behavior occurs Optimizing code based on wrong assumptions can and has in some cases lead to effects beyond the output of computations The signed integer overflow problem in speed critical code Code which is highly optimized and works with signed integers sometimes has the problem that often the output of the computation does not c
Definition: undefined.txt:32
FLAC_HEADER_NOT_SCORED_YET
#define FLAC_HEADER_NOT_SCORED_YET
Definition: flac_parser.c:54
AVCodecParser::codec_ids
int codec_ids[7]
Definition: avcodec.h:2935
size
int size
Definition: twinvq_data.h:10344
header
static const uint8_t header[24]
Definition: sdr2.c:67
av_crc_get_table
const AVCRC * av_crc_get_table(AVCRCId crc_id)
Get an initialized standard CRC table.
Definition: crc.c:374
offset
it s the only field you need to keep assuming you have a context There is some magic you don t need to care about around this just let it vf offset
Definition: writing_filters.txt:86
attributes.h
flac_parse_init
static av_cold int flac_parse_init(AVCodecParserContext *c)
Definition: flac_parser.c:742
FLACHeaderMarker::fi
FLACFrameInfo fi
decoded frame header info
Definition: flac_parser.c:67
AVCodecContext::channels
int channels
number of audio channels
Definition: avcodec.h:993
FLACParseContext::best_header
FLACHeaderMarker * best_header
highest scoring header within buffer
Definition: flac_parser.c:81
PARSER_FLAG_COMPLETE_FRAMES
#define PARSER_FLAG_COMPLETE_FRAMES
Definition: avcodec.h:2809
i
#define i(width, name, range_min, range_max)
Definition: cbs_h2645.c:271
FLACHeaderMarker::max_score
int max_score
maximum score found after checking each child that has a valid CRC
Definition: flac_parser.c:65
FLACParseContext::end_padded
int end_padded
specifies if fifo_buf's end is padded
Definition: flac_parser.c:89
av_fifo_alloc_array
AVFifoBuffer * av_fifo_alloc_array(size_t nmemb, size_t size)
Initialize an AVFifoBuffer.
Definition: fifo.c:49
FFMIN
#define FFMIN(a, b)
Definition: macros.h:49
av_mallocz
void * av_mallocz(size_t size)
Allocate a memory block with alignment suitable for all memory accesses (including vectors if availab...
Definition: mem.c:263
MAX_FRAME_VERIFY_SIZE
#define MAX_FRAME_VERIFY_SIZE
Definition: flac_parser.c:58
parser.h
len
int len
Definition: vorbis_enc_data.h:426
AVFifoBuffer::buffer
uint8_t * buffer
Definition: fifo.h:32
AVFifoBuffer::wndx
uint32_t wndx
Definition: fifo.h:34
check_header_mismatch
static int check_header_mismatch(FLACParseContext *fpc, FLACHeaderMarker *header, FLACHeaderMarker *child, int log_level_offset)
Definition: flac_parser.c:332
AVCodecParserContext
Definition: avcodec.h:2775
ret
ret
Definition: filter_design.txt:187
FLACParseContext::nb_headers_found
int nb_headers_found
number of headers found in the last flac_parse() call
Definition: flac_parser.c:82
MAX_FRAME_HEADER_SIZE
#define MAX_FRAME_HEADER_SIZE
largest possible size of flac header
Definition: flac_parser.c:57
AV_INPUT_BUFFER_PADDING_SIZE
#define AV_INPUT_BUFFER_PADDING_SIZE
Definition: defs.h:40
AVCodecContext
main external API structure.
Definition: avcodec.h:383
av_crc
uint32_t av_crc(const AVCRC *ctx, uint32_t crc, const uint8_t *buffer, size_t length)
Calculate the CRC of a block.
Definition: crc.c:392
PARSER_FLAG_USE_CODEC_TS
#define PARSER_FLAG_USE_CODEC_TS
Definition: avcodec.h:2813
temp
else temp
Definition: vf_mcdeint.c:248
FLACHeaderMarker::link_penalty
int link_penalty[FLAC_MAX_SEQUENTIAL_HEADERS]
array of local scores between this header and the one at a distance equal array position
Definition: flac_parser.c:62
FLAC_MIN_HEADERS
#define FLAC_MIN_HEADERS
minimum number of headers buffered and checked before returning frames
Definition: flac_parser.c:45
av_fifo_size
int av_fifo_size(const AVFifoBuffer *f)
Return the amount of data in bytes in the AVFifoBuffer, that is the amount of data you can read from ...
Definition: fifo.c:77
FLACHeaderMarker::offset
int offset
byte offset from start of FLACParseContext->buffer
Definition: flac_parser.c:61
av_fifo_freep
void av_fifo_freep(AVFifoBuffer **f)
Free an AVFifoBuffer and reset pointer to NULL.
Definition: fifo.c:63
av_free
#define av_free(p)
Definition: tableprint_vlc.h:34
av_freep
#define av_freep(p)
Definition: tableprint_vlc.h:35
FLAC_HEADER_NOT_PENALIZED_YET
#define FLAC_HEADER_NOT_PENALIZED_YET
Definition: flac_parser.c:53
AVCodecParser
Definition: avcodec.h:2934
FLACParseContext::last_fi
FLACFrameInfo last_fi
last decoded frame header info
Definition: flac_parser.c:92
bytestream.h
av_log
#define av_log(a,...)
Definition: tableprint_vlc.h:28
flac.h
flac_parse_close
static void flac_parse_close(AVCodecParserContext *c)
Definition: flac_parser.c:757
AV_RB16
uint64_t_TMPL AV_WL64 unsigned int_TMPL AV_WL32 unsigned int_TMPL AV_WL24 unsigned int_TMPL AV_WL16 uint64_t_TMPL AV_WB64 unsigned int_TMPL AV_WB32 unsigned int_TMPL AV_WB24 unsigned int_TMPL AV_RB16
Definition: bytestream.h:98