auth: remove auth from media and factory
authorWim Taymans <wim.taymans@collabora.co.uk>
Fri, 5 Jul 2013 10:08:36 +0000 (12:08 +0200)
committerWim Taymans <wim.taymans@collabora.co.uk>
Fri, 5 Jul 2013 18:53:19 +0000 (20:53 +0200)
Remove the auth object from media and factory. We want to have the RTSPClient
authenticate and authorize resources, there is no need to place another auth
manager on the media/factory.

examples/test-auth.c
gst/rtsp-server/rtsp-auth.c
gst/rtsp-server/rtsp-auth.h
gst/rtsp-server/rtsp-client.c
gst/rtsp-server/rtsp-client.h
gst/rtsp-server/rtsp-media-factory.c
gst/rtsp-server/rtsp-media-factory.h
gst/rtsp-server/rtsp-media.c
gst/rtsp-server/rtsp-media.h

index ee8af57..f5a129c 100644 (file)
@@ -87,16 +87,6 @@ main (int argc, char *argv[])
       "audiotestsrc ! audio/x-raw,rate=8000 ! "
       "alawenc ! rtppcmapay name=pay1 pt=97 " ")");
 
-  /* make a new authentication manager */
-  auth = gst_rtsp_auth_new ();
-  basic = gst_rtsp_auth_make_basic ("user", "password");
-  gst_rtsp_auth_add_basic (auth, basic, "user");
-  g_free (basic);
-  basic = gst_rtsp_auth_make_basic ("admin", "power");
-  gst_rtsp_auth_add_basic (auth, basic, "admin");
-  g_free (basic);
-  gst_rtsp_media_factory_set_auth (factory, auth);
-  g_object_unref (auth);
   /* attach the test factory to the /test url */
   gst_rtsp_mount_points_add_factory (mounts, "/test", factory);
 
@@ -105,18 +95,26 @@ main (int argc, char *argv[])
   gst_rtsp_media_factory_set_launch (factory, "( "
       "videotestsrc ! video/x-raw,width=352,height=288,framerate=30/1 ! "
       "x264enc ! rtph264pay name=pay0 pt=96 )");
+  /* attach the test factory to the /test url */
+  gst_rtsp_mount_points_add_factory (mounts, "/test2", factory);
+
+  /* don't need the ref to the mapper anymore */
+  g_object_unref (mounts);
+
   /* make a new authentication manager */
   auth = gst_rtsp_auth_new ();
+  basic = gst_rtsp_auth_make_basic ("user", "password");
+  gst_rtsp_auth_add_basic (auth, basic, "user");
+  g_free (basic);
+  basic = gst_rtsp_auth_make_basic ("admin", "power");
+  gst_rtsp_auth_add_basic (auth, basic, "admin");
+  g_free (basic);
   basic = gst_rtsp_auth_make_basic ("admin2", "power2");
   gst_rtsp_auth_add_basic (auth, basic, "admin");
   g_free (basic);
-  gst_rtsp_media_factory_set_auth (factory, auth);
+  /* set as the server authentication manager */
+  gst_rtsp_server_set_auth (server, auth);
   g_object_unref (auth);
-  /* attach the test factory to the /test url */
-  gst_rtsp_mount_points_add_factory (mounts, "/test2", factory);
-
-  /* don't need the ref to the mapper anymore */
-  g_object_unref (mounts);
 
   /* attach the server to the default maincontext */
   if (gst_rtsp_server_attach (server, NULL) == 0)
index 6ed627f..a0df870 100644 (file)
@@ -46,10 +46,12 @@ static void gst_rtsp_auth_set_property (GObject * object, guint propid,
     const GValue * value, GParamSpec * pspec);
 static void gst_rtsp_auth_finalize (GObject * obj);
 
-static gboolean default_setup_auth (GstRTSPAuth * auth, GstRTSPClient * client,
+static gboolean default_setup (GstRTSPAuth * auth, GstRTSPClient * client,
+    GstRTSPClientState * state);
+static gboolean default_validate (GstRTSPAuth * auth,
+    GstRTSPClient * client, GstRTSPClientState * state);
+static gboolean default_check (GstRTSPAuth * auth, GstRTSPClient * client,
     GQuark hint, GstRTSPClientState * state);
-static gboolean default_check_method (GstRTSPAuth * auth,
-    GstRTSPClient * client, GQuark hint, GstRTSPClientState * state);
 
 G_DEFINE_TYPE (GstRTSPAuth, gst_rtsp_auth, G_TYPE_OBJECT);
 
@@ -66,8 +68,9 @@ gst_rtsp_auth_class_init (GstRTSPAuthClass * klass)
   gobject_class->set_property = gst_rtsp_auth_set_property;
   gobject_class->finalize = gst_rtsp_auth_finalize;
 
-  klass->setup_auth = default_setup_auth;
-  klass->check_method = default_check_method;
+  klass->setup = default_setup;
+  klass->validate = default_validate;
+  klass->check = default_check;
 
   GST_DEBUG_CATEGORY_INIT (rtsp_auth_debug, "rtspauth", 0, "GstRTSPAuth");
 }
@@ -192,8 +195,8 @@ gst_rtsp_auth_remove_basic (GstRTSPAuth * auth, const gchar * basic)
 }
 
 static gboolean
-default_setup_auth (GstRTSPAuth * auth, GstRTSPClient * client,
-    GQuark hint, GstRTSPClientState * state)
+default_setup (GstRTSPAuth * auth, GstRTSPClient * client,
+    GstRTSPClientState * state)
 {
   if (state->response == NULL)
     return FALSE;
@@ -206,10 +209,9 @@ default_setup_auth (GstRTSPAuth * auth, GstRTSPClient * client,
 }
 
 /**
- * gst_rtsp_auth_setup_auth:
+ * gst_rtsp_auth_setup:
  * @auth: a #GstRTSPAuth
  * @client: the client
- * @hint: TODO
  * @state: TODO
  *
  * Add authentication tokens to @response.
@@ -217,8 +219,8 @@ default_setup_auth (GstRTSPAuth * auth, GstRTSPClient * client,
  * Returns: FALSE if something is wrong.
  */
 gboolean
-gst_rtsp_auth_setup_auth (GstRTSPAuth * auth, GstRTSPClient * client,
-    GQuark hint, GstRTSPClientState * state)
+gst_rtsp_auth_setup (GstRTSPAuth * auth, GstRTSPClient * client,
+    GstRTSPClientState * state)
 {
   gboolean result = FALSE;
   GstRTSPAuthClass *klass;
@@ -231,53 +233,83 @@ gst_rtsp_auth_setup_auth (GstRTSPAuth * auth, GstRTSPClient * client,
 
   GST_DEBUG_OBJECT (auth, "setup auth");
 
-  if (klass->setup_auth)
-    result = klass->setup_auth (auth, client, hint, state);
+  if (klass->setup)
+    result = klass->setup (auth, client, state);
 
   return result;
 }
 
 static gboolean
-default_check_method (GstRTSPAuth * auth, GstRTSPClient * client,
-    GQuark hint, GstRTSPClientState * state)
+default_validate (GstRTSPAuth * auth, GstRTSPClient * client,
+    GstRTSPClientState * state)
 {
   GstRTSPAuthPrivate *priv = auth->priv;
-  gboolean result = TRUE;
   GstRTSPResult res;
+  gchar *authorization;
 
-  if ((state->method & priv->methods) != 0) {
-    gchar *authorization;
+  GST_DEBUG_OBJECT (auth, "validate");
 
-    result = FALSE;
+  res =
+      gst_rtsp_message_get_header (state->request, GST_RTSP_HDR_AUTHORIZATION,
+      &authorization, 0);
+  if (res < 0)
+    goto no_auth;
 
-    res =
-        gst_rtsp_message_get_header (state->request, GST_RTSP_HDR_AUTHORIZATION,
-        &authorization, 0);
-    if (res < 0)
-      goto no_auth;
+  /* parse type */
+  if (g_ascii_strncasecmp (authorization, "basic ", 6) == 0) {
+    gchar *authgroup;
+
+    GST_DEBUG_OBJECT (auth, "check Basic auth");
+    g_mutex_lock (&priv->lock);
+    if ((authgroup = g_hash_table_lookup (priv->basic, &authorization[6]))) {
+      GST_DEBUG_OBJECT (auth, "setting authgroup %s", authgroup);
+      state->authgroup = authgroup;
+    }
+    g_mutex_unlock (&priv->lock);
+  } else if (g_ascii_strncasecmp (authorization, "digest ", 7) == 0) {
+    GST_DEBUG_OBJECT (auth, "check Digest auth");
+    /* not implemented yet */
+  }
+  return TRUE;
 
-    /* parse type */
-    if (g_ascii_strncasecmp (authorization, "basic ", 6) == 0) {
-      gchar *authgroup;
+no_auth:
+  {
+    GST_DEBUG_OBJECT (auth, "no authorization header found");
+    return TRUE;
+  }
+}
 
-      GST_DEBUG_OBJECT (auth, "check Basic auth");
-      g_mutex_lock (&priv->lock);
-      if ((authgroup = g_hash_table_lookup (priv->basic, &authorization[6]))) {
-        result = TRUE;
-        state->authgroup = authgroup;
+static gboolean
+default_check (GstRTSPAuth * auth, GstRTSPClient * client,
+    GQuark hint, GstRTSPClientState * state)
+{
+  GstRTSPAuthPrivate *priv = auth->priv;
+  GstRTSPAuthClass *klass;
+
+  klass = GST_RTSP_AUTH_GET_CLASS (auth);
+
+  if ((state->method & priv->methods) != 0) {
+    /* we need an authgroup to check */
+    if (state->authgroup == NULL) {
+      if (klass->validate) {
+        if (!klass->validate (auth, client, state))
+          goto validate_failed;
       }
-      g_mutex_unlock (&priv->lock);
-    } else if (g_ascii_strncasecmp (authorization, "digest ", 7) == 0) {
-      GST_DEBUG_OBJECT (auth, "check Digest auth");
-      /* not implemented yet */
-      result = FALSE;
     }
+
+    if (state->authgroup == NULL)
+      goto no_auth;
   }
-  return result;
+  return TRUE;
 
+validate_failed:
+  {
+    GST_DEBUG_OBJECT (auth, "validation failed");
+    return FALSE;
+  }
 no_auth:
   {
-    GST_DEBUG_OBJECT (auth, "no authorization header found");
+    GST_DEBUG_OBJECT (auth, "no authorization group found");
     return FALSE;
   }
 }
@@ -289,9 +321,10 @@ no_auth:
  * @hint: a hint
  * @state: client state
  *
- * Check if @client is allowed to perform the actions of @state.
+ * Check if @client with state is authorized to perform @hint in the
+ * current @state.
  *
- * Returns: FALSE if the action is not allowed.
+ * Returns: FALSE if check failed.
  */
 gboolean
 gst_rtsp_auth_check (GstRTSPAuth * auth, GstRTSPClient * client,
@@ -306,10 +339,10 @@ gst_rtsp_auth_check (GstRTSPAuth * auth, GstRTSPClient * client,
 
   klass = GST_RTSP_AUTH_GET_CLASS (auth);
 
-  GST_DEBUG_OBJECT (auth, "check state");
+  GST_DEBUG_OBJECT (auth, "check auth");
 
-  if (klass->check_method)
-    result = klass->check_method (auth, client, hint, state);
+  if (klass->check)
+    result = klass->check (auth, client, hint, state);
 
   return result;
 }
index 425413b..fd9b679 100644 (file)
@@ -53,10 +53,12 @@ struct _GstRTSPAuth {
 struct _GstRTSPAuthClass {
   GObjectClass  parent_class;
 
-  gboolean (*setup_auth)   (GstRTSPAuth *auth, GstRTSPClient * client,
-                            GQuark hint, GstRTSPClientState *state);
-  gboolean (*check_method) (GstRTSPAuth *auth, GstRTSPClient * client,
-                            GQuark hint, GstRTSPClientState *state);
+  gboolean (*setup)         (GstRTSPAuth *auth, GstRTSPClient * client,
+                             GstRTSPClientState *state);
+  gboolean (*validate)      (GstRTSPAuth *auth, GstRTSPClient * client,
+                             GstRTSPClientState *state);
+  gboolean (*check)         (GstRTSPAuth *auth, GstRTSPClient * client,
+                             GQuark hint, GstRTSPClientState *state);
 };
 
 GType               gst_rtsp_auth_get_type          (void);
@@ -67,10 +69,12 @@ void                gst_rtsp_auth_add_basic         (GstRTSPAuth *auth, const gc
                                                      const gchar *authgroup);
 void                gst_rtsp_auth_remove_basic      (GstRTSPAuth *auth, const gchar * basic);
 
-gboolean            gst_rtsp_auth_setup_auth        (GstRTSPAuth *auth, GstRTSPClient * client,
-                                                     GQuark hint, GstRTSPClientState *state);
+gboolean            gst_rtsp_auth_setup             (GstRTSPAuth *auth, GstRTSPClient * client,
+                                                     GstRTSPClientState *state);
+
 gboolean            gst_rtsp_auth_check             (GstRTSPAuth *auth, GstRTSPClient * client,
                                                      GQuark hint, GstRTSPClientState *state);
+
 /* helpers */
 gchar *             gst_rtsp_auth_make_basic        (const gchar * user, const gchar * pass);
 
index db82174..a597916 100644 (file)
@@ -456,7 +456,7 @@ handle_unauthorized_request (GstRTSPClient * client, GstRTSPAuth * auth,
 
   if (auth) {
     /* and let the authentication manager setup the auth tokens */
-    gst_rtsp_auth_setup_auth (auth, client, 0, state);
+    gst_rtsp_auth_setup (auth, client, state);
   }
 
   send_message (client, state->session, state->response, FALSE);
@@ -487,7 +487,6 @@ find_media (GstRTSPClient * client, GstRTSPClientState * state, gint * matched)
   GstRTSPClientPrivate *priv = client->priv;
   GstRTSPMediaFactory *factory;
   GstRTSPMedia *media;
-  GstRTSPAuth *auth;
   gchar *path;
   gint path_len;
 
@@ -518,17 +517,6 @@ find_media (GstRTSPClient * client, GstRTSPClientState * state, gint * matched)
     }
     priv->media = NULL;
 
-    /* check if we have access to the factory */
-    if ((auth = gst_rtsp_media_factory_get_auth (factory))) {
-      state->factory = factory;
-
-      if (!gst_rtsp_auth_check (auth, client, 0, state))
-        goto not_allowed;
-
-      state->factory = NULL;
-      g_object_unref (auth);
-    }
-
     /* prepare the media and add it to the pipeline */
     if (!(media = gst_rtsp_media_factory_construct (factory, state->uri)))
       goto no_media;
@@ -568,15 +556,6 @@ no_factory:
     send_generic_response (client, GST_RTSP_STS_NOT_FOUND, state);
     return NULL;
   }
-not_allowed:
-  {
-    GST_ERROR ("client %p: unauthorized request", client);
-    handle_unauthorized_request (client, auth, state);
-    g_object_unref (factory);
-    state->factory = NULL;
-    g_object_unref (auth);
-    return NULL;
-  }
 no_media:
   {
     GST_ERROR ("client %p: can't create media", client);
@@ -1847,6 +1826,8 @@ handle_request (GstRTSPClient * client, GstRTSPMessage * request)
   if (priv->auth) {
     if (!gst_rtsp_auth_check (priv->auth, client, 0, &state))
       goto not_authorized;
+
+    state.auth = priv->auth;
   }
 
   /* now see what is asked and dispatch to a dedicated handler */
index b5adc10..86ae980 100644 (file)
@@ -65,6 +65,7 @@ struct _GstRTSPClientState {
   GstRTSPMessage      *request;
   GstRTSPUrl          *uri;
   GstRTSPMethod        method;
+  GstRTSPAuth         *auth;
   const gchar         *authgroup;
   GstRTSPSession      *session;
   GstRTSPSessionMedia *sessmedia;
index f448276..b6fa8c0 100644 (file)
@@ -33,7 +33,6 @@ struct _GstRTSPMediaFactoryPrivate
   gboolean shared;
   gboolean eos_shutdown;
   GstRTSPLowerTrans protocols;
-  GstRTSPAuth *auth;
   guint buffer_size;
   GstRTSPAddressPool *pool;
 
@@ -194,8 +193,6 @@ gst_rtsp_media_factory_finalize (GObject * obj)
   g_mutex_clear (&priv->medias_lock);
   g_free (priv->launch);
   g_mutex_clear (&priv->lock);
-  if (priv->auth)
-    g_object_unref (priv->auth);
   if (priv->pool)
     g_object_unref (priv->pool);
 
@@ -536,62 +533,6 @@ gst_rtsp_media_factory_get_address_pool (GstRTSPMediaFactory * factory)
 }
 
 /**
- * gst_rtsp_media_factory_set_auth:
- * @factory: a #GstRTSPMediaFactory
- * @auth: a #GstRTSPAuth
- *
- * configure @auth to be used as the authentication manager of @factory.
- */
-void
-gst_rtsp_media_factory_set_auth (GstRTSPMediaFactory * factory,
-    GstRTSPAuth * auth)
-{
-  GstRTSPMediaFactoryPrivate *priv;
-  GstRTSPAuth *old;
-
-  g_return_if_fail (GST_IS_RTSP_MEDIA_FACTORY (factory));
-
-  priv = factory->priv;
-
-  GST_RTSP_MEDIA_FACTORY_LOCK (factory);
-  if ((old = priv->auth) != auth)
-    priv->auth = auth ? g_object_ref (auth) : NULL;
-  else
-    old = NULL;
-  GST_RTSP_MEDIA_FACTORY_UNLOCK (factory);
-
-  if (old)
-    g_object_unref (old);
-}
-
-/**
- * gst_rtsp_media_factory_get_auth:
- * @factory: a #GstRTSPMediaFactory
- *
- * Get the #GstRTSPAuth used as the authentication manager of @factory.
- *
- * Returns: (transfer full): the #GstRTSPAuth of @factory. g_object_unref() after
- * usage.
- */
-GstRTSPAuth *
-gst_rtsp_media_factory_get_auth (GstRTSPMediaFactory * factory)
-{
-  GstRTSPMediaFactoryPrivate *priv;
-  GstRTSPAuth *result;
-
-  g_return_val_if_fail (GST_IS_RTSP_MEDIA_FACTORY (factory), NULL);
-
-  priv = factory->priv;
-
-  GST_RTSP_MEDIA_FACTORY_LOCK (factory);
-  if ((result = priv->auth))
-    g_object_ref (result);
-  GST_RTSP_MEDIA_FACTORY_UNLOCK (factory);
-
-  return result;
-}
-
-/**
  * gst_rtsp_media_factory_set_protocols:
  * @factory: a #GstRTSPMediaFactory
  * @protocols: the new flags
@@ -896,7 +837,6 @@ default_configure (GstRTSPMediaFactory * factory, GstRTSPMedia * media)
   GstRTSPMediaFactoryPrivate *priv = factory->priv;
   gboolean shared, eos_shutdown;
   guint size;
-  GstRTSPAuth *auth;
   GstRTSPLowerTrans protocols;
   GstRTSPAddressPool *pool;
 
@@ -913,10 +853,6 @@ default_configure (GstRTSPMediaFactory * factory, GstRTSPMedia * media)
   gst_rtsp_media_set_buffer_size (media, size);
   gst_rtsp_media_set_protocols (media, protocols);
 
-  if ((auth = gst_rtsp_media_factory_get_auth (factory))) {
-    gst_rtsp_media_set_auth (media, auth);
-    g_object_unref (auth);
-  }
   if ((pool = gst_rtsp_media_factory_get_address_pool (factory))) {
     gst_rtsp_media_set_address_pool (media, pool);
     g_object_unref (pool);
index d974fa0..a492422 100644 (file)
@@ -114,9 +114,6 @@ gboolean              gst_rtsp_media_factory_is_eos_shutdown    (GstRTSPMediaFac
 void                  gst_rtsp_media_factory_set_protocols  (GstRTSPMediaFactory *factory, GstRTSPLowerTrans protocols);
 GstRTSPLowerTrans     gst_rtsp_media_factory_get_protocols  (GstRTSPMediaFactory *factory);
 
-void                  gst_rtsp_media_factory_set_auth     (GstRTSPMediaFactory *factory, GstRTSPAuth *auth);
-GstRTSPAuth *         gst_rtsp_media_factory_get_auth     (GstRTSPMediaFactory *factory);
-
 void                  gst_rtsp_media_factory_set_address_pool   (GstRTSPMediaFactory * factory,
                                                                  GstRTSPAddressPool * pool);
 GstRTSPAddressPool *  gst_rtsp_media_factory_get_address_pool   (GstRTSPMediaFactory * factory);
index d20087d..4e25e15 100644 (file)
@@ -40,7 +40,6 @@ struct _GstRTSPMediaPrivate
   gboolean reused;
   gboolean eos_shutdown;
   guint buffer_size;
-  GstRTSPAuth *auth;
   GstRTSPAddressPool *pool;
 
   GstElement *element;
@@ -262,8 +261,6 @@ gst_rtsp_media_finalize (GObject * obj)
   if (priv->nettime)
     gst_object_unref (priv->nettime);
   gst_object_unref (priv->element);
-  if (priv->auth)
-    g_object_unref (priv->auth);
   if (priv->pool)
     g_object_unref (priv->pool);
   g_mutex_clear (&priv->lock);
@@ -785,63 +782,6 @@ gst_rtsp_media_is_time_provider (GstRTSPMedia * media)
 }
 
 /**
- * gst_rtsp_media_set_auth:
- * @media: a #GstRTSPMedia
- * @auth: a #GstRTSPAuth
- *
- * configure @auth to be used as the authentication manager of @media.
- */
-void
-gst_rtsp_media_set_auth (GstRTSPMedia * media, GstRTSPAuth * auth)
-{
-  GstRTSPMediaPrivate *priv;
-  GstRTSPAuth *old;
-
-  g_return_if_fail (GST_IS_RTSP_MEDIA (media));
-
-  priv = media->priv;
-
-  GST_LOG_OBJECT (media, "set auth %p", auth);
-
-  g_mutex_lock (&priv->lock);
-  if ((old = priv->auth) != auth)
-    priv->auth = auth ? g_object_ref (auth) : NULL;
-  else
-    old = NULL;
-  g_mutex_unlock (&priv->lock);
-
-  if (old)
-    g_object_unref (old);
-}
-
-/**
- * gst_rtsp_media_get_auth:
- * @media: a #GstRTSPMedia
- *
- * Get the #GstRTSPAuth used as the authentication manager of @media.
- *
- * Returns: (transfer full): the #GstRTSPAuth of @media. g_object_unref() after
- * usage.
- */
-GstRTSPAuth *
-gst_rtsp_media_get_auth (GstRTSPMedia * media)
-{
-  GstRTSPMediaPrivate *priv;
-  GstRTSPAuth *result;
-
-  g_return_val_if_fail (GST_IS_RTSP_MEDIA (media), NULL);
-
-  priv = media->priv;
-
-  g_mutex_lock (&priv->lock);
-  if ((result = priv->auth))
-    g_object_ref (result);
-  g_mutex_unlock (&priv->lock);
-
-  return result;
-}
-
-/**
  * gst_rtsp_media_set_address_pool:
  * @media: a #GstRTSPMedia
  * @pool: a #GstRTSPAddressPool
index d6d2153..02be092 100644 (file)
@@ -137,9 +137,6 @@ GstRTSPLowerTrans     gst_rtsp_media_get_protocols    (GstRTSPMedia *media);
 void                  gst_rtsp_media_set_eos_shutdown (GstRTSPMedia *media, gboolean eos_shutdown);
 gboolean              gst_rtsp_media_is_eos_shutdown  (GstRTSPMedia *media);
 
-void                  gst_rtsp_media_set_auth         (GstRTSPMedia *media, GstRTSPAuth *auth);
-GstRTSPAuth *         gst_rtsp_media_get_auth         (GstRTSPMedia *media);
-
 void                  gst_rtsp_media_set_address_pool (GstRTSPMedia *media, GstRTSPAddressPool *pool);
 GstRTSPAddressPool *  gst_rtsp_media_get_address_pool (GstRTSPMedia *media);