hls.c
Go to the documentation of this file.
1 /*
2  * Apple HTTP Live Streaming demuxer
3  * Copyright (c) 2010 Martin Storsjo
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  * Apple HTTP Live Streaming demuxer
25  * http://tools.ietf.org/html/draft-pantos-http-live-streaming
26  */
27 
28 #include "libavutil/avstring.h"
29 #include "libavutil/intreadwrite.h"
30 #include "libavutil/mathematics.h"
31 #include "libavutil/opt.h"
32 #include "libavutil/dict.h"
33 #include "libavutil/time.h"
34 #include "avformat.h"
35 #include "internal.h"
36 #include "avio_internal.h"
37 #include "url.h"
38 
39 #define INITIAL_BUFFER_SIZE 32768
40 
41 /*
42  * An apple http stream consists of a playlist with media segment files,
43  * played sequentially. There may be several playlists with the same
44  * video content, in different bandwidth variants, that are played in
45  * parallel (preferably only one bandwidth variant at a time). In this case,
46  * the user supplied the url to a main playlist that only lists the variant
47  * playlists.
48  *
49  * If the main playlist doesn't point at any variants, we still create
50  * one anonymous toplevel variant for this, to maintain the structure.
51  */
52 
53 enum KeyType {
56 };
57 
58 struct segment {
59  int duration;
63  uint8_t iv[16];
64 };
65 
66 /*
67  * Each variant has its own demuxer. If it currently is active,
68  * it has an open AVIOContext too, and potentially an AVPacket
69  * containing the next packet from this stream.
70  */
71 struct variant {
72  int bandwidth;
78  int index;
82 
83  int finished;
87  struct segment **segments;
88  int needed, cur_needed;
90  int64_t last_load_time;
91 
92  char key_url[MAX_URL_SIZE];
93  uint8_t key[16];
94 };
95 
96 typedef struct HLSContext {
98  struct variant **variants;
103  int64_t seek_timestamp;
106  char *user_agent; ///< holds HTTP user agent set as an AVOption to the HTTP protocol context
107  char *cookies; ///< holds HTTP cookie values set in either the initial response or as an AVOption to the HTTP protocol context
108 } HLSContext;
109 
110 static int read_chomp_line(AVIOContext *s, char *buf, int maxlen)
111 {
112  int len = ff_get_line(s, buf, maxlen);
113  while (len > 0 && av_isspace(buf[len - 1]))
114  buf[--len] = '\0';
115  return len;
116 }
117 
118 static void free_segment_list(struct variant *var)
119 {
120  int i;
121  for (i = 0; i < var->n_segments; i++)
122  av_free(var->segments[i]);
123  av_freep(&var->segments);
124  var->n_segments = 0;
125 }
126 
128 {
129  int i;
130  for (i = 0; i < c->n_variants; i++) {
131  struct variant *var = c->variants[i];
132  free_segment_list(var);
133  av_free_packet(&var->pkt);
134  av_free(var->pb.buffer);
135  if (var->input)
136  ffurl_close(var->input);
137  if (var->ctx) {
138  var->ctx->pb = NULL;
139  avformat_close_input(&var->ctx);
140  }
141  av_free(var);
142  }
143  av_freep(&c->variants);
144  av_freep(&c->cookies);
145  av_freep(&c->user_agent);
146  c->n_variants = 0;
147 }
148 
149 /*
150  * Used to reset a statically allocated AVPacket to a clean slate,
151  * containing no data.
152  */
153 static void reset_packet(AVPacket *pkt)
154 {
155  av_init_packet(pkt);
156  pkt->data = NULL;
157 }
158 
159 static struct variant *new_variant(HLSContext *c, int bandwidth,
160  const char *url, const char *base)
161 {
162  struct variant *var = av_mallocz(sizeof(struct variant));
163  if (!var)
164  return NULL;
165  reset_packet(&var->pkt);
166  var->bandwidth = bandwidth;
167  ff_make_absolute_url(var->url, sizeof(var->url), base, url);
168  dynarray_add(&c->variants, &c->n_variants, var);
169  return var;
170 }
171 
172 struct variant_info {
173  char bandwidth[20];
174 };
175 
176 static void handle_variant_args(struct variant_info *info, const char *key,
177  int key_len, char **dest, int *dest_len)
178 {
179  if (!strncmp(key, "BANDWIDTH=", key_len)) {
180  *dest = info->bandwidth;
181  *dest_len = sizeof(info->bandwidth);
182  }
183 }
184 
185 struct key_info {
186  char uri[MAX_URL_SIZE];
187  char method[10];
188  char iv[35];
189 };
190 
191 static void handle_key_args(struct key_info *info, const char *key,
192  int key_len, char **dest, int *dest_len)
193 {
194  if (!strncmp(key, "METHOD=", key_len)) {
195  *dest = info->method;
196  *dest_len = sizeof(info->method);
197  } else if (!strncmp(key, "URI=", key_len)) {
198  *dest = info->uri;
199  *dest_len = sizeof(info->uri);
200  } else if (!strncmp(key, "IV=", key_len)) {
201  *dest = info->iv;
202  *dest_len = sizeof(info->iv);
203  }
204 }
205 
206 static int parse_playlist(HLSContext *c, const char *url,
207  struct variant *var, AVIOContext *in)
208 {
209  int ret = 0, duration = 0, is_segment = 0, is_variant = 0, bandwidth = 0;
210  enum KeyType key_type = KEY_NONE;
211  uint8_t iv[16] = "";
212  int has_iv = 0;
213  char key[MAX_URL_SIZE] = "";
214  char line[1024];
215  const char *ptr;
216  int close_in = 0;
217 
218  if (!in) {
219  AVDictionary *opts = NULL;
220  close_in = 1;
221  /* Some HLS servers dont like being sent the range header */
222  av_dict_set(&opts, "seekable", "0", 0);
223 
224  // broker prior HTTP options that should be consistent across requests
225  av_dict_set(&opts, "user-agent", c->user_agent, 0);
226  av_dict_set(&opts, "cookies", c->cookies, 0);
227 
228  ret = avio_open2(&in, url, AVIO_FLAG_READ,
229  c->interrupt_callback, &opts);
230  av_dict_free(&opts);
231  if (ret < 0)
232  return ret;
233  }
234 
235  read_chomp_line(in, line, sizeof(line));
236  if (strcmp(line, "#EXTM3U")) {
237  ret = AVERROR_INVALIDDATA;
238  goto fail;
239  }
240 
241  if (var) {
242  free_segment_list(var);
243  var->finished = 0;
244  }
245  while (!url_feof(in)) {
246  read_chomp_line(in, line, sizeof(line));
247  if (av_strstart(line, "#EXT-X-STREAM-INF:", &ptr)) {
248  struct variant_info info = {{0}};
249  is_variant = 1;
251  &info);
252  bandwidth = atoi(info.bandwidth);
253  } else if (av_strstart(line, "#EXT-X-KEY:", &ptr)) {
254  struct key_info info = {{0}};
256  &info);
257  key_type = KEY_NONE;
258  has_iv = 0;
259  if (!strcmp(info.method, "AES-128"))
260  key_type = KEY_AES_128;
261  if (!strncmp(info.iv, "0x", 2) || !strncmp(info.iv, "0X", 2)) {
262  ff_hex_to_data(iv, info.iv + 2);
263  has_iv = 1;
264  }
265  av_strlcpy(key, info.uri, sizeof(key));
266  } else if (av_strstart(line, "#EXT-X-TARGETDURATION:", &ptr)) {
267  if (!var) {
268  var = new_variant(c, 0, url, NULL);
269  if (!var) {
270  ret = AVERROR(ENOMEM);
271  goto fail;
272  }
273  }
274  var->target_duration = atoi(ptr);
275  } else if (av_strstart(line, "#EXT-X-MEDIA-SEQUENCE:", &ptr)) {
276  if (!var) {
277  var = new_variant(c, 0, url, NULL);
278  if (!var) {
279  ret = AVERROR(ENOMEM);
280  goto fail;
281  }
282  }
283  var->start_seq_no = atoi(ptr);
284  } else if (av_strstart(line, "#EXT-X-ENDLIST", &ptr)) {
285  if (var)
286  var->finished = 1;
287  } else if (av_strstart(line, "#EXTINF:", &ptr)) {
288  is_segment = 1;
289  duration = atoi(ptr);
290  } else if (av_strstart(line, "#", NULL)) {
291  continue;
292  } else if (line[0]) {
293  if (is_variant) {
294  if (!new_variant(c, bandwidth, line, url)) {
295  ret = AVERROR(ENOMEM);
296  goto fail;
297  }
298  is_variant = 0;
299  bandwidth = 0;
300  }
301  if (is_segment) {
302  struct segment *seg;
303  if (!var) {
304  var = new_variant(c, 0, url, NULL);
305  if (!var) {
306  ret = AVERROR(ENOMEM);
307  goto fail;
308  }
309  }
310  seg = av_malloc(sizeof(struct segment));
311  if (!seg) {
312  ret = AVERROR(ENOMEM);
313  goto fail;
314  }
315  seg->duration = duration;
316  seg->key_type = key_type;
317  if (has_iv) {
318  memcpy(seg->iv, iv, sizeof(iv));
319  } else {
320  int seq = var->start_seq_no + var->n_segments;
321  memset(seg->iv, 0, sizeof(seg->iv));
322  AV_WB32(seg->iv + 12, seq);
323  }
324  ff_make_absolute_url(seg->key, sizeof(seg->key), url, key);
325  ff_make_absolute_url(seg->url, sizeof(seg->url), url, line);
326  dynarray_add(&var->segments, &var->n_segments, seg);
327  is_segment = 0;
328  }
329  }
330  }
331  if (var)
332  var->last_load_time = av_gettime();
333 
334 fail:
335  if (close_in)
336  avio_close(in);
337  return ret;
338 }
339 
340 static int open_input(HLSContext *c, struct variant *var)
341 {
342  AVDictionary *opts = NULL;
343  int ret;
344  struct segment *seg = var->segments[var->cur_seq_no - var->start_seq_no];
345 
346  // broker prior HTTP options that should be consistent across requests
347  av_dict_set(&opts, "user-agent", c->user_agent, 0);
348  av_dict_set(&opts, "cookies", c->cookies, 0);
349  av_dict_set(&opts, "seekable", "0", 0);
350 
351  if (seg->key_type == KEY_NONE) {
352  ret = ffurl_open(&var->input, seg->url, AVIO_FLAG_READ,
353  &var->parent->interrupt_callback, &opts);
354  goto cleanup;
355  } else if (seg->key_type == KEY_AES_128) {
356  char iv[33], key[33], url[MAX_URL_SIZE];
357  if (strcmp(seg->key, var->key_url)) {
358  URLContext *uc;
359  if (ffurl_open(&uc, seg->key, AVIO_FLAG_READ,
360  &var->parent->interrupt_callback, &opts) == 0) {
361  if (ffurl_read_complete(uc, var->key, sizeof(var->key))
362  != sizeof(var->key)) {
363  av_log(NULL, AV_LOG_ERROR, "Unable to read key file %s\n",
364  seg->key);
365  }
366  ffurl_close(uc);
367  } else {
368  av_log(NULL, AV_LOG_ERROR, "Unable to open key file %s\n",
369  seg->key);
370  }
371  av_strlcpy(var->key_url, seg->key, sizeof(var->key_url));
372  }
373  ff_data_to_hex(iv, seg->iv, sizeof(seg->iv), 0);
374  ff_data_to_hex(key, var->key, sizeof(var->key), 0);
375  iv[32] = key[32] = '\0';
376  if (strstr(seg->url, "://"))
377  snprintf(url, sizeof(url), "crypto+%s", seg->url);
378  else
379  snprintf(url, sizeof(url), "crypto:%s", seg->url);
380  if ((ret = ffurl_alloc(&var->input, url, AVIO_FLAG_READ,
381  &var->parent->interrupt_callback)) < 0)
382  goto cleanup;
383  av_opt_set(var->input->priv_data, "key", key, 0);
384  av_opt_set(var->input->priv_data, "iv", iv, 0);
385  /* Need to repopulate options */
386  av_dict_free(&opts);
387  av_dict_set(&opts, "seekable", "0", 0);
388  if ((ret = ffurl_connect(var->input, &opts)) < 0) {
389  ffurl_close(var->input);
390  var->input = NULL;
391  goto cleanup;
392  }
393  ret = 0;
394  }
395  else
396  ret = AVERROR(ENOSYS);
397 
398 cleanup:
399  av_dict_free(&opts);
400  return ret;
401 }
402 
403 static int read_data(void *opaque, uint8_t *buf, int buf_size)
404 {
405  struct variant *v = opaque;
406  HLSContext *c = v->parent->priv_data;
407  int ret, i;
408 
409 restart:
410  if (!v->input) {
411  /* If this is a live stream and the reload interval has elapsed since
412  * the last playlist reload, reload the variant playlists now. */
413  int64_t reload_interval = v->n_segments > 0 ?
414  v->segments[v->n_segments - 1]->duration :
415  v->target_duration;
416  reload_interval *= 1000000;
417 
418 reload:
419  if (!v->finished &&
420  av_gettime() - v->last_load_time >= reload_interval) {
421  if ((ret = parse_playlist(c, v->url, v, NULL)) < 0)
422  return ret;
423  /* If we need to reload the playlist again below (if
424  * there's still no more segments), switch to a reload
425  * interval of half the target duration. */
426  reload_interval = v->target_duration * 500000LL;
427  }
428  if (v->cur_seq_no < v->start_seq_no) {
430  "skipping %d segments ahead, expired from playlists\n",
431  v->start_seq_no - v->cur_seq_no);
432  v->cur_seq_no = v->start_seq_no;
433  }
434  if (v->cur_seq_no >= v->start_seq_no + v->n_segments) {
435  if (v->finished)
436  return AVERROR_EOF;
437  while (av_gettime() - v->last_load_time < reload_interval) {
439  return AVERROR_EXIT;
440  av_usleep(100*1000);
441  }
442  /* Enough time has elapsed since the last reload */
443  goto reload;
444  }
445 
446  ret = open_input(c, v);
447  if (ret < 0)
448  return ret;
449  }
450  ret = ffurl_read(v->input, buf, buf_size);
451  if (ret > 0)
452  return ret;
453  ffurl_close(v->input);
454  v->input = NULL;
455  v->cur_seq_no++;
456 
457  c->end_of_segment = 1;
458  c->cur_seq_no = v->cur_seq_no;
459 
460  if (v->ctx && v->ctx->nb_streams && v->parent->nb_streams >= v->stream_offset + v->ctx->nb_streams) {
461  v->needed = 0;
462  for (i = v->stream_offset; i < v->stream_offset + v->ctx->nb_streams;
463  i++) {
464  if (v->parent->streams[i]->discard < AVDISCARD_ALL)
465  v->needed = 1;
466  }
467  }
468  if (!v->needed) {
469  av_log(v->parent, AV_LOG_INFO, "No longer receiving variant %d\n",
470  v->index);
471  return AVERROR_EOF;
472  }
473  goto restart;
474 }
475 
477 {
478  URLContext *u = (s->flags & AVFMT_FLAG_CUSTOM_IO) ? NULL : s->pb->opaque;
479  HLSContext *c = s->priv_data;
480  int ret = 0, i, j, stream_offset = 0;
481 
482  c->interrupt_callback = &s->interrupt_callback;
483 
484  // if the URL context is good, read important options we must broker later
485  if (u && u->prot->priv_data_class) {
486  // get the previous user agent & set back to null if string size is zero
487  av_freep(&c->user_agent);
488  av_opt_get(u->priv_data, "user-agent", 0, (uint8_t**)&(c->user_agent));
489  if (c->user_agent && !strlen(c->user_agent))
490  av_freep(&c->user_agent);
491 
492  // get the previous cookies & set back to null if string size is zero
493  av_freep(&c->cookies);
494  av_opt_get(u->priv_data, "cookies", 0, (uint8_t**)&(c->cookies));
495  if (c->cookies && !strlen(c->cookies))
496  av_freep(&c->cookies);
497  }
498 
499  if ((ret = parse_playlist(c, s->filename, NULL, s->pb)) < 0)
500  goto fail;
501 
502  if (c->n_variants == 0) {
503  av_log(NULL, AV_LOG_WARNING, "Empty playlist\n");
504  ret = AVERROR_EOF;
505  goto fail;
506  }
507  /* If the playlist only contained variants, parse each individual
508  * variant playlist. */
509  if (c->n_variants > 1 || c->variants[0]->n_segments == 0) {
510  for (i = 0; i < c->n_variants; i++) {
511  struct variant *v = c->variants[i];
512  if ((ret = parse_playlist(c, v->url, v, NULL)) < 0)
513  goto fail;
514  }
515  }
516 
517  if (c->variants[0]->n_segments == 0) {
518  av_log(NULL, AV_LOG_WARNING, "Empty playlist\n");
519  ret = AVERROR_EOF;
520  goto fail;
521  }
522 
523  /* If this isn't a live stream, calculate the total duration of the
524  * stream. */
525  if (c->variants[0]->finished) {
526  int64_t duration = 0;
527  for (i = 0; i < c->variants[0]->n_segments; i++)
528  duration += c->variants[0]->segments[i]->duration;
529  s->duration = duration * AV_TIME_BASE;
530  }
531 
532  /* Open the demuxer for each variant */
533  for (i = 0; i < c->n_variants; i++) {
534  struct variant *v = c->variants[i];
535  AVInputFormat *in_fmt = NULL;
536  char bitrate_str[20];
537  AVProgram *program = NULL;
538  if (v->n_segments == 0)
539  continue;
540 
541  if (!(v->ctx = avformat_alloc_context())) {
542  ret = AVERROR(ENOMEM);
543  goto fail;
544  }
545 
546  v->index = i;
547  v->needed = 1;
548  v->parent = s;
549 
550  /* If this is a live stream with more than 3 segments, start at the
551  * third last segment. */
552  v->cur_seq_no = v->start_seq_no;
553  if (!v->finished && v->n_segments > 3)
554  v->cur_seq_no = v->start_seq_no + v->n_segments - 3;
555 
558  read_data, NULL, NULL);
559  v->pb.seekable = 0;
560  ret = av_probe_input_buffer(&v->pb, &in_fmt, v->segments[0]->url,
561  NULL, 0, 0);
562  if (ret < 0) {
563  /* Free the ctx - it isn't initialized properly at this point,
564  * so avformat_close_input shouldn't be called. If
565  * avformat_open_input fails below, it frees and zeros the
566  * context, so it doesn't need any special treatment like this. */
567  av_log(s, AV_LOG_ERROR, "Error when loading first segment '%s'\n", v->segments[0]->url);
569  v->ctx = NULL;
570  goto fail;
571  }
572  v->ctx->pb = &v->pb;
573  ret = avformat_open_input(&v->ctx, v->segments[0]->url, in_fmt, NULL);
574  if (ret < 0)
575  goto fail;
576 
580  if (ret < 0)
581  goto fail;
582  snprintf(bitrate_str, sizeof(bitrate_str), "%d", v->bandwidth);
583 
584  /* Create new AVprogram for variant i */
585  program = av_new_program(s, i);
586  if (!program)
587  goto fail;
588  av_dict_set(&program->metadata, "variant_bitrate", bitrate_str, 0);
589 
590  /* Create new AVStreams for each stream in this variant */
591  for (j = 0; j < v->ctx->nb_streams; j++) {
593  AVStream *ist = v->ctx->streams[j];
594  if (!st) {
595  ret = AVERROR(ENOMEM);
596  goto fail;
597  }
599  st->id = i;
602  if (v->bandwidth)
603  av_dict_set(&st->metadata, "variant_bitrate", bitrate_str,
604  0);
605  }
607  }
608 
609  c->first_packet = 1;
610  c->first_timestamp = AV_NOPTS_VALUE;
611  c->seek_timestamp = AV_NOPTS_VALUE;
612 
613  return 0;
614 fail:
616  return ret;
617 }
618 
620 {
621  HLSContext *c = s->priv_data;
622  int i, changed = 0;
623 
624  /* Check if any new streams are needed */
625  for (i = 0; i < c->n_variants; i++)
626  c->variants[i]->cur_needed = 0;
627 
628  for (i = 0; i < s->nb_streams; i++) {
629  AVStream *st = s->streams[i];
630  struct variant *var = c->variants[s->streams[i]->id];
631  if (st->discard < AVDISCARD_ALL)
632  var->cur_needed = 1;
633  }
634  for (i = 0; i < c->n_variants; i++) {
635  struct variant *v = c->variants[i];
636  if (v->cur_needed && !v->needed) {
637  v->needed = 1;
638  changed = 1;
639  v->cur_seq_no = c->cur_seq_no;
640  v->pb.eof_reached = 0;
641  av_log(s, AV_LOG_INFO, "Now receiving variant %d\n", i);
642  } else if (first && !v->cur_needed && v->needed) {
643  if (v->input)
644  ffurl_close(v->input);
645  v->input = NULL;
646  v->needed = 0;
647  changed = 1;
648  av_log(s, AV_LOG_INFO, "No longer receiving variant %d\n", i);
649  }
650  }
651  return changed;
652 }
653 
655 {
656  HLSContext *c = s->priv_data;
657  int ret, i, minvariant = -1;
658 
659  if (c->first_packet) {
660  recheck_discard_flags(s, 1);
661  c->first_packet = 0;
662  }
663 
664 start:
665  c->end_of_segment = 0;
666  for (i = 0; i < c->n_variants; i++) {
667  struct variant *var = c->variants[i];
668  /* Make sure we've got one buffered packet from each open variant
669  * stream */
670  if (var->needed && !var->pkt.data) {
671  while (1) {
672  int64_t ts_diff;
673  AVStream *st;
674  ret = av_read_frame(var->ctx, &var->pkt);
675  if (ret < 0) {
676  if (!url_feof(&var->pb) && ret != AVERROR_EOF)
677  return ret;
678  reset_packet(&var->pkt);
679  break;
680  } else {
682  c->first_timestamp = var->pkt.dts;
683  }
684 
685  if (c->seek_timestamp == AV_NOPTS_VALUE)
686  break;
687 
688  if (var->pkt.dts == AV_NOPTS_VALUE) {
690  break;
691  }
692 
693  st = var->ctx->streams[var->pkt.stream_index];
694  ts_diff = av_rescale_rnd(var->pkt.dts, AV_TIME_BASE,
695  st->time_base.den, AV_ROUND_DOWN) -
696  c->seek_timestamp;
697  if (ts_diff >= 0 && (c->seek_flags & AVSEEK_FLAG_ANY ||
698  var->pkt.flags & AV_PKT_FLAG_KEY)) {
700  break;
701  }
702  }
703  }
704  /* Check if this stream has the packet with the lowest dts */
705  if (var->pkt.data) {
706  if(minvariant < 0) {
707  minvariant = i;
708  } else {
709  struct variant *minvar = c->variants[minvariant];
710  int64_t dts = var->pkt.dts;
711  int64_t mindts = minvar->pkt.dts;
712  AVStream *st = var->ctx->streams[ var->pkt.stream_index];
713  AVStream *minst= minvar->ctx->streams[minvar->pkt.stream_index];
714 
715  if( st->start_time != AV_NOPTS_VALUE) dts -= st->start_time;
716  if(minst->start_time != AV_NOPTS_VALUE) mindts -= minst->start_time;
717 
718  if (av_compare_ts(dts, st->time_base, mindts, minst->time_base) < 0)
719  minvariant = i;
720  }
721  }
722  }
723  if (c->end_of_segment) {
724  if (recheck_discard_flags(s, 0))
725  goto start;
726  }
727  /* If we got a packet, return it */
728  if (minvariant >= 0) {
729  *pkt = c->variants[minvariant]->pkt;
730  pkt->stream_index += c->variants[minvariant]->stream_offset;
731  reset_packet(&c->variants[minvariant]->pkt);
732  return 0;
733  }
734  return AVERROR_EOF;
735 }
736 
738 {
739  HLSContext *c = s->priv_data;
740 
742  return 0;
743 }
744 
745 static int hls_read_seek(AVFormatContext *s, int stream_index,
746  int64_t timestamp, int flags)
747 {
748  HLSContext *c = s->priv_data;
749  int i, j, ret;
750 
751  if ((flags & AVSEEK_FLAG_BYTE) || !c->variants[0]->finished)
752  return AVERROR(ENOSYS);
753 
754  c->seek_flags = flags;
755  c->seek_timestamp = stream_index < 0 ? timestamp :
756  av_rescale_rnd(timestamp, AV_TIME_BASE,
757  s->streams[stream_index]->time_base.den,
758  flags & AVSEEK_FLAG_BACKWARD ?
760  timestamp = av_rescale_rnd(timestamp, 1, stream_index >= 0 ?
761  s->streams[stream_index]->time_base.den :
763  AV_ROUND_DOWN : AV_ROUND_UP);
764  if (s->duration < c->seek_timestamp) {
766  return AVERROR(EIO);
767  }
768 
769  ret = AVERROR(EIO);
770  for (i = 0; i < c->n_variants; i++) {
771  /* Reset reading */
772  struct variant *var = c->variants[i];
773  int64_t pos = c->first_timestamp == AV_NOPTS_VALUE ? 0 :
774  av_rescale_rnd(c->first_timestamp, 1, stream_index >= 0 ?
775  s->streams[stream_index]->time_base.den :
776  AV_TIME_BASE, flags & AVSEEK_FLAG_BACKWARD ?
777  AV_ROUND_DOWN : AV_ROUND_UP);
778  if (var->input) {
779  ffurl_close(var->input);
780  var->input = NULL;
781  }
782  av_free_packet(&var->pkt);
783  reset_packet(&var->pkt);
784  var->pb.eof_reached = 0;
785  /* Clear any buffered data */
786  var->pb.buf_end = var->pb.buf_ptr = var->pb.buffer;
787  /* Reset the pos, to let the mpegts demuxer know we've seeked. */
788  var->pb.pos = 0;
789 
790  /* Locate the segment that contains the target timestamp */
791  for (j = 0; j < var->n_segments; j++) {
792  if (timestamp >= pos &&
793  timestamp < pos + var->segments[j]->duration) {
794  var->cur_seq_no = var->start_seq_no + j;
795  ret = 0;
796  break;
797  }
798  pos += var->segments[j]->duration;
799  }
800  if (ret)
802  }
803  return ret;
804 }
805 
806 static int hls_probe(AVProbeData *p)
807 {
808  /* Require #EXTM3U at the start, and either one of the ones below
809  * somewhere for a proper match. */
810  if (strncmp(p->buf, "#EXTM3U", 7))
811  return 0;
812  if (strstr(p->buf, "#EXT-X-STREAM-INF:") ||
813  strstr(p->buf, "#EXT-X-TARGETDURATION:") ||
814  strstr(p->buf, "#EXT-X-MEDIA-SEQUENCE:"))
815  return AVPROBE_SCORE_MAX;
816  return 0;
817 }
818 
820  .name = "hls,applehttp",
821  .long_name = NULL_IF_CONFIG_SMALL("Apple HTTP Live Streaming"),
822  .priv_data_size = sizeof(HLSContext),
828 };
#define AVSEEK_FLAG_BACKWARD
Definition: avformat.h:1743
Definition: start.py:1
int needed
Definition: hls.c:88
void * av_mallocz(size_t size)
Allocate a block of size bytes with alignment suitable for all memory accesses (including vectors if ...
Definition: mem.c:205
float v
const char * s
Definition: avisynth_c.h:668
Bytestream IO Context.
Definition: avio.h:68
#define AVERROR_INVALIDDATA
Invalid data found when processing input.
Definition: error.h:59
int bandwidth
Definition: hls.c:72
URLContext * input
Definition: hls.c:76
int cur_needed
Definition: hls.c:88
void av_free_packet(AVPacket *pkt)
Free a packet.
Definition: avpacket.c:242
AVIOInterruptCB interrupt_callback
Custom interrupt callbacks for the I/O layer.
Definition: avformat.h:1125
char key_url[MAX_URL_SIZE]
Definition: hls.c:92
struct HLSContext HLSContext
int64_t av_rescale_rnd(int64_t a, int64_t b, int64_t c, enum AVRounding rnd)
Rescale a 64-bit integer with specified rounding.
Definition: mathematics.c:60
unsigned char * buf_ptr
Current position in the buffer.
Definition: avio.h:84
unsigned char * buf_end
End of the data, may be less than buffer+buffer_size if the read function returned less data than req...
Definition: avio.h:85
int avformat_open_input(AVFormatContext **ps, const char *filename, AVInputFormat *fmt, AVDictionary **options)
Open an input stream and read the header.
void avpriv_set_pts_info(AVStream *s, int pts_wrap_bits, unsigned int pts_num, unsigned int pts_den)
Set the time base and wrapping info for a given stream.
#define AVSEEK_FLAG_ANY
seek to any frame, even non-keyframes
Definition: avformat.h:1745
#define AV_LOG_WARNING
Something somehow does not look correct.
Definition: log.h:154
static int read_seek(AVFormatContext *ctx, int stream_index, int64_t timestamp, int flags)
Definition: libcdio.c:153
int ffurl_connect(URLContext *uc, AVDictionary **options)
Connect an URLContext that has been allocated by ffurl_alloc.
Definition: avio.c:190
int finished
Definition: hls.c:83
int num
numerator
Definition: rational.h:44
#define AVIO_FLAG_READ
read-only
Definition: avio.h:332
struct URLProtocol * prot
Definition: url.h:43
About Git write you should know how to use GIT properly Luckily Git comes with excellent documentation git help man git shows you the available git< command > help man git< command > shows information about the subcommand< command > The most comprehensive manual is the website Git Reference visit they are quite exhaustive You do not need a special username or password All you need is to provide a ssh public key to the Git server admin What follows now is a basic introduction to Git and some FFmpeg specific guidelines Read it at least if you are granted commit privileges to the FFmpeg project you are expected to be familiar with these rules I if not You can get git from etc no matter how small Every one of them has been saved from looking like a fool by this many times It s very easy for stray debug output or cosmetic modifications to slip in
Definition: git-howto.txt:5
unsigned char * buffer
Start of the buffer.
Definition: avio.h:82
int target_duration
Definition: hls.c:84
void * opaque
A private pointer, passed to the read/write/seek/...
Definition: avio.h:89
int n_segments
Definition: hls.c:86
int64_t last_load_time
Definition: hls.c:90
int av_usleep(unsigned usec)
Sleep for a period of time.
Definition: time.c:56
char url[MAX_URL_SIZE]
Definition: hls.c:60
char * user_agent
holds HTTP user agent set as an AVOption to the HTTP protocol context
Definition: hls.c:106
int ctx_flags
Format-specific flags, see AVFMTCTX_xx.
Definition: avformat.h:980
static void reset_packet(AVPacket *pkt)
Definition: hls.c:153
int avcodec_copy_context(AVCodecContext *dest, const AVCodecContext *src)
Copy the settings of the source AVCodecContext into the destination AVCodecContext.
void av_freep(void *arg)
Free a memory block which has been allocated with av_malloc(z)() or av_realloc() and set the pointer ...
Definition: mem.c:198
const AVClass * priv_data_class
Definition: url.h:89
initialize output if(nPeaks >3)%at least 3 peaks in spectrum for trying to find f0 nf0peaks
Format I/O context.
Definition: avformat.h:944
#define AV_WB32(p, darg)
Definition: intreadwrite.h:265
#define MAX_URL_SIZE
Public dictionary API.
uint8_t iv[16]
Definition: hls.c:63
uint8_t
Round toward +infinity.
Definition: mathematics.h:71
int n_variants
Definition: hls.c:97
int start_seq_no
Definition: hls.c:85
#define AVFMTCTX_NOHEADER
signal that no header is present (streams are added dynamically)
Definition: avformat.h:914
AVOptions.
static AVPacket pkt
Definition: demuxing.c:56
int id
Format-specific stream ID.
Definition: avformat.h:650
trying all byte sequences megabyte in length and selecting the best looking sequence will yield cases to try But first
AVInputFormat ff_hls_demuxer
Definition: hls.c:819
AVStream * avformat_new_stream(AVFormatContext *s, const AVCodec *c)
Add a new stream to a media file.
AVStream ** streams
Definition: avformat.h:992
AVFormatContext * avformat_alloc_context(void)
Allocate an AVFormatContext.
uint8_t * data
AVProgram * av_new_program(AVFormatContext *s, int id)
static int read_data(void *opaque, uint8_t *buf, int buf_size)
Definition: hls.c:403
int64_t seek_timestamp
Definition: hls.c:103
#define AVERROR_EOF
End of file.
Definition: error.h:55
static av_cold int read_close(AVFormatContext *ctx)
Definition: libcdio.c:145
int end_of_segment
Definition: hls.c:100
char method[10]
Definition: hls.c:187
#define AV_PKT_FLAG_KEY
The packet contains a keyframe.
struct variant ** variants
Definition: hls.c:98
Callback for checking whether to abort blocking functions.
Definition: avio.h:51
struct segment ** segments
Definition: hls.c:87
int index
Definition: hls.c:78
int ffurl_alloc(URLContext **puc, const char *filename, int flags, const AVIOInterruptCB *int_cb)
Create a URLContext for accessing to the resource indicated by url, but do not initiate the connectio...
Definition: avio.c:211
void av_free(void *ptr)
Free a memory block which has been allocated with av_malloc(z)() or av_realloc(). ...
Definition: mem.c:183
AVIOInterruptCB * interrupt_callback
Definition: hls.c:105
char bandwidth[20]
Definition: hls.c:173
static struct variant * new_variant(HLSContext *c, int bandwidth, const char *url, const char *base)
Definition: hls.c:159
static void handle_key_args(struct key_info *info, const char *key, int key_len, char **dest, int *dest_len)
Definition: hls.c:191
AVIOContext pb
Definition: hls.c:74
#define NULL_IF_CONFIG_SMALL(x)
Return NULL if CONFIG_SMALL is true, otherwise the argument without modification. ...
int avio_close(AVIOContext *s)
Close the resource accessed by the AVIOContext s and free it.
Definition: aviobuf.c:821
void av_dict_free(AVDictionary **pm)
Free all the memory allocated for an AVDictionary struct and all keys and values. ...
Definition: dict.c:162
Definition: graph2dot.c:48
void ff_program_add_stream_index(AVFormatContext *ac, int progid, unsigned int idx)
void av_log(void *avcl, int level, const char *fmt,...)
Definition: log.c:246
int first_packet
Definition: hls.c:101
int av_isspace(int c)
Locale-independent conversion of ASCII isspace.
Definition: avstring.c:298
New fields can be added to the end with minor version bumps.
Definition: avformat.h:888
size_t av_strlcpy(char *dst, const char *src, size_t size)
Copy the string src to dst, but no more than size - 1 bytes, and null-terminate dst.
Definition: avstring.c:82
int flags
A combination of AV_PKT_FLAG values.
int av_compare_ts(int64_t ts_a, AVRational tb_a, int64_t ts_b, AVRational tb_b)
Compare 2 timestamps each in its own timebases.
Definition: mathematics.c:135
AVCodecContext * codec
Codec context associated with this stream.
Definition: avformat.h:662
unsigned char * buf
Buffer must have AVPROBE_PADDING_SIZE of extra allocated bytes filled with zero.
Definition: avformat.h:336
Definition: hls.c:58
unsigned int nb_streams
A list of all streams in the file.
Definition: avformat.h:991
char url[MAX_URL_SIZE]
Definition: hls.c:73
MIPS optimizations info
Definition: mips.txt:2
int seekable
A combination of AVIO_SEEKABLE_ flags or 0 when the stream is not seekable.
Definition: avio.h:117
#define dynarray_add(tab, nb_ptr, elem)
char filename[1024]
input or output filename
Definition: avformat.h:994
#define AV_TIME_BASE
Internal time base represented as integer.
Definition: avutil.h:196
void(* ff_parse_key_val_cb)(void *context, const char *key, int key_len, char **dest, int *dest_len)
Callback function type for ff_parse_key_value.
static int read_probe(AVProbeData *pd)
ret
Definition: avfilter.c:821
int av_probe_input_buffer(AVIOContext *pb, AVInputFormat **fmt, const char *filename, void *logctx, unsigned int offset, unsigned int max_probe_size)
Probe a bytestream to determine the input format.
Definition: hls.c:96
static int hls_read_packet(AVFormatContext *s, AVPacket *pkt)
Definition: hls.c:654
Definition: hls.c:185
float u
AVDictionary * metadata
Definition: avformat.h:711
#define AVFMT_FLAG_CUSTOM_IO
The caller has supplied a custom AVIOContext, don&#39;t avio_close() it.
Definition: avformat.h:1029
int ff_get_line(AVIOContext *s, char *buf, int maxlen)
Read a whole line of text from AVIOContext.
Definition: aviobuf.c:618
#define AVERROR_EXIT
Immediate exit was requested; the called function should not be restarted.
Definition: error.h:56
char * cookies
holds HTTP cookie values set in either the initial response or as an AVOption to the HTTP protocol co...
Definition: hls.c:107
int duration
Definition: hls.c:59
int url_feof(AVIOContext *s)
feof() equivalent for AVIOContext.
Definition: aviobuf.c:280
uint8_t * read_buffer
Definition: hls.c:75
static int read_header(FFV1Context *f)
Definition: ffv1dec.c:517
enum KeyType key_type
Definition: hls.c:62
int64_t av_gettime(void)
Get the current time in microseconds.
Definition: time.c:39
static void free_segment_list(struct variant *var)
Definition: hls.c:118
Stream structure.
Definition: avformat.h:643
static int open_input(HLSContext *c, struct variant *var)
Definition: hls.c:340
static int read_chomp_line(AVIOContext *s, char *buf, int maxlen)
Definition: hls.c:110
NULL
Definition: eval.c:55
int64_t first_timestamp
Definition: hls.c:102
dest
Definition: start.py:60
int ff_check_interrupt(AVIOInterruptCB *cb)
Check if the user has requested to interrup a blocking function associated with cb.
Definition: avio.c:428
AVIOContext * pb
I/O context.
Definition: avformat.h:977
int seek_flags
Definition: hls.c:104
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition: log.h:148
static int hls_read_header(AVFormatContext *s)
Definition: hls.c:476
AVFormatContext * parent
Definition: hls.c:77
void * buf
Definition: avisynth_c.h:594
Definition: url.h:41
static int read_packet(AVFormatContext *ctx, AVPacket *pkt)
Definition: libcdio.c:114
int av_dict_set(AVDictionary **pm, const char *key, const char *value, int flags)
Set the given entry in *pm, overwriting an existing entry.
Definition: dict.c:62
void * av_malloc(size_t size)
Allocate a block of size bytes with alignment suitable for all memory accesses (including vectors if ...
Definition: mem.c:73
synthesis window for stochastic i
void * priv_data
Definition: url.h:44
#define AVSEEK_FLAG_BYTE
seeking based on position in bytes
Definition: avformat.h:1744
int avio_open2(AVIOContext **s, const char *url, int flags, const AVIOInterruptCB *int_cb, AVDictionary **options)
Create and initialize a AVIOContext for accessing the resource indicated by url.
Definition: aviobuf.c:804
char key[MAX_URL_SIZE]
Definition: hls.c:61
#define snprintf
Definition: snprintf.h:34
void avformat_free_context(AVFormatContext *s)
Free an AVFormatContext and all its streams.
This structure contains the data a format has to probe a file.
Definition: avformat.h:334
int ff_hex_to_data(uint8_t *data, const char *p)
Parse a string of hexadecimal strings.
Filter the word “frame” indicates either a video frame or a group of audio as stored in an AVFilterBuffer 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.Buffer references ownership and permissions
int av_read_frame(AVFormatContext *s, AVPacket *pkt)
Return the next frame of a stream.
Round toward -infinity.
Definition: mathematics.h:70
static void handle_variant_args(struct variant_info *info, const char *key, int key_len, char **dest, int *dest_len)
Definition: hls.c:176
AVDictionary * metadata
Definition: avformat.h:894
KeyType
Definition: hls.c:53
static int flags
Definition: cpu.c:23
int ffurl_close(URLContext *h)
Definition: avio.c:359
static int recheck_discard_flags(AVFormatContext *s, int first)
Definition: hls.c:619
void ff_parse_key_value(const char *str, ff_parse_key_val_cb callback_get_buf, void *context)
Parse a string with comma-separated key=value pairs.
char iv[35]
Definition: hls.c:188
#define AVPROBE_SCORE_MAX
maximum score, half of that is used for file-extension-based detection
Definition: avformat.h:340
int av_strstart(const char *str, const char *pfx, const char **ptr)
Return non-zero if pfx is a prefix of str.
Definition: avstring.c:33
Main libavformat public API header.
char uri[MAX_URL_SIZE]
Definition: hls.c:186
#define INITIAL_BUFFER_SIZE
Definition: hls.c:39
int ffio_init_context(AVIOContext *s, unsigned char *buffer, int buffer_size, int write_flag, void *opaque, int(*read_packet)(void *opaque, uint8_t *buf, int buf_size), int(*write_packet)(void *opaque, uint8_t *buf, int buf_size), int64_t(*seek)(void *opaque, int64_t offset, int whence))
Definition: aviobuf.c:71
int ffurl_open(URLContext **puc, const char *filename, int flags, const AVIOInterruptCB *int_cb, AVDictionary **options)
Create an URLContext for accessing to the resource indicated by url, and open it. ...
Definition: avio.c:247
int avformat_find_stream_info(AVFormatContext *ic, AVDictionary **options)
Read packets of a media file to get stream information.
int64_t start_time
Decoding: pts of the first frame of the stream in presentation order, in stream time base...
Definition: avformat.h:689
static int parse_playlist(HLSContext *c, const char *url, struct variant *var, AVIOContext *in)
Definition: hls.c:206
static double c[64]
int cur_seq_no
Definition: hls.c:99
int ffurl_read_complete(URLContext *h, unsigned char *buf, int size)
Read as many bytes as possible (up to size), calling the read function multiple times if necessary...
Definition: avio.c:310
int stream_offset
Definition: hls.c:81
int64_t pos
position in the file of the current buffer
Definition: avio.h:94
int pts_wrap_bits
number of bits in pts (used for wrapping control)
Definition: avformat.h:773
void av_init_packet(AVPacket *pkt)
Initialize optional fields of a packet with default values.
Definition: avpacket.c:56
int den
denominator
Definition: rational.h:45
int cur_seq_no
Definition: hls.c:89
void avformat_close_input(AVFormatContext **s)
Close an opened input AVFormatContext.
static int hls_probe(AVProbeData *p)
Definition: hls.c:806
static int hls_read_seek(AVFormatContext *s, int stream_index, int64_t timestamp, int flags)
Definition: hls.c:745
int av_opt_get(void *obj, const char *name, int search_flags, uint8_t **out_val)
Definition: opt.c:566
int eof_reached
true if eof reached
Definition: avio.h:96
int len
void * priv_data
Format private data.
Definition: avformat.h:964
Definition: hls.c:71
int64_t dts
Decompression timestamp in AVStream->time_base units; the time at which the packet is decompressed...
int64_t duration
Decoding: duration of the stream, in AV_TIME_BASE fractional seconds.
Definition: avformat.h:1009
#define AV_LOG_INFO
Definition: log.h:156
void INT64 start
Definition: avisynth_c.h:594
const char * name
A comma separated list of short names for the format.
Definition: avformat.h:461
unbuffered private I/O API
uint8_t key[16]
Definition: hls.c:93
AVRational time_base
This is the fundamental unit of time (in seconds) in terms of which frame timestamps are represented...
Definition: avformat.h:679
AVPacket pkt
Definition: hls.c:80
static void free_variant_list(HLSContext *c)
Definition: hls.c:127
enum AVDiscard discard
Selects which packets can be discarded at will and do not need to be demuxed.
Definition: avformat.h:702
static int hls_close(AVFormatContext *s)
Definition: hls.c:737
char * ff_data_to_hex(char *buf, const uint8_t *src, int size, int lowercase)
This structure stores compressed data.
int av_opt_set(void *obj, const char *name, const char *val, int search_flags)
Definition: opt.c:252
void ff_make_absolute_url(char *buf, int size, const char *base, const char *rel)
Convert a relative url into an absolute url, given a base url.
int ffurl_read(URLContext *h, unsigned char *buf, int size)
Read up to size bytes from the resource accessed by h, and store the read bytes in buf...
Definition: avio.c:303
Definition: hls.c:54
for(j=16;j >0;--j)
#define AV_NOPTS_VALUE
Undefined timestamp value.
Definition: avutil.h:190
static av_cold void cleanup(FlashSV2Context *s)
Definition: flashsv2enc.c:128
AVFormatContext * ctx
Definition: hls.c:79