2 * Copyright (C) <1999> Erik Walthinsen <omega@cse.ogi.edu>
3 * Copyright (C) <2004> Thomas Vander Stichele <thomas at apestaart dot org>
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Library General Public
7 * License as published by the Free Software Foundation; either
8 * version 2 of the License, or (at your option) any later version.
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Library General Public License for more details.
15 * You should have received a copy of the GNU Library General Public
16 * License along with this library; if not, write to the
17 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 * Boston, MA 02111-1307, USA.
22 #ifndef __GST_MULTI_FD_SINK_H__
23 #define __GST_MULTI_FD_SINK_H__
26 #include <gst/base/gstbasesink.h>
33 #define GST_TYPE_MULTI_FD_SINK \
34 (gst_multi_fd_sink_get_type())
35 #define GST_MULTI_FD_SINK(obj) \
36 (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_MULTI_FD_SINK,GstMultiFdSink))
37 #define GST_MULTI_FD_SINK_CLASS(klass) \
38 (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_MULTI_FD_SINK,GstMultiFdSinkClass))
39 #define GST_IS_MULTI_FD_SINK(obj) \
40 (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_MULTI_FD_SINK))
41 #define GST_IS_MULTI_FD_SINK_CLASS(klass) \
42 (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_MULTI_FD_SINK))
43 #define GST_MULTI_FD_SINK_GET_CLASS(klass) \
44 (G_TYPE_INSTANCE_GET_CLASS ((klass), GST_TYPE_MULTI_FD_SINK, GstMultiFdSinkClass))
47 typedef struct _GstMultiFdSink GstMultiFdSink;
48 typedef struct _GstMultiFdSinkClass GstMultiFdSinkClass;
51 GST_MULTI_FD_SINK_OPEN = (GST_ELEMENT_FLAG_LAST << 0),
53 GST_MULTI_FD_SINK_FLAG_LAST = (GST_ELEMENT_FLAG_LAST << 2),
54 } GstMultiFdSinkFlags;
58 * @GST_RECOVER_POLICY_NONE : no recovering is done
59 * @GST_RECOVER_POLICY_RESYNC_LATEST : client is moved to last buffer
60 * @GST_RECOVER_POLICY_RESYNC_SOFT_LIMIT: client is moved to the soft limit
61 * @GST_RECOVER_POLICY_RESYNC_KEYFRAME : client is moved to latest keyframe
63 * Possible values for the recovery procedure to use when a client consumes
64 * data too slow and has a backlag of more that soft-limit buffers.
68 GST_RECOVER_POLICY_NONE,
69 GST_RECOVER_POLICY_RESYNC_LATEST,
70 GST_RECOVER_POLICY_RESYNC_SOFT_LIMIT,
71 GST_RECOVER_POLICY_RESYNC_KEYFRAME,
76 * @GST_SYNC_METHOD_LATEST : client receives most recent buffer
77 * @GST_SYNC_METHOD_NEXT_KEYFRAME : client receives next keyframe
78 * @GST_SYNC_METHOD_LATEST_KEYFRAME: client receives latest keyframe (burst)
80 * This enum defines the selection of the first buffer that is sent
85 GST_SYNC_METHOD_LATEST,
86 GST_SYNC_METHOD_NEXT_KEYFRAME,
87 GST_SYNC_METHOD_LATEST_KEYFRAME,
92 * @GST_UNIT_TYPE_BUFFERS: a buffer
93 * @GST_UNIT_TYPE_TIME : timeunits (in nanoseconds)
94 * @GST_UNIT_TYPE_BYTES : bytes
96 * The units used to specify limits.
100 GST_UNIT_TYPE_BUFFERS,
107 * @GST_CLIENT_STATUS_OK : client is ok
108 * @GST_CLIENT_STATUS_CLOSED : client closed the socket
109 * @GST_CLIENT_STATUS_REMOVED : client is removed
110 * @GST_CLIENT_STATUS_SLOW : client is too slow
111 * @GST_CLIENT_STATUS_ERROR : client is in error
112 * @GST_CLIENT_STATUS_DUPLICATE: same client added twice
114 * This specifies the reason why a client was removed from
115 * multifdsink and is received in the "client-removed" signal.
119 GST_CLIENT_STATUS_OK = 0,
120 GST_CLIENT_STATUS_CLOSED = 1,
121 GST_CLIENT_STATUS_REMOVED = 2,
122 GST_CLIENT_STATUS_SLOW = 3,
123 GST_CLIENT_STATUS_ERROR = 4,
124 GST_CLIENT_STATUS_DUPLICATE = 5,
127 /* structure for a client
132 gint bufpos; /* position of this client in the global queue */
134 GstClientStatus status;
137 GSList *sending; /* the buffers we need to send */
138 gint bufoffset; /* offset in the first buffer */
142 GstTCPProtocol protocol;
145 gboolean streamheader_sent;
146 gboolean new_connection;
150 guint64 connect_time;
151 guint64 disconnect_time;
152 guint64 last_activity_time;
153 guint64 dropped_buffers;
154 guint64 avg_queue_size;
158 #define CLIENTS_LOCK_INIT(fdsink) (g_static_rec_mutex_init(&fdsink->clientslock))
159 #define CLIENTS_LOCK_FREE(fdsink) (g_static_rec_mutex_free(&fdsink->clientslock))
160 #define CLIENTS_LOCK(fdsink) (g_static_rec_mutex_lock(&fdsink->clientslock))
161 #define CLIENTS_UNLOCK(fdsink) (g_static_rec_mutex_unlock(&fdsink->clientslock))
166 * The multifdsink object structure.
168 struct _GstMultiFdSink {
172 guint64 bytes_to_serve; /* how much bytes we must serve */
173 guint64 bytes_served; /* how much bytes have we served */
175 GStaticRecMutex clientslock; /* lock to protect the clients list */
176 GList *clients; /* list of clients we are serving */
177 GHashTable *fd_hash; /* index on fd to client */
182 GstFD control_sock[2];/* sockets for controlling the select call */
184 GSList *streamheader; /* GSList of GstBuffers to use as streamheader */
185 gboolean previous_buffer_in_caps;
187 GstTCPProtocol protocol;
190 GArray *bufqueue; /* global queue of buffers */
192 gboolean running; /* the thread state */
193 GThread *thread; /* the sender thread */
195 GstUnitType unit_type;/* the type of the units */
196 gint units_max; /* max units to queue */
197 gint units_soft_max; /* max units a client can lag before recovery starts */
198 GstRecoverPolicy recover_policy;
199 GstClockTime timeout; /* max amount of nanoseconds to remain idle */
200 GstSyncMethod sync_method; /* what method to use for connecting clients */
203 gint buffers_queued; /* number of queued buffers */
204 gint bytes_queued; /* number of queued bytes */
205 gint time_queued; /* number of queued time */
208 struct _GstMultiFdSinkClass {
209 GstBaseSinkClass parent_class;
211 /* element methods */
212 void (*add) (GstMultiFdSink *sink, int fd);
213 void (*remove) (GstMultiFdSink *sink, int fd);
214 void (*clear) (GstMultiFdSink *sink);
215 GValueArray* (*get_stats) (GstMultiFdSink *sink, int fd);
218 gboolean (*init) (GstMultiFdSink *sink);
219 gboolean (*wait) (GstMultiFdSink *sink, GstFDSet *set);
220 gboolean (*close) (GstMultiFdSink *sink);
221 void (*removed) (GstMultiFdSink *sink, int fd);
224 void (*client_added) (GstElement *element, gint fd);
225 void (*client_removed) (GstElement *element, gint fd, GstClientStatus status);
226 void (*client_fd_removed) (GstElement *element, gint fd);
229 GType gst_multi_fd_sink_get_type (void);
231 void gst_multi_fd_sink_add (GstMultiFdSink *sink, int fd);
232 void gst_multi_fd_sink_remove (GstMultiFdSink *sink, int fd);
233 void gst_multi_fd_sink_clear (GstMultiFdSink *sink);
234 GValueArray* gst_multi_fd_sink_get_stats (GstMultiFdSink *sink, int fd);
238 #endif /* __GST_MULTI_FD_SINK_H__ */