rtspconnection: Consistently translate GIOError to GstRTSPResult
The users of this API need to be able to differentiate between EINTR and ERROR. For example, in rtspsrc, gst_rtsp_conninfo_connect() behaves differently when gst_rtsp_connection_connect_with_response_usec() returns an ERROR or EINTR. The former is an element error while the latter is simple a GST_ERROR since it was a user cancellation of the connection attempt. Due to this, rtspsrc was incorrectly emitting element errors while going to NULL, which would or would not reach the application in a racy manner. Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-base/-/merge_requests/1069>
This commit is contained in:
parent
f4a1428a69
commit
9b01036664
@ -256,6 +256,28 @@ build_reset (GstRTSPBuilder * builder)
|
|||||||
memset (builder, 0, sizeof (GstRTSPBuilder));
|
memset (builder, 0, sizeof (GstRTSPBuilder));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static GstRTSPResult
|
||||||
|
gst_rtsp_result_from_g_io_error (GError * error, GstRTSPResult default_res)
|
||||||
|
{
|
||||||
|
if (error == NULL)
|
||||||
|
return GST_RTSP_OK;
|
||||||
|
|
||||||
|
if (error->domain != G_IO_ERROR)
|
||||||
|
return default_res;
|
||||||
|
|
||||||
|
switch (error->code) {
|
||||||
|
case G_IO_ERROR_TIMED_OUT:
|
||||||
|
return GST_RTSP_ETIMEOUT;
|
||||||
|
case G_IO_ERROR_INVALID_ARGUMENT:
|
||||||
|
return GST_RTSP_EINVAL;
|
||||||
|
case G_IO_ERROR_CANCELLED:
|
||||||
|
case G_IO_ERROR_WOULD_BLOCK:
|
||||||
|
return GST_RTSP_EINTR;
|
||||||
|
default:
|
||||||
|
return default_res;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
tls_accept_certificate (GTlsConnection * conn, GTlsCertificate * peer_cert,
|
tls_accept_certificate (GTlsConnection * conn, GTlsCertificate * peer_cert,
|
||||||
GTlsCertificateFlags errors, GstRTSPConnection * rtspconn)
|
GTlsCertificateFlags errors, GstRTSPConnection * rtspconn)
|
||||||
@ -470,8 +492,9 @@ gst_rtsp_connection_create_from_socket (GSocket * socket, const gchar * ip,
|
|||||||
getnameinfo_failed:
|
getnameinfo_failed:
|
||||||
{
|
{
|
||||||
GST_ERROR ("failed to get local address: %s", err->message);
|
GST_ERROR ("failed to get local address: %s", err->message);
|
||||||
|
res = gst_rtsp_result_from_g_io_error (err, GST_RTSP_ERROR);
|
||||||
g_clear_error (&err);
|
g_clear_error (&err);
|
||||||
return GST_RTSP_ERROR;
|
return res;
|
||||||
}
|
}
|
||||||
newconn_failed:
|
newconn_failed:
|
||||||
{
|
{
|
||||||
@ -526,19 +549,21 @@ gst_rtsp_connection_accept (GSocket * socket, GstRTSPConnection ** conn,
|
|||||||
accept_failed:
|
accept_failed:
|
||||||
{
|
{
|
||||||
GST_DEBUG ("Accepting client failed: %s", err->message);
|
GST_DEBUG ("Accepting client failed: %s", err->message);
|
||||||
|
ret = gst_rtsp_result_from_g_io_error (err, GST_RTSP_ESYS);
|
||||||
g_clear_error (&err);
|
g_clear_error (&err);
|
||||||
return GST_RTSP_ESYS;
|
return ret;
|
||||||
}
|
}
|
||||||
getnameinfo_failed:
|
getnameinfo_failed:
|
||||||
{
|
{
|
||||||
GST_DEBUG ("getnameinfo failed: %s", err->message);
|
GST_DEBUG ("getnameinfo failed: %s", err->message);
|
||||||
|
ret = gst_rtsp_result_from_g_io_error (err, GST_RTSP_ERROR);
|
||||||
g_clear_error (&err);
|
g_clear_error (&err);
|
||||||
if (!g_socket_close (client_sock, &err)) {
|
if (!g_socket_close (client_sock, &err)) {
|
||||||
GST_DEBUG ("Closing socket failed: %s", err->message);
|
GST_DEBUG ("Closing socket failed: %s", err->message);
|
||||||
g_clear_error (&err);
|
g_clear_error (&err);
|
||||||
}
|
}
|
||||||
g_object_unref (client_sock);
|
g_object_unref (client_sock);
|
||||||
return GST_RTSP_ERROR;
|
return ret;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -941,16 +966,17 @@ wrong_result:
|
|||||||
connect_failed:
|
connect_failed:
|
||||||
{
|
{
|
||||||
GST_ERROR ("failed to connect: %s", error->message);
|
GST_ERROR ("failed to connect: %s", error->message);
|
||||||
res = GST_RTSP_ERROR;
|
res = gst_rtsp_result_from_g_io_error (error, GST_RTSP_ERROR);
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
remote_address_failed:
|
remote_address_failed:
|
||||||
{
|
{
|
||||||
GST_ERROR ("failed to resolve address: %s", error->message);
|
GST_ERROR ("failed to resolve address: %s", error->message);
|
||||||
|
res = gst_rtsp_result_from_g_io_error (error, GST_RTSP_ERROR);
|
||||||
g_object_unref (connection);
|
g_object_unref (connection);
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
return GST_RTSP_ERROR;
|
return res;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1050,19 +1076,21 @@ gst_rtsp_connection_connect_with_response_usec (GstRTSPConnection * conn,
|
|||||||
connect_failed:
|
connect_failed:
|
||||||
{
|
{
|
||||||
GST_ERROR ("failed to connect: %s", error->message);
|
GST_ERROR ("failed to connect: %s", error->message);
|
||||||
|
res = gst_rtsp_result_from_g_io_error (error, GST_RTSP_ERROR);
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_free (connection_uri);
|
g_free (connection_uri);
|
||||||
g_free (request_uri);
|
g_free (request_uri);
|
||||||
return GST_RTSP_ERROR;
|
return res;
|
||||||
}
|
}
|
||||||
remote_address_failed:
|
remote_address_failed:
|
||||||
{
|
{
|
||||||
GST_ERROR ("failed to connect: %s", error->message);
|
GST_ERROR ("failed to connect: %s", error->message);
|
||||||
|
res = gst_rtsp_result_from_g_io_error (error, GST_RTSP_ERROR);
|
||||||
g_object_unref (connection);
|
g_object_unref (connection);
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_free (connection_uri);
|
g_free (connection_uri);
|
||||||
g_free (request_uri);
|
g_free (request_uri);
|
||||||
return GST_RTSP_ERROR;
|
return res;
|
||||||
}
|
}
|
||||||
tunneling_failed:
|
tunneling_failed:
|
||||||
{
|
{
|
||||||
@ -1211,6 +1239,7 @@ write_bytes (GOutputStream * stream, const guint8 * buffer, guint * idx,
|
|||||||
{
|
{
|
||||||
guint left;
|
guint left;
|
||||||
gssize r;
|
gssize r;
|
||||||
|
GstRTSPResult res;
|
||||||
GError *err = NULL;
|
GError *err = NULL;
|
||||||
|
|
||||||
if (G_UNLIKELY (*idx > size))
|
if (G_UNLIKELY (*idx > size))
|
||||||
@ -1244,18 +1273,9 @@ error:
|
|||||||
else
|
else
|
||||||
GST_DEBUG ("%s", err->message);
|
GST_DEBUG ("%s", err->message);
|
||||||
|
|
||||||
if (g_error_matches (err, G_IO_ERROR, G_IO_ERROR_CANCELLED)) {
|
res = gst_rtsp_result_from_g_io_error (err, GST_RTSP_ESYS);
|
||||||
g_clear_error (&err);
|
|
||||||
return GST_RTSP_EINTR;
|
|
||||||
} else if (g_error_matches (err, G_IO_ERROR, G_IO_ERROR_WOULD_BLOCK)) {
|
|
||||||
g_clear_error (&err);
|
|
||||||
return GST_RTSP_EINTR;
|
|
||||||
} else if (g_error_matches (err, G_IO_ERROR, G_IO_ERROR_TIMED_OUT)) {
|
|
||||||
g_clear_error (&err);
|
|
||||||
return GST_RTSP_ETIMEOUT;
|
|
||||||
}
|
|
||||||
g_clear_error (&err);
|
g_clear_error (&err);
|
||||||
return GST_RTSP_ESYS;
|
return res;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1267,6 +1287,7 @@ writev_bytes (GOutputStream * stream, GOutputVector * vectors, gint n_vectors,
|
|||||||
{
|
{
|
||||||
gsize _bytes_written = 0;
|
gsize _bytes_written = 0;
|
||||||
gsize written;
|
gsize written;
|
||||||
|
GstRTSPResult ret;
|
||||||
GError *err = NULL;
|
GError *err = NULL;
|
||||||
GPollableReturn res = G_POLLABLE_RETURN_OK;
|
GPollableReturn res = G_POLLABLE_RETURN_OK;
|
||||||
|
|
||||||
@ -1318,19 +1339,14 @@ error:
|
|||||||
if (res == G_POLLABLE_RETURN_WOULD_BLOCK) {
|
if (res == G_POLLABLE_RETURN_WOULD_BLOCK) {
|
||||||
g_assert (!err);
|
g_assert (!err);
|
||||||
return GST_RTSP_EINTR;
|
return GST_RTSP_EINTR;
|
||||||
} else if (g_error_matches (err, G_IO_ERROR, G_IO_ERROR_CANCELLED)) {
|
|
||||||
g_clear_error (&err);
|
|
||||||
return GST_RTSP_EINTR;
|
|
||||||
} else if (g_error_matches (err, G_IO_ERROR, G_IO_ERROR_TIMED_OUT)) {
|
|
||||||
g_clear_error (&err);
|
|
||||||
return GST_RTSP_ETIMEOUT;
|
|
||||||
} else if (G_UNLIKELY (written == 0)) {
|
} else if (G_UNLIKELY (written == 0)) {
|
||||||
g_clear_error (&err);
|
g_clear_error (&err);
|
||||||
return GST_RTSP_EEOF;
|
return GST_RTSP_EEOF;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ret = gst_rtsp_result_from_g_io_error (err, GST_RTSP_ESYS);
|
||||||
g_clear_error (&err);
|
g_clear_error (&err);
|
||||||
return GST_RTSP_ESYS;
|
return ret;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
@ -1458,6 +1474,7 @@ read_bytes (GstRTSPConnection * conn, guint8 * buffer, guint * idx, guint size,
|
|||||||
{
|
{
|
||||||
guint left;
|
guint left;
|
||||||
gint r;
|
gint r;
|
||||||
|
GstRTSPResult res;
|
||||||
GError *err = NULL;
|
GError *err = NULL;
|
||||||
|
|
||||||
if (G_UNLIKELY (*idx > size))
|
if (G_UNLIKELY (*idx > size))
|
||||||
@ -1482,18 +1499,9 @@ error:
|
|||||||
return GST_RTSP_EEOF;
|
return GST_RTSP_EEOF;
|
||||||
|
|
||||||
GST_DEBUG ("%s", err->message);
|
GST_DEBUG ("%s", err->message);
|
||||||
if (g_error_matches (err, G_IO_ERROR, G_IO_ERROR_CANCELLED)) {
|
res = gst_rtsp_result_from_g_io_error (err, GST_RTSP_ESYS);
|
||||||
g_clear_error (&err);
|
|
||||||
return GST_RTSP_EINTR;
|
|
||||||
} else if (g_error_matches (err, G_IO_ERROR, G_IO_ERROR_WOULD_BLOCK)) {
|
|
||||||
g_clear_error (&err);
|
|
||||||
return GST_RTSP_EINTR;
|
|
||||||
} else if (g_error_matches (err, G_IO_ERROR, G_IO_ERROR_TIMED_OUT)) {
|
|
||||||
g_clear_error (&err);
|
|
||||||
return GST_RTSP_ETIMEOUT;
|
|
||||||
}
|
|
||||||
g_clear_error (&err);
|
g_clear_error (&err);
|
||||||
return GST_RTSP_ESYS;
|
return res;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user