FFmpeg
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
teeproto.c
Go to the documentation of this file.
1 /*
2  * Tee output protocol
3  * Copyright (c) 2016 Michael Niedermayer
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 #include "libavutil/avstring.h"
23 #include "libavutil/opt.h"
24 #include "avformat.h"
25 #include "avio_internal.h"
26 #include "tee_common.h"
27 
28 typedef struct ChildContext {
30 } ChildContext;
31 
32 typedef struct TeeContext {
33  const AVClass *class;
36 } TeeContext;
37 
38 static const AVOption tee_options[] = {
39  { NULL }
40 };
41 
42 static const AVClass tee_class = {
43  .class_name = "tee",
44  .item_name = av_default_item_name,
45  .option = tee_options,
46  .version = LIBAVUTIL_VERSION_INT,
47 };
48 
49 static const char *const child_delim = "|";
50 
51 static int tee_write(URLContext *h, const unsigned char *buf, int size)
52 {
53  TeeContext *c = h->priv_data;
54  int i;
55  int main_ret = size;
56 
57  for (i=0; i<c->child_count; i++) {
58  int ret = ffurl_write(c->child[i].url_context, buf, size);
59  if (ret < 0)
60  main_ret = ret;
61  }
62  return main_ret;
63 }
64 
65 static int tee_close(URLContext *h)
66 {
67  TeeContext *c = h->priv_data;
68  int i;
69  int main_ret = 0;
70 
71  for (i=0; i<c->child_count; i++) {
72  int ret = ffurl_closep(&c->child[i].url_context);
73  if (ret < 0)
74  main_ret = ret;
75  }
76 
77  av_freep(&c->child);
78  c->child_count = 0;
79  return main_ret;
80 }
81 
82 static int tee_open(URLContext *h, const char *filename, int flags)
83 {
84  TeeContext *c = h->priv_data;
85  int ret, i;
86 
87  av_strstart(filename, "tee:", &filename);
88 
89  if (flags & AVIO_FLAG_READ)
90  return AVERROR(ENOSYS);
91 
92  while (*filename) {
93  char *child_string = av_get_token(&filename, child_delim);
94  char *child_name = NULL;
95  void *tmp;
97  if (!child_string) {
98  ret = AVERROR(ENOMEM);
99  goto fail;
100  }
101 
102  tmp = av_realloc_array(c->child, c->child_count + 1, sizeof(*c->child));
103  if (!tmp) {
104  ret = AVERROR(ENOMEM);
105  goto loop_fail;
106  }
107  c->child = tmp;
108  memset(&c->child[c->child_count], 0, sizeof(c->child[c->child_count]));
109 
110  ret = ff_tee_parse_slave_options(h, child_string, &options, &child_name);
111  if (ret < 0)
112  goto loop_fail;
113 
114  ret = ffurl_open_whitelist(&c->child[c->child_count].url_context, child_name, flags,
115  &h->interrupt_callback, &options,
117  h);
118 loop_fail:
119  av_freep(&child_string);
120  av_dict_free(&options);
121  if (ret < 0)
122  goto fail;
123  c->child_count++;
124 
125  if (strspn(filename, child_delim))
126  filename++;
127  }
128 
129  h->is_streamed = 0;
130  for (i=0; i<c->child_count; i++) {
132  }
133 
134  return 0;
135 fail:
136  tee_close(h);
137  return ret;
138 }
140  .name = "tee",
141  .url_open = tee_open,
142  .url_write = tee_write,
143  .url_close = tee_close,
144  .priv_data_size = sizeof(TeeContext),
145  .priv_data_class = &tee_class,
146  .default_whitelist = "crypto,file,http,https,httpproxy,rtmp,tcp,tls"
147 };
#define NULL
Definition: coverity.c:32
int ffurl_open_whitelist(URLContext **puc, const char *filename, int flags, const AVIOInterruptCB *int_cb, AVDictionary **options, const char *whitelist, const char *blacklist, URLContext *parent)
Create an URLContext for accessing to the resource indicated by url, and open it. ...
Definition: avio.c:309
AVOption.
Definition: opt.h:245
#define LIBAVUTIL_VERSION_INT
Definition: version.h:85
static const char *const child_delim
Definition: teeproto.c:49
int ffurl_write(URLContext *h, const unsigned char *buf, int size)
Write size bytes from buf to the resource accessed by h.
Definition: avio.c:421
int is_streamed
true if streamed (no seek possible), default = false
Definition: url.h:45
static const AVClass tee_class
Definition: teeproto.c:42
AVIOInterruptCB interrupt_callback
Definition: url.h:47
#define AVIO_FLAG_READ
read-only
Definition: avio.h:606
static int tee_write(URLContext *h, const unsigned char *buf, int size)
Definition: teeproto.c:51
int child_count
Definition: teeproto.c:34
const char * class_name
The name of the class; usually it is the same name as the context structure type to which the AVClass...
Definition: log.h:72
AVOptions.
URLContext * url_context
Definition: teeproto.c:29
ptrdiff_t size
Definition: opengl_enc.c:101
void * av_realloc_array(void *ptr, size_t nmemb, size_t size)
Definition: mem.c:208
const OptionDef options[]
Definition: ffserver.c:3969
const char * protocol_whitelist
Definition: url.h:49
av_default_item_name
#define AVERROR(e)
Definition: error.h:43
void av_dict_free(AVDictionary **pm)
Free all the memory allocated for an AVDictionary struct and all keys and values. ...
Definition: dict.c:203
#define fail()
Definition: checkasm.h:83
char * av_get_token(const char **buf, const char *term)
Unescape the given string until a non escaped terminating char, and return the token corresponding to...
Definition: avstring.c:149
static int tee_close(URLContext *h)
Definition: teeproto.c:65
ChildContext * child
Definition: teeproto.c:35
int ff_tee_parse_slave_options(void *log, char *slave, AVDictionary **options, char **filename)
Definition: tee_common.c:32
static const AVOption tee_options[]
Definition: teeproto.c:38
int ffurl_closep(URLContext **hh)
Close the resource accessed by the URLContext h, and free the memory used by it.
Definition: avio.c:444
const char * protocol_blacklist
Definition: url.h:50
Definition: tee.c:50
void * buf
Definition: avisynth_c.h:690
Definition: url.h:38
Describe the class of an AVClass context structure.
Definition: log.h:67
void * priv_data
Definition: url.h:41
const char * name
Definition: url.h:54
static int flags
Definition: cpu.c:47
static int tee_open(URLContext *h, const char *filename, int flags)
Definition: teeproto.c:82
const URLProtocol ff_tee_protocol
Definition: teeproto.c:139
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:34
Main libavformat public API header.
static double c[64]
static uint8_t tmp[8]
Definition: des.c:38
#define av_freep(p)