static FsMsnPollFD * add_pollfd_locked (FsMsnConnection *self, int fd, PollFdCallback callback, gboolean read, gboolean write, gboolean server) { FsMsnPollFD *pollfd = g_slice_new0 (FsMsnPollFD); gst_poll_fd_init (&pollfd->pollfd); pollfd->pollfd.fd = fd; pollfd->server = server; pollfd->want_read = read; pollfd->want_write = write; pollfd->status = FS_MSN_STATUS_AUTH; gst_poll_add_fd (self->poll, &pollfd->pollfd); gst_poll_fd_ctl_read (self->poll, &pollfd->pollfd, read); gst_poll_fd_ctl_write (self->poll, &pollfd->pollfd, write); pollfd->callback = callback; GST_DEBUG ("ADD_POLLFD %p (%p) - error %d, close %d, read %d-%d, write %d-%d", self->pollfds, pollfd, gst_poll_fd_has_error (self->poll, &pollfd->pollfd), gst_poll_fd_has_closed (self->poll, &pollfd->pollfd), pollfd->want_read, gst_poll_fd_can_read (self->poll, &pollfd->pollfd), pollfd->want_write, gst_poll_fd_can_write (self->poll, &pollfd->pollfd)); g_ptr_array_add (self->pollfds, pollfd); gst_poll_restart (self->poll); return pollfd; }
static GstFlowReturn gst_shm_src_create (GstPushSrc * psrc, GstBuffer ** outbuf) { GstShmSrc *self = GST_SHM_SRC (psrc); gchar *buf = NULL; int rv = 0; struct GstShmBuffer *gsb; do { if (gst_poll_wait (self->poll, GST_CLOCK_TIME_NONE) < 0) { if (errno == EBUSY) return GST_FLOW_FLUSHING; GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed to read from shmsrc"), ("Poll failed on fd: %s", strerror (errno))); return GST_FLOW_ERROR; } if (self->unlocked) return GST_FLOW_FLUSHING; if (gst_poll_fd_has_closed (self->poll, &self->pollfd)) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed to read from shmsrc"), ("Control socket has closed")); return GST_FLOW_ERROR; } if (gst_poll_fd_has_error (self->poll, &self->pollfd)) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed to read from shmsrc"), ("Control socket has error")); return GST_FLOW_ERROR; } if (gst_poll_fd_can_read (self->poll, &self->pollfd)) { buf = NULL; GST_LOG_OBJECT (self, "Reading from pipe"); GST_OBJECT_LOCK (self); rv = sp_client_recv (self->pipe->pipe, &buf); GST_OBJECT_UNLOCK (self); if (rv < 0) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed to read from shmsrc"), ("Error reading control data: %d", rv)); return GST_FLOW_ERROR; } } } while (buf == NULL); GST_LOG_OBJECT (self, "Got buffer %p of size %d", buf, rv); gsb = g_slice_new0 (struct GstShmBuffer); gsb->buf = buf; gsb->pipe = self->pipe; gst_shm_pipe_inc (self->pipe); *outbuf = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY, buf, rv, 0, rv, gsb, free_buffer); return GST_FLOW_OK; }
static gboolean exchange_packets (GstPluginLoader * l) { gint res; /* Wait for activity on our FDs */ do { do { res = gst_poll_wait (l->fdset, GST_SECOND); } while (res == -1 && (errno == EINTR || errno == EAGAIN)); if (res < 0) return FALSE; GST_LOG ("Poll res = %d. %d bytes pending for write", res, l->tx_buf_write - l->tx_buf_read); if (!l->rx_done) { if (gst_poll_fd_has_error (l->fdset, &l->fd_r) || gst_poll_fd_has_closed (l->fdset, &l->fd_r)) { GST_LOG ("read fd %d closed/errored", l->fd_r.fd); goto fail_and_cleanup; } if (gst_poll_fd_can_read (l->fdset, &l->fd_r)) { if (!read_one (l)) goto fail_and_cleanup; } } if (l->tx_buf_read < l->tx_buf_write) { if (gst_poll_fd_has_error (l->fdset, &l->fd_w) || gst_poll_fd_has_closed (l->fdset, &l->fd_r)) { GST_ERROR ("write fd %d closed/errored", l->fd_w.fd); goto fail_and_cleanup; } if (gst_poll_fd_can_write (l->fdset, &l->fd_w)) { if (!write_one (l)) goto fail_and_cleanup; } } } while (l->tx_buf_read < l->tx_buf_write); return TRUE; fail_and_cleanup: plugin_loader_cleanup_child (l); return FALSE; }
static gpointer pollthread_func (gpointer data) { GstShmSink *self = GST_SHM_SINK (data); GList *item; GstClockTime timeout = GST_CLOCK_TIME_NONE; int rv = 0; while (!self->stop) { do { rv = gst_poll_wait (self->poll, timeout); } while (rv < 0 && errno == EINTR); if (rv < 0) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed waiting on fd activity"), ("gst_poll_wait returned %d, errno: %d", rv, errno)); return NULL; } timeout = GST_CLOCK_TIME_NONE; if (self->stop) return NULL; if (gst_poll_fd_has_closed (self->poll, &self->serverpollfd)) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed read from shmsink"), ("Control socket has closed")); return NULL; } if (gst_poll_fd_has_error (self->poll, &self->serverpollfd)) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed to read from shmsink"), ("Control socket has error")); return NULL; } if (gst_poll_fd_can_read (self->poll, &self->serverpollfd)) { ShmClient *client; struct GstShmClient *gclient; GST_OBJECT_LOCK (self); client = sp_writer_accept_client (self->pipe); GST_OBJECT_UNLOCK (self); if (!client) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed to read from shmsink"), ("Control socket returns wrong data")); return NULL; } gclient = g_slice_new (struct GstShmClient); gclient->client = client; gst_poll_fd_init (&gclient->pollfd); gclient->pollfd.fd = sp_writer_get_client_fd (client); gst_poll_add_fd (self->poll, &gclient->pollfd); gst_poll_fd_ctl_read (self->poll, &gclient->pollfd, TRUE); self->clients = g_list_prepend (self->clients, gclient); g_signal_emit (self, signals[SIGNAL_CLIENT_CONNECTED], 0, gclient->pollfd.fd); /* we need to call gst_poll_wait before calling gst_poll_* status functions on that new descriptor, so restart the loop, so _wait will have been called on all elements of self->poll, whether they have just been added or not. */ timeout = 0; continue; } again: for (item = self->clients; item; item = item->next) { struct GstShmClient *gclient = item->data; if (gst_poll_fd_has_closed (self->poll, &gclient->pollfd)) { GST_WARNING_OBJECT (self, "One client is gone, closing"); goto close_client; } if (gst_poll_fd_has_error (self->poll, &gclient->pollfd)) { GST_WARNING_OBJECT (self, "One client fd has error, closing"); goto close_client; } if (gst_poll_fd_can_read (self->poll, &gclient->pollfd)) { int rv; gpointer tag = NULL; GST_OBJECT_LOCK (self); rv = sp_writer_recv (self->pipe, gclient->client, &tag); GST_OBJECT_UNLOCK (self); if (rv < 0) { GST_WARNING_OBJECT (self, "One client has read error," " closing (retval: %d errno: %d)", rv, errno); goto close_client; } g_assert (rv == 0 || tag == NULL); if (rv == 0) gst_buffer_unref (tag); } continue; close_client: { GSList *list = NULL; GST_OBJECT_LOCK (self); sp_writer_close_client (self->pipe, gclient->client, (sp_buffer_free_callback) free_buffer_locked, (void **) &list); GST_OBJECT_UNLOCK (self); g_slist_free_full (list, (GDestroyNotify) gst_buffer_unref); } gst_poll_remove_fd (self->poll, &gclient->pollfd); self->clients = g_list_remove (self->clients, gclient); g_signal_emit (self, signals[SIGNAL_CLIENT_DISCONNECTED], 0, gclient->pollfd.fd); g_slice_free (struct GstShmClient, gclient); goto again; } g_cond_broadcast (&self->cond); }
static gpointer connection_polling_thread (gpointer data) { FsMsnConnection *self = data; gint ret; GstClockTime timeout; GstPoll * poll; FS_MSN_CONNECTION_LOCK(self); timeout = self->poll_timeout; poll = self->poll; GST_DEBUG ("poll waiting %d", self->pollfds->len); FS_MSN_CONNECTION_UNLOCK(self); while ((ret = gst_poll_wait (poll, timeout)) >= 0) { GST_DEBUG ("gst_poll_wait returned : %d", ret); FS_MSN_CONNECTION_LOCK(self); if (ret > 0) { gint i; for (i = 0; i < self->pollfds->len; i++) { FsMsnPollFD *pollfd = NULL; pollfd = g_ptr_array_index(self->pollfds, i); GST_DEBUG ("ret %d - i = %d, len = %d", ret, i, self->pollfds->len); GST_DEBUG ("%p - error %d, close %d, read %d-%d, write %d-%d", pollfd, gst_poll_fd_has_error (poll, &pollfd->pollfd), gst_poll_fd_has_closed (poll, &pollfd->pollfd), pollfd->want_read, gst_poll_fd_can_read (poll, &pollfd->pollfd), pollfd->want_write, gst_poll_fd_can_write (poll, &pollfd->pollfd)); if (gst_poll_fd_has_error (poll, &pollfd->pollfd) || gst_poll_fd_has_closed (poll, &pollfd->pollfd)) { pollfd->callback (self, pollfd); shutdown_fd_locked (self, pollfd, TRUE); i--; continue; } if ((pollfd->want_read && gst_poll_fd_can_read (poll, &pollfd->pollfd)) || (pollfd->want_write && gst_poll_fd_can_write (poll, &pollfd->pollfd))) { pollfd->callback (self, pollfd); } } } timeout = self->poll_timeout; FS_MSN_CONNECTION_UNLOCK(self); } return NULL; }
static void connection_cb (FsMsnConnection *self, FsMsnPollFD *pollfd) { gboolean success = FALSE; GST_DEBUG ("handler called on fd:%d server: %d status:%d r:%d w:%d", pollfd->pollfd.fd, pollfd->server, pollfd->status, gst_poll_fd_can_read (self->poll, &pollfd->pollfd), gst_poll_fd_can_write (self->poll, &pollfd->pollfd)); if (gst_poll_fd_has_error (self->poll, &pollfd->pollfd) || gst_poll_fd_has_closed (self->poll, &pollfd->pollfd)) { GST_WARNING ("connecton closed or error (error: %d closed: %d)", gst_poll_fd_has_error (self->poll, &pollfd->pollfd), gst_poll_fd_has_closed (self->poll, &pollfd->pollfd)); goto error; } if (gst_poll_fd_can_read (self->poll, &pollfd->pollfd)) { switch (pollfd->status) { case FS_MSN_STATUS_AUTH: if (pollfd->server) { gchar str[35] = {0}; gchar check[35] = {0}; if (recv (pollfd->pollfd.fd, str, 34, 0) == 34) { GST_DEBUG ("Got %s, checking if it's auth", str); FS_MSN_CONNECTION_LOCK(self); snprintf(check, 35, "recipientid=%s&sessionid=%d\r\n\r\n", self->local_recipient_id, self->session_id); FS_MSN_CONNECTION_UNLOCK(self); if (strncmp (str, check, 35) == 0) { GST_DEBUG ("Authentication successful"); pollfd->status = FS_MSN_STATUS_CONNECTED; pollfd->want_write = TRUE; gst_poll_fd_ctl_write (self->poll, &pollfd->pollfd, TRUE); } else { GST_WARNING ("Authentication failed check=%s", check); goto error; } } else { gchar error_str[256]; strerror_r (errno, error_str, 256); GST_WARNING ("auth: %s", error_str); goto error; } } else { GST_ERROR ("shouldn't receive data when client on AUTH state"); goto error; } break; case FS_MSN_STATUS_CONNECTED: if (!pollfd->server) { gchar str[14] = {0}; ssize_t size; size = recv (pollfd->pollfd.fd, str, 13, MSG_PEEK); if (size > 0) { GST_DEBUG ("Got %s, checking if it's connected", str); if (size == 13 && strcmp (str, "connected\r\n\r\n") == 0) { GST_DEBUG ("connection successful"); recv (pollfd->pollfd.fd, str, 13, 0); pollfd->status = FS_MSN_STATUS_CONNECTED2; pollfd->want_write = TRUE; gst_poll_fd_ctl_write (self->poll, &pollfd->pollfd, TRUE); } else if (!self->producer) { GST_DEBUG ("connection successful"); pollfd->status = FS_MSN_STATUS_SEND_RECEIVE; success = TRUE; } else { GST_WARNING ("connected failed"); goto error; } } else { gchar error_str[256]; strerror_r (errno, error_str, 256); GST_WARNING ("recv: %s", error_str); goto error; } } else { GST_ERROR ("shouldn't receive data when server on CONNECTED state"); goto error; } break; case FS_MSN_STATUS_CONNECTED2: if (pollfd->server) { gchar str[14] = {0}; ssize_t size; size = recv (pollfd->pollfd.fd, str, 13, MSG_PEEK); if (size > 0) { GST_DEBUG ("Got %s, checking if it's connected", str); if (size == 13 && strcmp (str, "connected\r\n\r\n") == 0) { GST_DEBUG ("connection successful"); recv (pollfd->pollfd.fd, str, 13, 0); pollfd->status = FS_MSN_STATUS_SEND_RECEIVE; success = TRUE; } else if (!self->producer) { GST_DEBUG ("connection successful"); pollfd->status = FS_MSN_STATUS_SEND_RECEIVE; success = TRUE; } else { GST_WARNING ("connected failed"); goto error; } } else { gchar error_str[256]; strerror_r (errno, error_str, 256); GST_WARNING ("recv: %s", error_str); goto error; } } else { GST_ERROR ("shouldn't receive data when client on CONNECTED2 state"); goto error; } break; default: GST_ERROR ("Invalid status %d", pollfd->status); goto error; break; } } else if (gst_poll_fd_can_write (self->poll, &pollfd->pollfd)) { pollfd->want_write = FALSE; gst_poll_fd_ctl_write (self->poll, &pollfd->pollfd, FALSE); switch (pollfd->status) { case FS_MSN_STATUS_AUTH: if (!pollfd->server) { gchar *str; FS_MSN_CONNECTION_LOCK(self); str = g_strdup_printf("recipientid=%s&sessionid=%d\r\n\r\n", self->remote_recipient_id, self->session_id); FS_MSN_CONNECTION_UNLOCK(self); if (send(pollfd->pollfd.fd, str, strlen (str), 0) != -1) { GST_DEBUG ("Sent %s", str); pollfd->status = FS_MSN_STATUS_CONNECTED; g_free (str); } else { gchar error_str[256]; strerror_r (errno, error_str, 256); GST_WARNING ("auth send: %s", error_str); g_free (str); goto error; } } break; case FS_MSN_STATUS_CONNECTED: if (pollfd->server) { if (send(pollfd->pollfd.fd, "connected\r\n\r\n", 13, 0) != -1) { GST_DEBUG ("sent connected"); if (self->producer) { pollfd->status = FS_MSN_STATUS_SEND_RECEIVE; success = TRUE; } else { pollfd->status = FS_MSN_STATUS_CONNECTED2; } } else { gchar error_str[256]; strerror_r (errno, error_str, 256); GST_WARNING ("sending connected: %s", error_str); goto error; } } else { GST_DEBUG ("shouldn't receive data when server on CONNECTED state"); goto error; } break; case FS_MSN_STATUS_CONNECTED2: if (!pollfd->server) { if (send(pollfd->pollfd.fd, "connected\r\n\r\n", 13, 0) != -1) { GST_DEBUG ("sent connected"); pollfd->status = FS_MSN_STATUS_SEND_RECEIVE; success = TRUE; } else { gchar error_str[256]; strerror_r (errno, error_str, 256); GST_WARNING ("sending connected: %s", error_str); goto error; } } else { GST_ERROR ("shouldn't receive data when client on CONNECTED2 state"); goto error; } break; default: GST_ERROR ("Invalid status %d", pollfd->status); goto error; break; } } if (success) { // success! we need to shutdown/close all other channels shutdown_fd (self, pollfd, FALSE); g_signal_emit (self, signals[SIGNAL_CONNECTED], 0, pollfd->pollfd.fd); pollfd->want_read = FALSE; pollfd->want_write = FALSE; gst_poll_fd_ctl_read (self->poll, &pollfd->pollfd, FALSE); gst_poll_fd_ctl_write (self->poll, &pollfd->pollfd, FALSE); } return; error: /* Error */ GST_WARNING ("Got error from fd %d, closing", pollfd->pollfd.fd); shutdown_fd (self, pollfd, TRUE); FS_MSN_CONNECTION_LOCK (self); success = (self->pollfds->len > 1); FS_MSN_CONNECTION_UNLOCK (self); if (!success) g_signal_emit (self, signals[SIGNAL_CONNECTION_FAILED], 0); return; }
static gpointer pollthread_func (gpointer data) { GstShmSink *self = GST_SHM_SINK (data); GList *item; while (!self->stop) { if (gst_poll_wait (self->poll, GST_CLOCK_TIME_NONE) < 0) return NULL; if (self->stop) return NULL; if (gst_poll_fd_has_closed (self->poll, &self->serverpollfd)) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed read from shmsink"), ("Control socket has closed")); return NULL; } if (gst_poll_fd_has_error (self->poll, &self->serverpollfd)) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed to read from shmsink"), ("Control socket has error")); return NULL; } if (gst_poll_fd_can_read (self->poll, &self->serverpollfd)) { ShmClient *client; struct GstShmClient *gclient; GST_OBJECT_LOCK (self); client = sp_writer_accept_client (self->pipe); GST_OBJECT_UNLOCK (self); if (!client) { GST_ELEMENT_ERROR (self, RESOURCE, READ, ("Failed to read from shmsink"), ("Control socket returns wrong data")); return NULL; } gclient = g_slice_new (struct GstShmClient); gclient->client = client; gst_poll_fd_init (&gclient->pollfd); gclient->pollfd.fd = sp_writer_get_client_fd (client); gst_poll_add_fd (self->poll, &gclient->pollfd); gst_poll_fd_ctl_read (self->poll, &gclient->pollfd, TRUE); self->clients = g_list_prepend (self->clients, gclient); g_signal_emit (self, signals[SIGNAL_CLIENT_CONNECTED], 0, gclient->pollfd.fd); } again: for (item = self->clients; item; item = item->next) { struct GstShmClient *gclient = item->data; if (gst_poll_fd_has_closed (self->poll, &gclient->pollfd)) { GST_WARNING_OBJECT (self, "One client is gone, closing"); goto close_client; } if (gst_poll_fd_has_error (self->poll, &gclient->pollfd)) { GST_WARNING_OBJECT (self, "One client fd has error, closing"); goto close_client; } if (gst_poll_fd_can_read (self->poll, &gclient->pollfd)) { int rv; GST_OBJECT_LOCK (self); rv = sp_writer_recv (self->pipe, gclient->client); GST_OBJECT_UNLOCK (self); if (rv < 0) { GST_WARNING_OBJECT (self, "One client has read error," " closing (retval: %d errno: %d)", rv, errno); goto close_client; } } continue; close_client: GST_OBJECT_LOCK (self); sp_writer_close_client (self->pipe, gclient->client); GST_OBJECT_UNLOCK (self); gst_poll_remove_fd (self->poll, &gclient->pollfd); self->clients = g_list_remove (self->clients, gclient); g_signal_emit (self, signals[SIGNAL_CLIENT_DISCONNECTED], 0, gclient->pollfd.fd); g_slice_free (struct GstShmClient, gclient); goto again; } g_cond_broadcast (self->cond); }
static void mess_some_more (void) { GList *walk; gint random; gint removed = 0; g_mutex_lock (fdlock); for (walk = fds; walk;) { GstPollFD *fd = (GstPollFD *) walk->data; walk = g_list_next (walk); random = (gint) (10.0 * rand () / (RAND_MAX + 1.0)); switch (random) { case 0: { /* GstPollFD *newfd = g_new0 (GstPollFD, 1); gst_poll_add_fd (set, newfd); fds = g_list_prepend (fds, newfd); */ break; } case 1: if ((gint) (10.0 * rand () / (RAND_MAX + 1.0)) < 2) { gst_poll_remove_fd (set, fd); fds = g_list_remove (fds, fd); g_free (fd); removed++; } break; case 2: gst_poll_fd_ctl_write (set, fd, TRUE); break; case 3: gst_poll_fd_ctl_write (set, fd, FALSE); break; case 4: gst_poll_fd_ctl_read (set, fd, TRUE); break; case 5: gst_poll_fd_ctl_read (set, fd, FALSE); break; case 6: gst_poll_fd_has_closed (set, fd); break; case 7: gst_poll_fd_has_error (set, fd); break; case 8: gst_poll_fd_can_read (set, fd); break; case 9: gst_poll_fd_can_write (set, fd); break; default: g_assert_not_reached (); break; } } if (g_list_length (fds) < 900) { random = removed + (gint) (2.0 * rand () / (RAND_MAX + 1.0)); while (random) { GstPollFD *newfd = g_new0 (GstPollFD, 1); gst_poll_add_fd (set, newfd); fds = g_list_prepend (fds, newfd); random--; } } g_mutex_unlock (fdlock); }
static GstFlowReturn gst_tcp_server_src_create (GstPushSrc * psrc, GstBuffer ** outbuf) { GstTCPServerSrc *src; GstFlowReturn ret = GST_FLOW_OK; src = GST_TCP_SERVER_SRC (psrc); if (!GST_OBJECT_FLAG_IS_SET (src, GST_TCP_SERVER_SRC_OPEN)) goto wrong_state; restart: if (src->client_sock_fd.fd >= 0) { /* if we have a client, wait for read */ gst_poll_fd_ctl_read (src->fdset, &src->server_sock_fd, FALSE); gst_poll_fd_ctl_read (src->fdset, &src->client_sock_fd, TRUE); } else { /* else wait on server socket for connections */ gst_poll_fd_ctl_read (src->fdset, &src->server_sock_fd, TRUE); } /* no action (0) is an error too in our case */ if ((ret = gst_poll_wait (src->fdset, GST_CLOCK_TIME_NONE)) <= 0) { if (ret == -1 && errno == EBUSY) goto select_cancelled; else goto select_error; } /* if we have no client socket we can accept one now */ if (src->client_sock_fd.fd < 0) { if (gst_poll_fd_can_read (src->fdset, &src->server_sock_fd)) { if ((src->client_sock_fd.fd = accept (src->server_sock_fd.fd, (struct sockaddr *) &src->client_sin, &src->client_sin_len)) == -1) goto accept_error; gst_poll_add_fd (src->fdset, &src->client_sock_fd); } /* and restart now to poll the socket. */ goto restart; } GST_LOG_OBJECT (src, "asked for a buffer"); switch (src->protocol) { case GST_TCP_PROTOCOL_NONE: ret = gst_tcp_read_buffer (GST_ELEMENT (src), src->client_sock_fd.fd, src->fdset, outbuf); break; case GST_TCP_PROTOCOL_GDP: if (!src->caps_received) { GstCaps *caps; gchar *string; ret = gst_tcp_gdp_read_caps (GST_ELEMENT (src), src->client_sock_fd.fd, src->fdset, &caps); if (ret == GST_FLOW_WRONG_STATE) goto gdp_cancelled; if (ret != GST_FLOW_OK) goto gdp_caps_read_error; src->caps_received = TRUE; string = gst_caps_to_string (caps); GST_DEBUG_OBJECT (src, "Received caps through GDP: %s", string); g_free (string); gst_pad_set_caps (GST_BASE_SRC_PAD (psrc), caps); } ret = gst_tcp_gdp_read_buffer (GST_ELEMENT (src), src->client_sock_fd.fd, src->fdset, outbuf); if (ret == GST_FLOW_OK) gst_buffer_set_caps (*outbuf, GST_PAD_CAPS (GST_BASE_SRC_PAD (src))); break; default: /* need to assert as buf == NULL */ g_assert ("Unhandled protocol type"); break; } if (ret == GST_FLOW_OK) { GST_LOG_OBJECT (src, "Returning buffer from _get of size %d, ts %" GST_TIME_FORMAT ", dur %" GST_TIME_FORMAT ", offset %" G_GINT64_FORMAT ", offset_end %" G_GINT64_FORMAT, GST_BUFFER_SIZE (*outbuf), GST_TIME_ARGS (GST_BUFFER_TIMESTAMP (*outbuf)), GST_TIME_ARGS (GST_BUFFER_DURATION (*outbuf)), GST_BUFFER_OFFSET (*outbuf), GST_BUFFER_OFFSET_END (*outbuf)); } return ret; wrong_state: { GST_DEBUG_OBJECT (src, "connection to closed, cannot read data"); return GST_FLOW_WRONG_STATE; } select_error: { GST_ELEMENT_ERROR (src, RESOURCE, READ, (NULL), ("Select error: %s", g_strerror (errno))); return GST_FLOW_ERROR; } select_cancelled: { GST_DEBUG_OBJECT (src, "select canceled"); return GST_FLOW_WRONG_STATE; } accept_error: { GST_ELEMENT_ERROR (src, RESOURCE, OPEN_READ, (NULL), ("Could not accept client on server socket: %s", g_strerror (errno))); return GST_FLOW_ERROR; } gdp_cancelled: { GST_DEBUG_OBJECT (src, "reading gdp canceled"); return GST_FLOW_WRONG_STATE; } gdp_caps_read_error: { /* if we did not get canceled, report an error */ if (ret != GST_FLOW_WRONG_STATE) { GST_ELEMENT_ERROR (src, RESOURCE, READ, (NULL), ("Could not read caps through GDP")); } return ret; } }
static gpointer gst_net_client_clock_thread (gpointer data) { GstNetClientClock *self = data; struct sockaddr_in tmpaddr; socklen_t len; GstNetTimePacket *packet; gint ret; GstClock *clock = data; while (TRUE) { ret = gst_net_client_clock_do_select (self); if (ret < 0 && errno == EBUSY) { GST_LOG_OBJECT (self, "stop"); goto stopped; } else if (ret == 0) { /* timed out, let's send another packet */ GST_DEBUG_OBJECT (self, "timed out"); packet = gst_net_time_packet_new (NULL); packet->local_time = gst_clock_get_internal_time (GST_CLOCK (self)); GST_DEBUG_OBJECT (self, "sending packet, local time = %" GST_TIME_FORMAT, GST_TIME_ARGS (packet->local_time)); gst_net_time_packet_send (packet, self->priv->sock.fd, (struct sockaddr *) self->servaddr, sizeof (struct sockaddr_in)); g_free (packet); /* reset timeout */ self->current_timeout = clock->timeout; continue; } else if (gst_poll_fd_can_read (self->priv->fdset, &self->priv->sock)) { /* got data in */ GstClockTime new_local = gst_clock_get_internal_time (GST_CLOCK (self)); len = sizeof (struct sockaddr); packet = gst_net_time_packet_receive (self->priv->sock.fd, (struct sockaddr *) &tmpaddr, &len); if (!packet) goto receive_error; GST_LOG_OBJECT (self, "got packet back"); GST_LOG_OBJECT (self, "local_1 = %" GST_TIME_FORMAT, GST_TIME_ARGS (packet->local_time)); GST_LOG_OBJECT (self, "remote = %" GST_TIME_FORMAT, GST_TIME_ARGS (packet->remote_time)); GST_LOG_OBJECT (self, "local_2 = %" GST_TIME_FORMAT, GST_TIME_ARGS (new_local)); /* observe_times will reset the timeout */ gst_net_client_clock_observe_times (self, packet->local_time, packet->remote_time, new_local); g_free (packet); continue; } else { GST_WARNING_OBJECT (self, "unhandled select return state?"); continue; } g_assert_not_reached (); stopped: { GST_DEBUG_OBJECT (self, "shutting down"); /* socket gets closed in _stop() */ return NULL; } receive_error: { GST_WARNING_OBJECT (self, "receive error"); continue; } g_assert_not_reached (); } g_assert_not_reached (); return NULL; }