Browse code

lavf/segment: add segment_list_entry_prefix option

This option allows to add a prefix to the segment list entry filenames.

Also set by default the list entry filenames to the corresponding
segment basename, consistent with the HLS muxer.

Based on an idea by Steven Liu <lingjiujianke@gmail.com>.

Stefano Sabatini authored on 2013/11/22 20:49:05
Showing 3 changed files
... ...
@@ -674,7 +674,9 @@ The segment muxer works best with a single constant frame rate video.
674 674
 
675 675
 Optionally it can generate a list of the created segments, by setting
676 676
 the option @var{segment_list}. The list type is specified by the
677
-@var{segment_list_type} option.
677
+@var{segment_list_type} option. The entry filenames in the segment
678
+list are set by default to the basename of the corresponding segment
679
+files.
678 680
 
679 681
 The segment muxer supports the following options:
680 682
 
... ...
@@ -711,6 +713,10 @@ Update the list file so that it contains at most the last @var{size}
711 711
 segments. If 0 the list file will contain all the segments. Default
712 712
 value is 0.
713 713
 
714
+@item segment_list_entry_prefix @var{prefix}
715
+Set @var{prefix} to prepend to the name of each entry filename. By
716
+default no prefix is applied.
717
+
714 718
 @item segment_list_type @var{type}
715 719
 Specify the format for the segment list file.
716 720
 
... ...
@@ -44,7 +44,7 @@ typedef struct SegmentListEntry {
44 44
     double start_time, end_time;
45 45
     int64_t start_pts;
46 46
     int64_t offset_pts;
47
-    char filename[1024];
47
+    char *filename;
48 48
     struct SegmentListEntry *next;
49 49
 } SegmentListEntry;
50 50
 
... ...
@@ -72,6 +72,7 @@ typedef struct {
72 72
     char *list;            ///< filename for the segment list file
73 73
     int   list_flags;      ///< flags affecting list generation
74 74
     int   list_size;       ///< number of entries for the segment list file
75
+    char *list_entry_prefix; ///< prefix to add to list entry filenames
75 76
     ListType list_type;    ///< set the list type
76 77
     AVIOContext *list_pb;  ///< list file put-byte context
77 78
     char *time_str;        ///< segment duration specification string
... ...
@@ -158,6 +159,7 @@ static int set_segment_filename(AVFormatContext *s)
158 158
 {
159 159
     SegmentContext *seg = s->priv_data;
160 160
     AVFormatContext *oc = seg->avf;
161
+    size_t size;
161 162
 
162 163
     if (seg->segment_idx_wrap)
163 164
         seg->segment_idx %= seg->segment_idx_wrap;
... ...
@@ -166,7 +168,19 @@ static int set_segment_filename(AVFormatContext *s)
166 166
         av_log(oc, AV_LOG_ERROR, "Invalid segment filename template '%s'\n", s->filename);
167 167
         return AVERROR(EINVAL);
168 168
     }
169
-    av_strlcpy(seg->cur_entry.filename, oc->filename, sizeof(seg->cur_entry.filename));
169
+
170
+    /* copy modified name in list entry */
171
+    size = strlen(av_basename(oc->filename)) + 1;
172
+    if (seg->list_entry_prefix)
173
+        size += strlen(seg->list_entry_prefix);
174
+
175
+    seg->cur_entry.filename = av_mallocz(size);
176
+    if (!seg->cur_entry.filename)
177
+        return AVERROR(ENOMEM);
178
+    snprintf(seg->cur_entry.filename, size, "%s%s",
179
+             seg->list_entry_prefix ? seg->list_entry_prefix : "",
180
+             av_basename(oc->filename));
181
+
170 182
     return 0;
171 183
 }
172 184
 
... ...
@@ -303,6 +317,7 @@ static int segment_end(AVFormatContext *s, int write_trailer, int is_last)
303 303
             if (seg->list_size && seg->segment_count > seg->list_size) {
304 304
                 entry = seg->segment_list_entries;
305 305
                 seg->segment_list_entries = seg->segment_list_entries->next;
306
+                av_free(entry->filename);
306 307
                 av_freep(&entry);
307 308
             }
308 309
 
... ...
@@ -746,6 +761,7 @@ fail:
746 746
     cur = seg->segment_list_entries;
747 747
     while (cur) {
748 748
         next = cur->next;
749
+        av_free(cur->filename);
749 750
         av_free(cur);
750 751
         cur = next;
751 752
     }
... ...
@@ -766,6 +782,7 @@ static const AVOption options[] = {
766 766
     { "live",              "enable live-friendly list generation (useful for HLS)", 0, AV_OPT_TYPE_CONST, {.i64 = SEGMENT_LIST_FLAG_LIVE }, INT_MIN, INT_MAX,    E, "list_flags"},
767 767
 
768 768
     { "segment_list_size", "set the maximum number of playlist entries", OFFSET(list_size), AV_OPT_TYPE_INT,  {.i64 = 0},     0, INT_MAX, E },
769
+    { "segment_list_entry_prefix", "set prefix to prepend to each list entry filename", OFFSET(list_entry_prefix), AV_OPT_TYPE_STRING,  {.str = NULL}, 0, 0, E },
769 770
 
770 771
     { "segment_list_type", "set the segment list type",                  OFFSET(list_type), AV_OPT_TYPE_INT,  {.i64 = LIST_TYPE_UNDEFINED}, -1, LIST_TYPE_NB-1, E, "list_type" },
771 772
     { "flat", "flat format",     0, AV_OPT_TYPE_CONST, {.i64=LIST_TYPE_FLAT }, INT_MIN, INT_MAX, E, "list_type" },
... ...
@@ -31,7 +31,7 @@
31 31
 
32 32
 #define LIBAVFORMAT_VERSION_MAJOR 55
33 33
 #define LIBAVFORMAT_VERSION_MINOR 21
34
-#define LIBAVFORMAT_VERSION_MICRO 101
34
+#define LIBAVFORMAT_VERSION_MICRO 102
35 35
 
36 36
 #define LIBAVFORMAT_VERSION_INT AV_VERSION_INT(LIBAVFORMAT_VERSION_MAJOR, \
37 37
                                                LIBAVFORMAT_VERSION_MINOR, \