From eefe6aacb992a9360f822ae45ba0e361a4522d64 Mon Sep 17 00:00:00 2001 From: Wim Taymans Date: Mon, 18 Jul 2016 17:40:58 +0200 Subject: [PATCH] some more rework --- pinos/Makefile.am | 12 +- pinos/client/client-node.c | 408 ------------- pinos/client/client-node.h | 74 --- pinos/client/context.c | 175 ------ pinos/client/context.h | 12 - pinos/client/stream.c | 136 +---- pinos/dbus/org.pinos.xml | 139 +++-- pinos/gst/gstpinosportsink.h | 1 + pinos/gst/gstpinosportsrc.h | 1 + pinos/modules/gst/gst-manager.c | 8 +- pinos/modules/gst/gst-sink.c | 32 +- pinos/modules/gst/gst-sink.h | 8 +- pinos/modules/gst/gst-source.c | 38 +- pinos/modules/gst/gst-source.h | 8 +- pinos/server/daemon.c | 59 +- pinos/server/daemon.h | 8 +- pinos/{client => server}/node.c | 394 ++++++++++-- pinos/{client => server}/node.h | 61 +- pinos/{client => server}/port.c | 1019 +++++++++---------------------- pinos/{client => server}/port.h | 18 +- pinos/server/server-node.c | 627 ------------------- pinos/server/server-node.h | 91 --- pinos/server/server-port.c | 278 --------- pinos/server/server-port.h | 71 --- 24 files changed, 849 insertions(+), 2829 deletions(-) delete mode 100644 pinos/client/client-node.c delete mode 100644 pinos/client/client-node.h rename pinos/{client => server}/node.c (57%) rename pinos/{client => server}/node.h (68%) rename pinos/{client => server}/port.c (66%) rename pinos/{client => server}/port.h (84%) delete mode 100644 pinos/server/server-node.c delete mode 100644 pinos/server/server-node.h delete mode 100644 pinos/server/server-port.c delete mode 100644 pinos/server/server-port.h diff --git a/pinos/Makefile.am b/pinos/Makefile.am index e6c43069a..4f9793e66 100644 --- a/pinos/Makefile.am +++ b/pinos/Makefile.am @@ -171,10 +171,6 @@ pinosinclude_HEADERS = \ client/introspect.h \ client/mainloop.h \ client/properties.h \ - client/node.h \ - client/port.h \ - client/client-node.h \ - client/client-port.h \ client/stream.h \ client/subscribe.h @@ -189,10 +185,6 @@ libpinos_@PINOS_MAJORMINOR@_la_SOURCES = \ client/introspect.h client/introspect.c \ client/mainloop.h client/mainloop.c \ client/properties.h client/properties.c \ - client/node.h client/node.c \ - client/port.h client/port.c \ - client/client-node.h client/client-node.c \ - client/client-port.h client/client-port.c \ client/stream.h client/stream.c \ client/pinos.c client/pinos.h \ client/fdmanager.c client/fdmanager.h \ @@ -213,8 +205,8 @@ lib_LTLIBRARIES += libpinoscore-@PINOS_MAJORMINOR@.la # Pure core stuff libpinoscore_@PINOS_MAJORMINOR@_la_SOURCES = \ server/daemon.c server/daemon.h \ - server/server-node.c server/server-node.h \ - server/server-port.c server/server-port.h \ + server/node.c server/node.h \ + server/port.c server/port.h \ server/node-factory.c server/node-factory.h \ modules/gst/gst-manager.c modules/gst/gst-manager.h \ modules/gst/gst-source.c modules/gst/gst-source.h \ diff --git a/pinos/client/client-node.c b/pinos/client/client-node.c deleted file mode 100644 index e2227224a..000000000 --- a/pinos/client/client-node.c +++ /dev/null @@ -1,408 +0,0 @@ -/* Pinos - * Copyright (C) 2015 Wim Taymans - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, - * Boston, MA 02110-1301, USA. - */ - -#include -#include - -#include "pinos/client/pinos.h" -#include "pinos/client/subscribe.h" -#include "pinos/client/enumtypes.h" - -#include "pinos/client/context.h" -#include "pinos/client/private.h" -#include "pinos/client/client-node.h" -#include "pinos/client/client-port.h" - -#define PINOS_CLIENT_NODE_GET_PRIVATE(node) \ - (G_TYPE_INSTANCE_GET_PRIVATE ((node), PINOS_TYPE_CLIENT_NODE, PinosClientNodePrivate)) - -struct _PinosClientNodePrivate -{ - PinosContext *context; - GDBusProxy *proxy; -}; - -G_DEFINE_TYPE (PinosClientNode, pinos_client_node, PINOS_TYPE_NODE); - -enum -{ - PROP_0, - PROP_CONTEXT, - PROP_PROXY, -}; - -static gboolean -client_node_set_state (PinosNode *node, - PinosNodeState state) -{ - return FALSE; -} - -typedef struct { - PinosDirection direction; - gchar *name; - PinosProperties *properties; - GBytes *possible_formats; - GSocket *socket; -} CreatePortData; - -static void -create_port_data_free (CreatePortData *data) -{ - g_free (data->name); - if (data->properties) - pinos_properties_free (data->properties); - g_clear_object (&data->socket); - g_slice_free (CreatePortData, data); -} - -static void -on_port_proxy (GObject *source_object, - GAsyncResult *res, - gpointer user_data) -{ - GTask *task = user_data; - CreatePortData *data = g_task_get_task_data (task); - PinosClientNode *node = g_task_get_source_object (task); - PinosClientNodePrivate *priv = node->priv; - PinosContext *context = priv->context; - GError *error = NULL; - GDBusProxy *proxy; - PinosClientPort *port; - - proxy = pinos_subscribe_get_proxy_finish (context->priv->subscribe, - res, - &error); - if (proxy == NULL) - goto port_failed; - - port = pinos_client_port_new (node, - proxy, - data->socket); - g_task_return_pointer (task, port, (GDestroyNotify) g_object_unref); - g_object_unref (task); - - return; - -port_failed: - { - g_warning ("failed to get port proxy: %s", error->message); - g_task_return_error (task, error); - g_object_unref (task); - return; - } -} - -static void -on_port_created (GObject *source_object, - GAsyncResult *res, - gpointer user_data) -{ - GTask *task = user_data; - PinosClientNode *node = g_task_get_source_object (task); - CreatePortData *data = g_task_get_task_data (task); - PinosClientNodePrivate *priv = node->priv; - PinosContext *context = priv->context; - GVariant *ret; - GError *error = NULL; - const gchar *port_path; - GUnixFDList *fdlist; - gint fd, fd_idx; - - g_assert (priv->proxy == G_DBUS_PROXY (source_object)); - - ret = g_dbus_proxy_call_with_unix_fd_list_finish (priv->proxy, &fdlist, res, &error); - if (ret == NULL) - goto create_failed; - - g_variant_get (ret, "(&oh)", &port_path, &fd_idx); - - fd = g_unix_fd_list_get (fdlist, fd_idx, &error); - g_object_unref (fdlist); - if (fd == -1) - goto create_failed; - - data->socket = g_socket_new_from_fd (fd, &error); - if (data->socket == NULL) - goto create_failed; - - pinos_subscribe_get_proxy (context->priv->subscribe, - PINOS_DBUS_SERVICE, - port_path, - "org.pinos.Port1", - NULL, - on_port_proxy, - task); - g_variant_unref (ret); - - return; - - /* ERRORS */ -create_failed: - { - g_warning ("failed to create port: %s", error->message); - g_task_return_error (task, error); - g_object_unref (task); - if (ret) - g_variant_unref (ret); - return; - } -} - - -static gboolean -do_create_port (GTask *task) -{ - PinosClientNode *node = g_task_get_source_object (task); - PinosClientNodePrivate *priv = node->priv; - CreatePortData *data = g_task_get_task_data (task); - - g_dbus_proxy_call (priv->proxy, - "CreatePort", - g_variant_new ("(us@a{sv}s)", - data->direction, - data->name, - pinos_properties_to_variant (data->properties), - g_bytes_get_data (data->possible_formats, NULL)), - G_DBUS_CALL_FLAGS_NONE, - -1, - NULL, /* GCancellable *cancellable */ - on_port_created, - task); - return FALSE; -} - - -static void -client_node_create_port (PinosNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *properties, - GTask *task) -{ - PinosClientNodePrivate *priv = PINOS_CLIENT_NODE (node)->priv; - PinosContext *context = priv->context; - CreatePortData *data; - - data = g_slice_new (CreatePortData); - data->direction = direction; - data->name = g_strdup (name); - data->possible_formats = possible_formats ? g_bytes_ref (possible_formats) : NULL; - data->properties = pinos_properties_merge (pinos_node_get_properties (node), properties); - data->socket = NULL; - - g_task_set_task_data (task, data, (GDestroyNotify) create_port_data_free); - - g_main_context_invoke (context->priv->context, - (GSourceFunc) do_create_port, - task); - -} - -static void -client_node_remove_port (PinosNode *node, - PinosPort *port) -{ -} - -static void -pinos_client_node_get_property (GObject *_object, - guint prop_id, - GValue *value, - GParamSpec *pspec) -{ - PinosClientNode *node = PINOS_CLIENT_NODE (_object); - PinosClientNodePrivate *priv = node->priv; - - switch (prop_id) { - case PROP_CONTEXT: - g_value_set_object (value, priv->context); - break; - - case PROP_PROXY: - g_value_set_object (value, priv->proxy); - break; - - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (node, prop_id, pspec); - break; - } -} - -static void -pinos_client_node_set_property (GObject *_object, - guint prop_id, - const GValue *value, - GParamSpec *pspec) -{ - PinosClientNode *node = PINOS_CLIENT_NODE (_object); - PinosClientNodePrivate *priv = node->priv; - - switch (prop_id) { - case PROP_CONTEXT: - priv->context = g_value_dup_object (value); - break; - - case PROP_PROXY: - priv->proxy = g_value_dup_object (value); - break; - - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (node, prop_id, pspec); - break; - } -} - -static void -pinos_client_node_constructed (GObject * obj) -{ - PinosClientNode *node = PINOS_CLIENT_NODE (obj); - - g_debug ("client-node %p: constructed", node); - - G_OBJECT_CLASS (pinos_client_node_parent_class)->constructed (obj); -} - -static void -pinos_client_node_dispose (GObject * obj) -{ - PinosClientNode *node = PINOS_CLIENT_NODE (obj); - - g_debug ("client-node %p: dispose", node); - - G_OBJECT_CLASS (pinos_client_node_parent_class)->dispose (obj); -} - -static void -pinos_client_node_finalize (GObject * obj) -{ - PinosClientNode *node = PINOS_CLIENT_NODE (obj); - PinosClientNodePrivate *priv = node->priv; - - g_debug ("client-node %p: finalize", node); - g_clear_object (&priv->context); - g_clear_object (&priv->proxy); - - G_OBJECT_CLASS (pinos_client_node_parent_class)->finalize (obj); -} - -static void -pinos_client_node_class_init (PinosClientNodeClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - PinosNodeClass *node_class = PINOS_NODE_CLASS (klass); - - g_type_class_add_private (klass, sizeof (PinosClientNodePrivate)); - - gobject_class->constructed = pinos_client_node_constructed; - gobject_class->dispose = pinos_client_node_dispose; - gobject_class->finalize = pinos_client_node_finalize; - gobject_class->set_property = pinos_client_node_set_property; - gobject_class->get_property = pinos_client_node_get_property; - - g_object_class_install_property (gobject_class, - PROP_CONTEXT, - g_param_spec_object ("context", - "Context", - "The Context", - PINOS_TYPE_CONTEXT, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - g_object_class_install_property (gobject_class, - PROP_PROXY, - g_param_spec_object ("proxy", - "Proxy", - "The Proxy", - G_TYPE_DBUS_PROXY, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - node_class->set_state = client_node_set_state; - node_class->create_port = client_node_create_port; - node_class->remove_port = client_node_remove_port; -} - -static void -pinos_client_node_init (PinosClientNode * node) -{ - node->priv = PINOS_CLIENT_NODE_GET_PRIVATE (node); - - g_debug ("client-node %p: new", node); -} - -/** - * pinos_client_node_get_context: - * @node: a #PinosClientNode - * - * Get the context of @node. - * - * Returns: the context of @node. - */ -PinosContext * -pinos_client_node_get_context (PinosClientNode *node) -{ - PinosClientNodePrivate *priv; - - g_return_val_if_fail (PINOS_IS_CLIENT_NODE (node), NULL); - priv = node->priv; - - return priv->context; -} - -/** - * pinos_client_port_new: - * @node: a #PinosClientNode - * @id: an id - * @socket: a socket with the server port - * - * Create a new client port. - * - * Returns: a new client port - */ -PinosClientNode * -pinos_client_node_new (PinosContext *context, - gpointer id) -{ - PinosClientNode *node; - GDBusProxy *proxy = id; - GVariant *variant; - PinosProperties *properties = NULL; - const gchar *name = NULL; - - variant = g_dbus_proxy_get_cached_property (G_DBUS_PROXY (proxy), "Name"); - if (variant != NULL) { - name = g_variant_get_string (variant, NULL); - g_variant_unref (variant); - } - variant = g_dbus_proxy_get_cached_property (G_DBUS_PROXY (proxy), "Properties"); - if (variant != NULL) { - properties = pinos_properties_from_variant (variant); - g_variant_unref (variant); - } - - node = g_object_new (PINOS_TYPE_CLIENT_NODE, - "context", context, - "proxy", proxy, - "name", name, - "properties", properties, - NULL); - return node; -} diff --git a/pinos/client/client-node.h b/pinos/client/client-node.h deleted file mode 100644 index 5ef7de986..000000000 --- a/pinos/client/client-node.h +++ /dev/null @@ -1,74 +0,0 @@ -/* Pinos - * Copyright (C) 2015 Wim Taymans - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, - * Boston, MA 02110-1301, USA. - */ - -#ifndef __PINOS_CLIENT_NODE_H__ -#define __PINOS_CLIENT_NODE_H__ - -#include - -G_BEGIN_DECLS - -typedef struct _PinosClientNode PinosClientNode; -typedef struct _PinosClientNodeClass PinosClientNodeClass; -typedef struct _PinosClientNodePrivate PinosClientNodePrivate; - -#include -#include - -#define PINOS_TYPE_CLIENT_NODE (pinos_client_node_get_type ()) -#define PINOS_IS_CLIENT_NODE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), PINOS_TYPE_CLIENT_NODE)) -#define PINOS_IS_CLIENT_NODE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), PINOS_TYPE_CLIENT_NODE)) -#define PINOS_CLIENT_NODE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), PINOS_TYPE_CLIENT_NODE, PinosClientNodeClass)) -#define PINOS_CLIENT_NODE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), PINOS_TYPE_CLIENT_NODE, PinosClientNode)) -#define PINOS_CLIENT_NODE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), PINOS_TYPE_CLIENT_NODE, PinosClientNodeClass)) -#define PINOS_CLIENT_NODE_CAST(obj) ((PinosClientNode*)(obj)) -#define PINOS_CLIENT_NODE_CLASS_CAST(klass) ((PinosClientNodeClass*)(klass)) - -/** - * PinosClientNode: - * - * Pinos client node class. - */ -struct _PinosClientNode { - PinosNodeClass object; - - PinosClientNodePrivate *priv; -}; - -/** - * PinosClientNodeClass: - * @set_state: called to change the current state of the client node - * - * Pinos client node class. - */ -struct _PinosClientNodeClass { - PinosNodeClass parent_class; -}; - -/* normal GObject stuff */ -GType pinos_client_node_get_type (void); - -PinosClientNode * pinos_client_node_new (PinosContext *context, - gpointer id); - -PinosContext * pinos_client_node_get_context (PinosClientNode *node); - -G_END_DECLS - -#endif /* __PINOS_CLIENT_NODE_H__ */ diff --git a/pinos/client/context.c b/pinos/client/context.c index ef55454e3..f1a0b9abf 100644 --- a/pinos/client/context.c +++ b/pinos/client/context.c @@ -22,7 +22,6 @@ #include "pinos/client/context.h" #include "pinos/client/enumtypes.h" #include "pinos/client/subscribe.h" -#include "pinos/client/client-node.h" #include "pinos/client/private.h" @@ -619,177 +618,3 @@ pinos_context_get_error (PinosContext *context) return priv->error; } - -typedef struct { - gchar *factory_name; - gchar *name; - PinosProperties *properties; -} CreateNodeData; - -static void -create_node_data_free (CreateNodeData *data) -{ - g_free (data->factory_name); - g_free (data->name); - if (data->properties) - pinos_properties_free (data->properties); - g_slice_free (CreateNodeData, data); -} - -static void -on_node_proxy (GObject *source_object, - GAsyncResult *res, - gpointer user_data) -{ - GTask *task = user_data; - PinosContext *context = g_task_get_source_object (task); - GError *error = NULL; - GDBusProxy *proxy; - PinosClientNode *node; - - proxy = pinos_subscribe_get_proxy_finish (context->priv->subscribe, - res, - &error); - if (proxy == NULL) - goto node_failed; - - node = pinos_client_node_new (context, proxy); - - g_task_return_pointer (task, node, (GDestroyNotify) g_object_unref); - g_object_unref (task); - - return; - -node_failed: - { - g_warning ("failed to get node proxy: %s", error->message); - g_task_return_error (task, error); - g_object_unref (task); - return; - } -} - -static void -on_node_created (GObject *source_object, - GAsyncResult *res, - gpointer user_data) -{ - GTask *task = user_data; - PinosContext *context = g_task_get_source_object (task); - GVariant *ret; - GError *error = NULL; - const gchar *node_path; - - g_assert (context->priv->daemon == G_DBUS_PROXY (source_object)); - - ret = g_dbus_proxy_call_finish (context->priv->daemon, res, &error); - if (ret == NULL) - goto create_failed; - - g_variant_get (ret, "(&o)", &node_path); - - pinos_subscribe_get_proxy (context->priv->subscribe, - PINOS_DBUS_SERVICE, - node_path, - "org.pinos.Node1", - NULL, - on_node_proxy, - task); - g_variant_unref (ret); - - return; - - /* ERRORS */ -create_failed: - { - g_warning ("failed to create node: %s", error->message); - g_task_return_error (task, error); - g_object_unref (task); - return; - } -} - - -static gboolean -do_create_node (GTask *task) -{ - PinosContext *context = g_task_get_source_object (task); - CreateNodeData *data = g_task_get_task_data (task); - - g_dbus_proxy_call (context->priv->daemon, - "CreateNode", - g_variant_new ("(ss@a{sv})", - data->factory_name, - data->name, - pinos_properties_to_variant (data->properties)), - G_DBUS_CALL_FLAGS_NONE, - -1, - NULL, /* GCancellable *cancellable */ - on_node_created, - task); - return FALSE; -} - -/** - * pinos_context_create_node: - * @context: a #PinosContext - * @name: the name of the Node - * @properties: properties of the node - * @cancelable: a #GCancellable - * @callback: a #GAsyncReadyCallback - * @user_data: user data. - * - * Asynchronously create a new node in @context. - */ -void -pinos_context_create_node (PinosContext *context, - const gchar *factory_name, - const gchar *name, - PinosProperties *properties, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - PinosContextPrivate *priv; - GTask *task; - CreateNodeData *data; - - g_return_if_fail (PINOS_IS_CONTEXT (context)); - priv = context->priv; - - task = g_task_new (context, - cancellable, - callback, - user_data); - - data = g_slice_new (CreateNodeData); - data->factory_name = g_strdup (factory_name); - data->name = g_strdup (name); - data->properties = pinos_properties_merge (priv->properties, properties); - - g_task_set_task_data (task, data, (GDestroyNotify) create_node_data_free); - - g_main_context_invoke (context->priv->context, - (GSourceFunc) do_create_node, - task); -} - -/** - * pinos_context_create_node_finish: - * @context: a #PinosContext - * @res: a #GAsyncResult - * @error: a #GError or %NULL - * - * Get the newly created #PinosNode. This function should be called in the callback - * of pinos_context_create_node() to get the result or error. - * - * Returns: a new #PinosNode. If %NULL is returned, @error will - * be set. - */ -PinosNode * -pinos_context_create_node_finish (PinosContext *context, - GAsyncResult *res, - GError **error) -{ - return g_task_propagate_pointer (G_TASK (res), error); -} diff --git a/pinos/client/context.h b/pinos/client/context.h index e84a6a166..40d3ada4c 100644 --- a/pinos/client/context.h +++ b/pinos/client/context.h @@ -31,7 +31,6 @@ typedef struct _PinosContextPrivate PinosContextPrivate; #include #include -#include #define PINOS_TYPE_CONTEXT (pinos_context_get_type ()) #define PINOS_IS_CONTEXT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), PINOS_TYPE_CONTEXT)) @@ -106,17 +105,6 @@ PinosContext * pinos_context_new (GMainContext *ctx, gboolean pinos_context_connect (PinosContext *context, PinosContextFlags flags); gboolean pinos_context_disconnect (PinosContext *context); -void pinos_context_create_node (PinosContext *context, - const gchar *factory_name, - const gchar *name, - PinosProperties *properties, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data); -PinosNode * pinos_context_create_node_finish (PinosContext *context, - GAsyncResult *res, - GError **error); - PinosContextState pinos_context_get_state (PinosContext *context); const GError * pinos_context_get_error (PinosContext *context); diff --git a/pinos/client/stream.c b/pinos/client/stream.c index 567454e17..1db124e7a 100644 --- a/pinos/client/stream.c +++ b/pinos/client/stream.c @@ -577,131 +577,12 @@ pinos_stream_get_error (PinosStream *stream) return stream->priv->error; } -static void -on_received_buffer (PinosPort *port, - gpointer user_data) -{ - PinosStream *stream = user_data; - - g_signal_emit (stream, signals[SIGNAL_NEW_BUFFER], 0, NULL); -} - -static void -on_port_notify (GObject *object, - GParamSpec *pspec, - gpointer user_data) -{ - PinosPort *port = PINOS_PORT (object); - PinosStream *stream = user_data; - PinosStreamPrivate *priv = stream->priv; - - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "format")) { - g_clear_pointer (&priv->format, g_bytes_unref); - g_object_get (port, "format", &priv->format, NULL); - g_object_notify (G_OBJECT (stream), "format"); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "possible-formats")) { - g_clear_pointer (&priv->possible_formats, g_bytes_unref); - g_object_get (port, "possible-formats", &priv->possible_formats, NULL); - g_object_notify (G_OBJECT (stream), "possible-formats"); - } -} - -static void -on_port_created (GObject *source_object, - GAsyncResult *res, - gpointer user_data) -{ - PinosStream *stream = user_data; - PinosStreamPrivate *priv = stream->priv; - GError *error = NULL; - - g_assert (priv->node == PINOS_NODE (source_object)); - - priv->port = pinos_node_create_port_finish (priv->node, - res, - &error); - if (priv->port == NULL) - goto create_failed; - - on_port_notify (G_OBJECT (priv->port), NULL, stream); - g_signal_connect (priv->port, "notify", (GCallback) on_port_notify, stream); - - pinos_port_set_received_buffer_cb (priv->port, on_received_buffer, stream, NULL); - - stream_set_state (stream, PINOS_STREAM_STATE_READY, NULL); - g_object_unref (stream); - - return; - - /* ERRORS */ -create_failed: - { - g_warning ("failed to create port: %s", error->message); - stream_set_state (stream, PINOS_STREAM_STATE_ERROR, error); - g_object_unref (stream); - return; - } -} - -static void -on_node_created (GObject *source_object, - GAsyncResult *res, - gpointer user_data) -{ - PinosStream *stream = user_data; - PinosStreamPrivate *priv = stream->priv; - PinosContext *context = priv->context; - GError *error = NULL; - - priv->node = pinos_context_create_node_finish (context, res, &error); - if (priv->node == NULL) - goto create_failed; - - if (priv->properties == NULL) - priv->properties = pinos_properties_new (NULL, NULL); - - if (priv->flags & PINOS_STREAM_FLAG_AUTOCONNECT) - pinos_properties_set (priv->properties, "autoconnect", "1"); - else - pinos_properties_set (priv->properties, "autoconnect", "0"); - - if (priv->path) - pinos_properties_set (priv->properties, "target-path", priv->path); - - pinos_node_create_port (priv->node, - priv->direction, - "client-port", - priv->possible_formats, - priv->properties, - NULL, /* GCancellable *cancellable */ - on_port_created, - stream); - return; - - /* ERRORS */ -create_failed: - { - g_warning ("failed to create node: %s", error->message); - stream_set_state (stream, PINOS_STREAM_STATE_ERROR, error); - g_object_unref (stream); - return; - } -} - static gboolean do_connect (PinosStream *stream) { PinosStreamPrivate *priv = stream->priv; PinosContext *context = priv->context; - pinos_context_create_node (context, - "client-node", - "client-node", - priv->properties, - NULL, /* GCancellable *cancellable */ - on_node_created, - stream); return FALSE; } @@ -841,8 +722,6 @@ do_disconnect (PinosStream *stream) { PinosStreamPrivate *priv = stream->priv; - pinos_node_remove (priv->node); - return FALSE; } @@ -896,7 +775,7 @@ pinos_stream_peek_buffer (PinosStream *stream) priv = stream->priv; //g_return_val_if_fail (priv->state == PINOS_STREAM_STATE_STREAMING, FALSE); - return pinos_port_peek_buffer (priv->port); + return NULL; } /** @@ -916,7 +795,6 @@ pinos_stream_buffer_builder_init (PinosStream *stream, PinosBufferBuilder *buil g_return_if_fail (PINOS_IS_STREAM (stream)); priv = stream->priv; - pinos_port_buffer_builder_init (priv->port, builder); } /** @@ -947,17 +825,5 @@ pinos_stream_send_buffer (PinosStream *stream, priv = stream->priv; g_return_val_if_fail (priv->state == PINOS_STREAM_STATE_STREAMING, FALSE); - if (!pinos_port_send_buffer (priv->port, buffer, &error)) - goto send_error; - return TRUE; - - /* ERRORS */ -send_error: - { - g_warning ("failed to send message: %s", error->message); - stream_set_state (stream, PINOS_STREAM_STATE_ERROR, error); - g_clear_error (&error); - return FALSE; - } } diff --git a/pinos/dbus/org.pinos.xml b/pinos/dbus/org.pinos.xml index ed384db87..888e44a8f 100644 --- a/pinos/dbus/org.pinos.xml +++ b/pinos/dbus/org.pinos.xml @@ -23,6 +23,27 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - + + + + - A port on a Node1 can provide or consume data. - --> - - - - - - - - - - - - - diff --git a/pinos/gst/gstpinosportsink.h b/pinos/gst/gstpinosportsink.h index 57a251a3d..108e20165 100644 --- a/pinos/gst/gstpinosportsink.h +++ b/pinos/gst/gstpinosportsink.h @@ -23,6 +23,7 @@ #include #include +#include #include #include diff --git a/pinos/gst/gstpinosportsrc.h b/pinos/gst/gstpinosportsrc.h index a135e59b9..29635ef82 100644 --- a/pinos/gst/gstpinosportsrc.h +++ b/pinos/gst/gstpinosportsrc.h @@ -24,6 +24,7 @@ #include #include +#include G_BEGIN_DECLS diff --git a/pinos/modules/gst/gst-manager.c b/pinos/modules/gst/gst-manager.c index 9be9d4970..6de81e6f4 100644 --- a/pinos/modules/gst/gst-manager.c +++ b/pinos/modules/gst/gst-manager.c @@ -65,7 +65,7 @@ device_added (PinosGstManager *manager, PinosGstManagerPrivate *priv = manager->priv; gchar *name, *klass; GstElement *element; - PinosServerNode *node = NULL; + PinosNode *node = NULL; GstStructure *p; PinosProperties *properties; GstCaps *caps; @@ -112,7 +112,7 @@ device_added (PinosGstManager *manager, NULL); } if (node) - g_object_set_data (G_OBJECT (device), "PinosServerNode", node); + g_object_set_data (G_OBJECT (device), "PinosNode", node); pinos_properties_free (properties); gst_caps_unref (caps); @@ -125,7 +125,7 @@ device_removed (PinosGstManager *manager, GstDevice *device) { gchar *name; - PinosServerNode *node; + PinosNode *node; name = gst_device_get_display_name (device); if (strcmp (name, "gst") == 0) @@ -133,7 +133,7 @@ device_removed (PinosGstManager *manager, g_print("Device removed: %s\n", name); - node = g_object_steal_data (G_OBJECT (device), "PinosServerNode"); + node = g_object_steal_data (G_OBJECT (device), "PinosNode"); g_object_unref (node); g_free (name); } diff --git a/pinos/modules/gst/gst-sink.c b/pinos/modules/gst/gst-sink.c index 0598d89ff..9d9fe335f 100644 --- a/pinos/modules/gst/gst-sink.c +++ b/pinos/modules/gst/gst-sink.c @@ -31,7 +31,7 @@ typedef struct { PinosGstSink *sink; - PinosServerPort *port; + PinosPort *port; GstElement *src; GstElement *convert; @@ -62,7 +62,7 @@ enum { PROP_CONVERT_NAME }; -G_DEFINE_TYPE (PinosGstSink, pinos_gst_sink, PINOS_TYPE_SERVER_NODE); +G_DEFINE_TYPE (PinosGstSink, pinos_gst_sink, PINOS_TYPE_NODE); static gboolean bus_handler (GstBus *bus, @@ -381,12 +381,10 @@ free_sink_port_data (SinkPortData *data) g_slice_free (SinkPortData, data); } -static PinosServerPort * -create_port_sync (PinosServerNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props) +static PinosPort * +add_port (PinosNode *node, + PinosDirection direction, + GError **error) { PinosGstSink *sink = PINOS_GST_SINK (node); PinosGstSinkPrivate *priv = sink->priv; @@ -395,12 +393,8 @@ create_port_sync (PinosServerNode *node, data = g_slice_new0 (SinkPortData); data->sink = sink; - data->port = PINOS_SERVER_NODE_CLASS (pinos_gst_sink_parent_class) - ->create_port_sync (node, - direction, - name, - possible_formats, - props); + data->port = PINOS_NODE_CLASS (pinos_gst_sink_parent_class) + ->add_port (node, direction, error); g_debug ("connecting signals"); g_signal_connect (data->port, "linked", (GCallback) on_linked, data); @@ -435,7 +429,7 @@ remove_port (PinosNode *node, for (walk = priv->ports; walk; walk = g_list_next (walk)) { SinkPortData *data = walk->data; - if (data->port == PINOS_SERVER_PORT_CAST (port)) { + if (data->port == PINOS_PORT_CAST (port)) { free_sink_port_data (data); priv->ports = g_list_delete_link (priv->ports, walk); break; @@ -472,7 +466,6 @@ pinos_gst_sink_class_init (PinosGstSinkClass * klass) { GObjectClass *gobject_class = G_OBJECT_CLASS (klass); PinosNodeClass *node_class = PINOS_NODE_CLASS (klass); - PinosServerNodeClass *server_node_class = PINOS_SERVER_NODE_CLASS (klass); g_type_class_add_private (klass, sizeof (PinosGstSinkPrivate)); @@ -518,9 +511,8 @@ pinos_gst_sink_class_init (PinosGstSinkClass * klass) G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_STRINGS)); node_class->set_state = set_state; + node_class->add_port = add_port; node_class->remove_port = remove_port; - - server_node_class->create_port_sync = create_port_sync; } static void @@ -529,7 +521,7 @@ pinos_gst_sink_init (PinosGstSink * sink) sink->priv = PINOS_GST_SINK_GET_PRIVATE (sink); } -PinosServerNode * +PinosNode * pinos_gst_sink_new (PinosDaemon *daemon, const gchar *name, PinosProperties *properties, @@ -538,7 +530,7 @@ pinos_gst_sink_new (PinosDaemon *daemon, GstElement *mixer, const gchar *convert_name) { - PinosServerNode *node; + PinosNode *node; node = g_object_new (PINOS_TYPE_GST_SINK, "daemon", daemon, diff --git a/pinos/modules/gst/gst-sink.h b/pinos/modules/gst/gst-sink.h index 0b4aa2669..cfe8fdbd2 100644 --- a/pinos/modules/gst/gst-sink.h +++ b/pinos/modules/gst/gst-sink.h @@ -23,7 +23,7 @@ #include #include -#include +#include G_BEGIN_DECLS @@ -41,18 +41,18 @@ typedef struct _PinosGstSinkClass PinosGstSinkClass; typedef struct _PinosGstSinkPrivate PinosGstSinkPrivate; struct _PinosGstSink { - PinosServerNode object; + PinosNode object; PinosGstSinkPrivate *priv; }; struct _PinosGstSinkClass { - PinosServerNodeClass parent_class; + PinosNodeClass parent_class; }; GType pinos_gst_sink_get_type (void); -PinosServerNode * pinos_gst_sink_new (PinosDaemon *daemon, +PinosNode * pinos_gst_sink_new (PinosDaemon *daemon, const gchar *name, PinosProperties *properties, GstElement *element, diff --git a/pinos/modules/gst/gst-source.c b/pinos/modules/gst/gst-source.c index 404f400ec..3ddab2ac6 100644 --- a/pinos/modules/gst/gst-source.c +++ b/pinos/modules/gst/gst-source.c @@ -31,7 +31,7 @@ typedef struct { PinosGstSource *source; - PinosServerPort *port; + PinosPort *port; GstElement *convert; GstElement *sink; @@ -62,7 +62,7 @@ enum { PROP_CONVERT_NAME }; -G_DEFINE_TYPE (PinosGstSource, pinos_gst_source, PINOS_TYPE_SERVER_NODE); +G_DEFINE_TYPE (PinosGstSource, pinos_gst_source, PINOS_TYPE_NODE); static gboolean bus_handler (GstBus *bus, @@ -451,7 +451,7 @@ remove_port (PinosNode *node, for (walk = priv->ports; walk; walk = g_list_next (walk)) { SourcePortData *data = walk->data; - if (data->port == PINOS_SERVER_PORT_CAST (port)) { + if (data->port == PINOS_PORT_CAST (port)) { free_source_port_data (data); priv->ports = g_list_delete_link (priv->ports, walk); break; @@ -557,27 +557,25 @@ create_best_element (GstCaps *caps) return element; } -static PinosServerPort * -create_port_sync (PinosServerNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props) +static PinosPort * +add_port (PinosNode *node, + PinosDirection direction, + GError **error) { PinosGstSource *source = PINOS_GST_SOURCE (node); PinosGstSourcePrivate *priv = source->priv; SourcePortData *data; + PinosProperties *props = NULL; if (priv->element == NULL) { GstCaps *caps; - caps = gst_caps_from_string (g_bytes_get_data (possible_formats, NULL)); + caps = NULL; priv->element = create_best_element (caps); gst_caps_unref (caps); if (priv->element) { - if (props == NULL) - props = pinos_properties_new (NULL, NULL); + props = pinos_properties_new (NULL, NULL); pinos_properties_set (props, "autoconnect", "0"); setup_pipeline (source, NULL); } @@ -586,12 +584,8 @@ create_port_sync (PinosServerNode *node, data = g_slice_new0 (SourcePortData); data->source = source; - data->port = PINOS_SERVER_NODE_CLASS (pinos_gst_source_parent_class) - ->create_port_sync (node, - direction, - name, - possible_formats, - props); + data->port = PINOS_NODE_CLASS (pinos_gst_source_parent_class) + ->add_port (node, direction, error); g_debug ("connecting signals"); g_signal_connect (data->port, "linked", (GCallback) on_linked, data); @@ -624,7 +618,6 @@ pinos_gst_source_class_init (PinosGstSourceClass * klass) { GObjectClass *gobject_class = G_OBJECT_CLASS (klass); PinosNodeClass *node_class = PINOS_NODE_CLASS (klass); - PinosServerNodeClass *server_node_class = PINOS_SERVER_NODE_CLASS (klass); g_type_class_add_private (klass, sizeof (PinosGstSourcePrivate)); @@ -671,9 +664,8 @@ pinos_gst_source_class_init (PinosGstSourceClass * klass) G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_STRINGS)); node_class->set_state = set_state; + node_class->add_port = add_port; node_class->remove_port = remove_port; - - server_node_class->create_port_sync = create_port_sync; } static void @@ -682,7 +674,7 @@ pinos_gst_source_init (PinosGstSource * source) source->priv = PINOS_GST_SOURCE_GET_PRIVATE (source); } -PinosServerNode * +PinosNode * pinos_gst_source_new (PinosDaemon *daemon, const gchar *name, PinosProperties *properties, @@ -691,7 +683,7 @@ pinos_gst_source_new (PinosDaemon *daemon, GstElement *splitter, const gchar *convert_name) { - PinosServerNode *node; + PinosNode *node; node = g_object_new (PINOS_TYPE_GST_SOURCE, "daemon", daemon, diff --git a/pinos/modules/gst/gst-source.h b/pinos/modules/gst/gst-source.h index aa0bea7ba..2ce4f3060 100644 --- a/pinos/modules/gst/gst-source.h +++ b/pinos/modules/gst/gst-source.h @@ -23,7 +23,7 @@ #include #include -#include +#include G_BEGIN_DECLS @@ -41,18 +41,18 @@ typedef struct _PinosGstSourceClass PinosGstSourceClass; typedef struct _PinosGstSourcePrivate PinosGstSourcePrivate; struct _PinosGstSource { - PinosServerNode object; + PinosNode object; PinosGstSourcePrivate *priv; }; struct _PinosGstSourceClass { - PinosServerNodeClass parent_class; + PinosNodeClass parent_class; }; GType pinos_gst_source_get_type (void); -PinosServerNode * pinos_gst_source_new (PinosDaemon *daemon, +PinosNode * pinos_gst_source_new (PinosDaemon *daemon, const gchar *name, PinosProperties *properties, GstElement *element, diff --git a/pinos/server/daemon.c b/pinos/server/daemon.c index c1e0fb111..9c32e524a 100644 --- a/pinos/server/daemon.c +++ b/pinos/server/daemon.c @@ -26,7 +26,7 @@ #include "pinos/client/pinos.h" #include "pinos/server/daemon.h" -#include "pinos/server/server-node.h" +#include "pinos/server/node.h" #include "pinos/dbus/org-pinos.h" @@ -122,15 +122,15 @@ sender_data_new (PinosDaemon *daemon, } static void -handle_remove_node (PinosServerNode *node, - gpointer user_data) +handle_remove_node (PinosNode *node, + gpointer user_data) { PinosDaemon *daemon = user_data; PinosDaemonPrivate *priv = daemon->priv; const gchar *sender; SenderData *data; - sender = pinos_server_node_get_sender (node); + sender = pinos_node_get_sender (node); g_debug ("daemon %p: sender %s removed node %p", daemon, sender, node); @@ -173,10 +173,10 @@ handle_create_node (PinosDaemon1 *interface, arg_name, props); } else { - node = pinos_server_node_new (daemon, - sender, - arg_name, - props); + node = pinos_node_new (daemon, + sender, + arg_name, + props); } pinos_properties_free (props); @@ -195,7 +195,7 @@ handle_create_node (PinosDaemon1 *interface, (GCallback) handle_remove_node, daemon); - object_path = pinos_server_node_get_object_path (PINOS_SERVER_NODE (node)); + object_path = pinos_node_get_object_path (node); g_debug ("daemon %p: added node %p with path %s", daemon, node, object_path); g_dbus_method_invocation_return_value (invocation, g_variant_new ("(o)", object_path)); @@ -385,18 +385,18 @@ pinos_daemon_unexport (PinosDaemon *daemon, /** * pinos_daemon_add_node: * @daemon: a #PinosDaemon - * @node: a #PinosServerNode + * @node: a #PinosNode * * Add @node to @daemon. */ void -pinos_daemon_add_node (PinosDaemon *daemon, - PinosServerNode *node) +pinos_daemon_add_node (PinosDaemon *daemon, + PinosNode *node) { PinosDaemonPrivate *priv; g_return_if_fail (PINOS_IS_DAEMON (daemon)); - g_return_if_fail (PINOS_IS_SERVER_NODE (node)); + g_return_if_fail (PINOS_IS_NODE (node)); priv = daemon->priv; priv->nodes = g_list_prepend (priv->nodes, node); @@ -405,18 +405,18 @@ pinos_daemon_add_node (PinosDaemon *daemon, /** * pinos_daemon_remove_node: * @daemon: a #PinosDaemon - * @node: a #PinosServerNode + * @node: a #PinosNode * * Remove @node from @daemon. */ void -pinos_daemon_remove_node (PinosDaemon *daemon, - PinosServerNode *node) +pinos_daemon_remove_node (PinosDaemon *daemon, + PinosNode *node) { PinosDaemonPrivate *priv; g_return_if_fail (PINOS_IS_DAEMON (daemon)); - g_return_if_fail (PINOS_IS_SERVER_NODE (node)); + g_return_if_fail (PINOS_IS_NODE (node)); priv = daemon->priv; priv->nodes = g_list_remove (priv->nodes, node); @@ -444,7 +444,7 @@ pinos_daemon_find_port (PinosDaemon *daemon, GError **error) { PinosDaemonPrivate *priv; - PinosServerPort *best = NULL; + PinosPort *best = NULL; GList *nodes, *ports; gboolean have_name, created_port = FALSE; @@ -454,19 +454,19 @@ pinos_daemon_find_port (PinosDaemon *daemon, have_name = name ? strlen (name) > 0 : FALSE; for (nodes = priv->nodes; nodes; nodes = g_list_next (nodes)) { - PinosServerNode *n = nodes->data; + PinosNode *n = nodes->data; gboolean node_found = FALSE; - g_debug ("name %s, node path %s", name, pinos_server_node_get_object_path (n)); + g_debug ("name %s, node path %s", name, pinos_node_get_object_path (n)); /* we found the node */ - if (have_name && g_str_has_suffix (pinos_server_node_get_object_path (n), name)) { + if (have_name && g_str_has_suffix (pinos_node_get_object_path (n), name)) { g_debug ("name \"%s\" matches node %p", name, n); node_found = TRUE; } - for (ports = pinos_node_get_ports (PINOS_NODE (n)); ports; ports = g_list_next (ports)) { - PinosServerPort *p = ports->data; + for (ports = pinos_node_get_ports (n); ports; ports = g_list_next (ports)) { + PinosPort *p = ports->data; PinosDirection dir; GBytes *format; @@ -474,16 +474,7 @@ pinos_daemon_find_port (PinosDaemon *daemon, if (dir != direction) continue; - if (have_name && !node_found) { - if (!g_str_has_suffix (pinos_server_port_get_object_path (p), name)) - continue; - g_debug ("name \"%s\" matches port %p", name, p); - best = p; - node_found = TRUE; - break; - } - - format = pinos_port_filter_formats (PINOS_PORT (p), format_filter, NULL); + format = pinos_port_filter_formats (p, format_filter, NULL); if (format != NULL) { g_debug ("port %p matches filter", p); g_bytes_unref (format); @@ -494,7 +485,7 @@ pinos_daemon_find_port (PinosDaemon *daemon, } if (best == NULL && node_found) { g_debug ("node %p: making port", n); - best = pinos_server_node_create_port_sync (n, direction, name, format_filter, props); + best = pinos_node_add_port (n, direction, NULL); if (best != NULL) { created_port = TRUE; break; diff --git a/pinos/server/daemon.h b/pinos/server/daemon.h index a64cbfed7..c9d887675 100644 --- a/pinos/server/daemon.h +++ b/pinos/server/daemon.h @@ -37,8 +37,8 @@ typedef struct _PinosDaemon PinosDaemon; typedef struct _PinosDaemonClass PinosDaemonClass; typedef struct _PinosDaemonPrivate PinosDaemonPrivate; -#include -#include +#include +#include #include #include @@ -74,8 +74,8 @@ void pinos_daemon_stop (PinosDaemon *daemon); gchar * pinos_daemon_export_uniquely (PinosDaemon *daemon, GDBusObjectSkeleton *skel); void pinos_daemon_unexport (PinosDaemon *daemon, const gchar *name); -void pinos_daemon_add_node (PinosDaemon *daemon, PinosServerNode *node); -void pinos_daemon_remove_node (PinosDaemon *daemon, PinosServerNode *node); +void pinos_daemon_add_node (PinosDaemon *daemon, PinosNode *node); +void pinos_daemon_remove_node (PinosDaemon *daemon, PinosNode *node); PinosPort * pinos_daemon_find_port (PinosDaemon *daemon, PinosDirection direction, diff --git a/pinos/client/node.c b/pinos/server/node.c similarity index 57% rename from pinos/client/node.c rename to pinos/server/node.c index 672959831..872529fdc 100644 --- a/pinos/client/node.c +++ b/pinos/server/node.c @@ -17,19 +17,30 @@ * Boston, MA 02110-1301, USA. */ +#include +#include + #include +#include #include "pinos/client/pinos.h" #include "pinos/client/enumtypes.h" -#include "pinos/client/node.h" +#include "pinos/server/node.h" +#include "pinos/server/daemon.h" +#include "pinos/dbus/org-pinos.h" #define PINOS_NODE_GET_PRIVATE(node) \ (G_TYPE_INSTANCE_GET_PRIVATE ((node), PINOS_TYPE_NODE, PinosNodePrivate)) struct _PinosNodePrivate { + PinosDaemon *daemon; + PinosNode1 *iface; + + gchar *sender; + gchar *object_path; gchar *name; PinosNodeState state; @@ -46,6 +57,9 @@ G_DEFINE_ABSTRACT_TYPE (PinosNode, pinos_node, G_TYPE_OBJECT); enum { PROP_0, + PROP_DAEMON, + PROP_SENDER, + PROP_OBJECT_PATH, PROP_NAME, PROP_STATE, PROP_PROPERTIES, @@ -59,6 +73,93 @@ enum static guint signals[LAST_SIGNAL] = { 0 }; +static gboolean +node_set_state (PinosNode *node, + PinosNodeState state) +{ + return FALSE; +} + +static PinosPort * +node_add_port (PinosNode *node, + PinosDirection direction, + GError **error) +{ + PinosNodePrivate *priv = node->priv; + PinosPort *port; + + port = g_object_new (PINOS_TYPE_PORT, + "daemon", priv->daemon, + "node", node, + "direction", direction, + NULL); + return port; +} + +static void +node_remove_port (PinosNode *node, + PinosPort *port) +{ +} + +static gboolean +handle_add_port (PinosNode1 *interface, + GDBusMethodInvocation *invocation, + PinosDirection arg_direction, + gpointer user_data) +{ + PinosNode *node = user_data; + PinosNodePrivate *priv = node->priv; + const gchar *sender; + PinosPort *port; + GError *error = NULL; + + sender = g_dbus_method_invocation_get_sender (invocation); + if (g_strcmp0 (priv->sender, sender) != 0) + goto not_allowed; + + port = pinos_node_add_port (node, arg_direction, &error); + if (port == NULL) + goto no_port; + + g_debug ("node %p: add port %p", node, port); + g_dbus_method_invocation_return_value (invocation, + g_variant_new ("(u)", 1)); + + return TRUE; + + /* ERRORS */ +not_allowed: + { + g_debug ("sender %s is not owner of node with sender %s", sender, priv->sender); + g_dbus_method_invocation_return_dbus_error (invocation, + "org.pinos.Error", "not node owner"); + return TRUE; + } +no_port: + { + g_debug ("node %p: could create port", node); + g_dbus_method_invocation_return_dbus_error (invocation, + "org.pinos.Error", "can't create port"); + return TRUE; + } +} + +static gboolean +handle_remove (PinosNode1 *interface, + GDBusMethodInvocation *invocation, + gpointer user_data) +{ + PinosNode *node = user_data; + + g_debug ("node %p: remove", node); + pinos_node_remove (node); + + g_dbus_method_invocation_return_value (invocation, + g_variant_new ("()")); + return TRUE; +} + static void pinos_node_get_property (GObject *_object, guint prop_id, @@ -69,6 +170,18 @@ pinos_node_get_property (GObject *_object, PinosNodePrivate *priv = node->priv; switch (prop_id) { + case PROP_DAEMON: + g_value_set_object (value, priv->daemon); + break; + + case PROP_SENDER: + g_value_set_string (value, priv->sender); + break; + + case PROP_OBJECT_PATH: + g_value_set_string (value, priv->object_path); + break; + case PROP_NAME: g_value_set_string (value, priv->name); break; @@ -97,6 +210,14 @@ pinos_node_set_property (GObject *_object, PinosNodePrivate *priv = node->priv; switch (prop_id) { + case PROP_DAEMON: + priv->daemon = g_value_dup_object (value); + break; + + case PROP_SENDER: + priv->sender = g_value_dup_string (value); + break; + case PROP_NAME: priv->name = g_value_dup_string (value); break; @@ -113,14 +234,74 @@ pinos_node_set_property (GObject *_object, } } +static void +node_register_object (PinosNode *node) +{ + PinosNodePrivate *priv = node->priv; + PinosDaemon *daemon = priv->daemon; + PinosObjectSkeleton *skel; + + skel = pinos_object_skeleton_new (PINOS_DBUS_OBJECT_NODE); + + pinos_object_skeleton_set_node1 (skel, priv->iface); + + g_free (priv->object_path); + priv->object_path = pinos_daemon_export_uniquely (daemon, G_DBUS_OBJECT_SKELETON (skel)); + g_object_unref (skel); + + g_debug ("node %p: register object %s", node, priv->object_path); + pinos_daemon_add_node (daemon, node); + + return; +} + +static void +node_unregister_object (PinosNode *node) +{ + PinosNodePrivate *priv = node->priv; + + g_debug ("node %p: unregister object %s", node, priv->object_path); + pinos_daemon_unexport (priv->daemon, priv->object_path); + pinos_daemon_remove_node (priv->daemon, node); +} + +static void +on_property_notify (GObject *obj, + GParamSpec *pspec, + gpointer user_data) +{ + PinosNode *node = user_data; + PinosNodePrivate *priv = node->priv; + + if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "sender") == 0) { + pinos_node1_set_owner (priv->iface, priv->sender); + } + if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "name") == 0) { + pinos_node1_set_name (priv->iface, pinos_node_get_name (node)); + } + if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "properties") == 0) { + PinosProperties *props = pinos_node_get_properties (node); + pinos_node1_set_properties (priv->iface, props ? pinos_properties_to_variant (props) : NULL); + } +} + static void pinos_node_constructed (GObject * obj) { PinosNode *node = PINOS_NODE (obj); + PinosNodePrivate *priv = node->priv; g_debug ("node %p: constructed", node); + g_signal_connect (node, "notify", (GCallback) on_property_notify, node); G_OBJECT_CLASS (pinos_node_parent_class)->constructed (obj); + + if (priv->sender == NULL) { + priv->sender = g_strdup (pinos_daemon_get_sender (priv->daemon)); + pinos_node1_set_owner (priv->iface, priv->sender); + } + + node_register_object (node); } static void @@ -129,8 +310,11 @@ pinos_node_dispose (GObject * obj) PinosNode *node = PINOS_NODE (obj); PinosNodePrivate *priv = node->priv; - g_debug ("node %p: dispose", node); pinos_node_set_state (node, PINOS_NODE_STATE_SUSPENDED); + + g_debug ("node %p: dispose", node); + node_unregister_object (node); + g_list_free_full (priv->ports, (GDestroyNotify) g_object_unref); priv->ports = NULL; @@ -144,6 +328,9 @@ pinos_node_finalize (GObject * obj) PinosNodePrivate *priv = node->priv; g_debug ("node %p: finalize", node); + g_clear_object (&priv->daemon); + g_clear_object (&priv->iface); + g_free (priv->sender); g_free (priv->name); g_clear_error (&priv->error); if (priv->properties) @@ -156,6 +343,7 @@ static void pinos_node_class_init (PinosNodeClass * klass) { GObjectClass *gobject_class = G_OBJECT_CLASS (klass); + PinosNodeClass *node_class = PINOS_NODE_CLASS (klass); g_type_class_add_private (klass, sizeof (PinosNodePrivate)); @@ -165,6 +353,35 @@ pinos_node_class_init (PinosNodeClass * klass) gobject_class->set_property = pinos_node_set_property; gobject_class->get_property = pinos_node_get_property; + g_object_class_install_property (gobject_class, + PROP_DAEMON, + g_param_spec_object ("daemon", + "Daemon", + "The Daemon", + PINOS_TYPE_DAEMON, + G_PARAM_READWRITE | + G_PARAM_CONSTRUCT_ONLY | + G_PARAM_STATIC_STRINGS)); + + g_object_class_install_property (gobject_class, + PROP_SENDER, + g_param_spec_string ("sender", + "Sender", + "The Sender", + NULL, + G_PARAM_READWRITE | + G_PARAM_CONSTRUCT_ONLY | + G_PARAM_STATIC_STRINGS)); + + g_object_class_install_property (gobject_class, + PROP_OBJECT_PATH, + g_param_spec_string ("object-path", + "Object Path", + "The object path", + NULL, + G_PARAM_READABLE | + G_PARAM_STATIC_STRINGS)); + g_object_class_install_property (gobject_class, PROP_NAME, g_param_spec_string ("name", @@ -205,6 +422,10 @@ pinos_node_class_init (PinosNodeClass * klass) G_TYPE_NONE, 0, G_TYPE_NONE); + + node_class->set_state = node_set_state; + node_class->add_port = node_add_port; + node_class->remove_port = node_remove_port; } static void @@ -213,7 +434,42 @@ pinos_node_init (PinosNode * node) PinosNodePrivate *priv = node->priv = PINOS_NODE_GET_PRIVATE (node); g_debug ("node %p: new", node); + priv->iface = pinos_node1_skeleton_new (); + g_signal_connect (priv->iface, "handle-add-port", + (GCallback) handle_add_port, + node); + g_signal_connect (priv->iface, "handle-remove", + (GCallback) handle_remove, + node); priv->state = PINOS_NODE_STATE_SUSPENDED; + pinos_node1_set_state (priv->iface, PINOS_NODE_STATE_SUSPENDED); +} + +/** + * pinos_node_new: + * @daemon: a #PinosDaemon + * @sender: the path of the owner + * @name: a name + * @properties: extra properties + * + * Create a new #PinosNode. + * + * Returns: a new #PinosNode + */ +PinosNode * +pinos_node_new (PinosDaemon *daemon, + const gchar *sender, + const gchar *name, + PinosProperties *properties) +{ + g_return_val_if_fail (PINOS_IS_DAEMON (daemon), NULL); + + return g_object_new (PINOS_TYPE_NODE, + "daemon", daemon, + "sender", sender, + "name", name, + "properties", properties, + NULL); } /** @@ -273,6 +529,62 @@ pinos_node_get_properties (PinosNode *node) return priv->properties; } +/** + * pinos_node_get_daemon: + * @node: a #PinosNode + * + * Get the daemon of @node. + * + * Returns: the daemon of @node. + */ +PinosDaemon * +pinos_node_get_daemon (PinosNode *node) +{ + PinosNodePrivate *priv; + + g_return_val_if_fail (PINOS_IS_NODE (node), NULL); + priv = node->priv; + + return priv->daemon; +} + +/** + * pinos_node_get_sender: + * @node: a #PinosNode + * + * Get the owner path of @node. + * + * Returns: the owner path of @node. + */ +const gchar * +pinos_node_get_sender (PinosNode *node) +{ + PinosNodePrivate *priv; + + g_return_val_if_fail (PINOS_IS_NODE (node), NULL); + priv = node->priv; + + return priv->sender; +} +/** + * pinos_node_get_object_path: + * @node: a #PinosNode + * + * Get the object path of @node. + * + * Returns: the object path of @node. + */ +const gchar * +pinos_node_get_object_path (PinosNode *node) +{ + PinosNodePrivate *priv; + + g_return_val_if_fail (PINOS_IS_NODE (node), NULL); + priv = node->priv; + + return priv->object_path; +} + /** * pinos_node_remove: * @node: a #PinosNode @@ -296,84 +608,42 @@ handle_remove_port (PinosPort *port, PinosNode *node) } /** - * pinos_node_create_port: + * pinos_node_add_port: * @node: a #PinosNode * @direction: the direction of the port - * @name: the name of the port - * @possible_formats: possible media formats for the port - * @props: extra properties for the port + * @error: location of #GError * - * Create a new #PinosPort from @node. + * Add the #PinosPort to @node * - * Returns: a new #PinosPort that should be freed with - * pinos_node_remove_port(). + * Returns: a new #PinosPort or %NULL */ -void -pinos_node_create_port (PinosNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) +PinosPort * +pinos_node_add_port (PinosNode *node, + PinosDirection direction, + GError **error) { PinosNodeClass *klass; - GTask *task; - - g_return_if_fail (PINOS_IS_NODE (node)); - - klass = PINOS_NODE_GET_CLASS (node); - if (!klass->create_port) - return; - - g_debug ("node %p: create port", node); - task = g_task_new (node, cancellable, callback, user_data); - klass->create_port (node, direction, name, possible_formats, props, task); -} - -PinosPort * -pinos_node_create_port_finish (PinosNode *node, - GAsyncResult *res, - GError **error) -{ - PinosPort *port; PinosNodePrivate *priv; + PinosPort *port; g_return_val_if_fail (PINOS_IS_NODE (node), NULL); priv = node->priv; - port = g_task_propagate_pointer (G_TASK (res), error); - if (port != NULL) { - pinos_node_add_port (node, port); + klass = PINOS_NODE_GET_CLASS (node); + if (!klass->add_port) { + g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, "add-port not implemented"); + return NULL; } - g_debug ("node %p: created port %p", node, port); - return port; -} -/** - * pinos_node_add_port: - * @node: a #PinosNode - * @port: (transfer full): a #PinosPort - * - * Add the #PinosPort to @node - */ -void -pinos_node_add_port (PinosNode *node, PinosPort *port) -{ - PinosNodePrivate *priv; - GList *find; + g_debug ("node %p: add port", node); + port = klass->add_port (node, direction, error); - g_return_if_fail (PINOS_IS_NODE (node)); - g_return_if_fail (PINOS_IS_PORT (port)); - priv = node->priv; - - find = g_list_find (priv->ports, port); - if (find == NULL) { - g_debug ("node %p: add port %p", node, port); + if (port) { priv->ports = g_list_append (priv->ports, port); g_signal_connect (port, "remove", (GCallback) handle_remove_port, node); } + + return port; } /** diff --git a/pinos/client/node.h b/pinos/server/node.h similarity index 68% rename from pinos/client/node.h rename to pinos/server/node.h index 3a44f0788..352c57d72 100644 --- a/pinos/client/node.h +++ b/pinos/server/node.h @@ -29,7 +29,8 @@ typedef struct _PinosNodeClass PinosNodeClass; typedef struct _PinosNodePrivate PinosNodePrivate; #include -#include +#include +#include #define PINOS_TYPE_NODE (pinos_node_get_type ()) #define PINOS_IS_NODE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), PINOS_TYPE_NODE)) @@ -54,55 +55,47 @@ struct _PinosNode { /** * PinosNodeClass: * @set_state: called to change the current state of the node - * @create_node: make a new port - * @remove_node: remove a port * * Pinos node class. */ struct _PinosNodeClass { GObjectClass parent_class; - gboolean (*set_state) (PinosNode *node, - PinosNodeState state); - - void (*create_port) (PinosNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props, - GTask *task); - void (*remove_port) (PinosNode *node, - PinosPort *port); + gboolean (*set_state) (PinosNode *node, + PinosNodeState state); + PinosPort * (*add_port) (PinosNode *node, + PinosDirection direction, + GError **error); + void (*remove_port) (PinosNode *node, + PinosPort *port); }; /* normal GObject stuff */ GType pinos_node_get_type (void); -const gchar * pinos_node_get_name (PinosNode *node); -PinosNodeState pinos_node_get_state (PinosNode *node); -PinosProperties * pinos_node_get_properties (PinosNode *node); - +PinosNode * pinos_node_new (PinosDaemon *daemon, + const gchar *sender, + const gchar *name, + PinosProperties *properties); void pinos_node_remove (PinosNode *node); -void pinos_node_create_port (PinosNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data); -PinosPort * pinos_node_create_port_finish (PinosNode *node, - GAsyncResult *res, - GError **error); -void pinos_node_add_port (PinosNode *node, - PinosPort *port); -void pinos_node_remove_port (PinosNode *node, - PinosPort *port); -GList * pinos_node_get_ports (PinosNode *node); +const gchar * pinos_node_get_name (PinosNode *node); +PinosProperties * pinos_node_get_properties (PinosNode *node); +PinosDaemon * pinos_node_get_daemon (PinosNode *node); +const gchar * pinos_node_get_sender (PinosNode *node); +const gchar * pinos_node_get_object_path (PinosNode *node); + +PinosPort * pinos_node_add_port (PinosNode *node, + PinosDirection direction, + GError **error); +void pinos_node_remove_port (PinosNode *node, + PinosPort *port); +GList * pinos_node_get_ports (PinosNode *node); + +PinosNodeState pinos_node_get_state (PinosNode *node); gboolean pinos_node_set_state (PinosNode *node, PinosNodeState state); void pinos_node_update_state (PinosNode *node, PinosNodeState state); diff --git a/pinos/client/port.c b/pinos/server/port.c similarity index 66% rename from pinos/client/port.c rename to pinos/server/port.c index 0ef6fd919..7474f15ca 100644 --- a/pinos/client/port.c +++ b/pinos/server/port.c @@ -17,21 +17,17 @@ * Boston, MA 02110-1301, USA. */ -#include #include +#include #include #include -#include -#include - #include "pinos/client/pinos.h" #include "pinos/client/enumtypes.h" -#include "pinos/client/private.h" -#include "pinos/client/port.h" -#include "pinos/client/node.h" +#include "pinos/server/port.h" +#include "pinos/server/node.h" #define PINOS_PORT_GET_PRIVATE(obj) \ (G_TYPE_INSTANCE_GET_PRIVATE ((obj), PINOS_TYPE_PORT, PinosPortPrivate)) @@ -43,27 +39,18 @@ #endif #define MAX_BUFFER_SIZE 1024 -#define MAX_FDS 16 +#define MAX_FDS 16 struct _PinosPortPrivate { - PinosNode *node; + PinosDaemon *daemon; - gchar *name; - GSocket *sockets[2]; + PinosNode *node; PinosDirection direction; GBytes *possible_formats; GBytes *format; PinosProperties *properties; - int fd; - GSource *socket_source; - - PinosBuffer recv_buffer; - - guint8 recv_data[MAX_BUFFER_SIZE]; - int recv_fds[MAX_FDS]; - guint8 send_data[MAX_BUFFER_SIZE]; int send_fds[MAX_FDS]; @@ -77,15 +64,14 @@ struct _PinosPortPrivate GDestroyNotify received_buffer_notify; }; -G_DEFINE_ABSTRACT_TYPE (PinosPort, pinos_port, G_TYPE_OBJECT); +G_DEFINE_TYPE (PinosPort, pinos_port, G_TYPE_OBJECT); enum { PROP_0, + PROP_DAEMON, PROP_NODE, - PROP_SOCKET, PROP_MAIN_CONTEXT, - PROP_NAME, PROP_DIRECTION, PROP_MAX_PEERS, PROP_PEERS, @@ -105,6 +91,7 @@ enum static guint signals[LAST_SIGNAL] = { 0 }; + void pinos_port_set_received_buffer_cb (PinosPort *port, PinosReceivedBufferCallback cb, @@ -125,6 +112,295 @@ pinos_port_set_received_buffer_cb (PinosPort *port, priv->received_buffer_notify = notify; } + +static void +pinos_port_get_property (GObject *_object, + guint prop_id, + GValue *value, + GParamSpec *pspec) +{ + PinosPort *port = PINOS_PORT (_object); + PinosPortPrivate *priv = port->priv; + + switch (prop_id) { + case PROP_DAEMON: + g_value_set_object (value, priv->daemon); + break; + + case PROP_NODE: + g_value_set_object (value, priv->node); + break; + + case PROP_MAX_PEERS: + g_value_set_uint (value, priv->max_peers); + break; + + case PROP_PEERS: + g_value_set_boxed (value, priv->peer_paths); + break; + + case PROP_DIRECTION: + g_value_set_enum (value, priv->direction); + break; + + case PROP_POSSIBLE_FORMATS: + g_value_set_boxed (value, priv->possible_formats); + break; + + case PROP_FORMAT: + g_value_set_boxed (value, priv->format); + break; + + case PROP_PROPERTIES: + g_value_set_boxed (value, priv->properties); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (port, prop_id, pspec); + break; + } +} + +static void +pinos_port_set_property (GObject *_object, + guint prop_id, + const GValue *value, + GParamSpec *pspec) +{ + PinosPort *port = PINOS_PORT (_object); + PinosPortPrivate *priv = port->priv; + + switch (prop_id) { + case PROP_DAEMON: + priv->daemon = g_value_dup_object (value); + break; + + case PROP_NODE: + priv->node = g_value_get_object (value); + break; + + case PROP_DIRECTION: + priv->direction = g_value_get_enum (value); + break; + + case PROP_MAX_PEERS: + priv->max_peers = g_value_get_uint (value); + break; + + case PROP_PEERS: + if (priv->peer_paths) + g_strfreev (priv->peer_paths); + priv->peer_paths = g_value_dup_boxed (value); + break; + + case PROP_POSSIBLE_FORMATS: + if (priv->possible_formats) + g_bytes_unref (priv->possible_formats); + priv->possible_formats = g_value_dup_boxed (value); + break; + + case PROP_FORMAT: + if (priv->format) + g_bytes_unref (priv->format); + priv->format = g_value_dup_boxed (value); + break; + + case PROP_PROPERTIES: + if (priv->properties) + pinos_properties_free (priv->properties); + priv->properties = g_value_dup_boxed (value); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (port, prop_id, pspec); + break; + } +} + +static void +pinos_port_constructed (GObject * object) +{ + PinosPort *port = PINOS_PORT (object); + + g_debug ("port %p: constructed", port); + + G_OBJECT_CLASS (pinos_port_parent_class)->constructed (object); +} + +static void +pinos_port_dispose (GObject * object) +{ + PinosPort *port = PINOS_PORT (object); + + g_debug ("port %p: dispose", port); + + G_OBJECT_CLASS (pinos_port_parent_class)->dispose (object); +} + +static void +pinos_port_finalize (GObject * object) +{ + PinosPort *port = PINOS_PORT (object); + PinosPortPrivate *priv = port->priv; + + g_debug ("port %p: finalize", port); + g_clear_pointer (&priv->possible_formats, g_bytes_unref); + g_clear_pointer (&priv->format, g_bytes_unref); + g_clear_pointer (&priv->properties, pinos_properties_free); + if (priv->received_buffer_notify) + priv->received_buffer_notify (priv->received_buffer_data); + g_ptr_array_unref (priv->peers); + g_clear_object (&priv->daemon); + + G_OBJECT_CLASS (pinos_port_parent_class)->finalize (object); +} + +static void +pinos_port_class_init (PinosPortClass * klass) +{ + GObjectClass *gobject_class = G_OBJECT_CLASS (klass); + //PinosPortClass *port_class = PINOS_PORT_CLASS (klass); + + g_type_class_add_private (klass, sizeof (PinosPortPrivate)); + + gobject_class->constructed = pinos_port_constructed; + gobject_class->dispose = pinos_port_dispose; + gobject_class->finalize = pinos_port_finalize; + gobject_class->set_property = pinos_port_set_property; + gobject_class->get_property = pinos_port_get_property; + + g_object_class_install_property (gobject_class, + PROP_DAEMON, + g_param_spec_object ("daemon", + "Daemon", + "The Daemon", + PINOS_TYPE_DAEMON, + G_PARAM_READWRITE | + G_PARAM_CONSTRUCT_ONLY | + G_PARAM_STATIC_STRINGS)); + g_object_class_install_property (gobject_class, + PROP_NODE, + g_param_spec_object ("node", + "Node", + "The Node", + PINOS_TYPE_NODE, + G_PARAM_READWRITE | + G_PARAM_CONSTRUCT_ONLY | + G_PARAM_STATIC_STRINGS)); + + g_object_class_install_property (gobject_class, + PROP_DIRECTION, + g_param_spec_enum ("direction", + "Direction", + "The direction of the port", + PINOS_TYPE_DIRECTION, + PINOS_DIRECTION_INVALID, + G_PARAM_READWRITE | + G_PARAM_CONSTRUCT_ONLY | + G_PARAM_STATIC_STRINGS)); + g_object_class_install_property (gobject_class, + PROP_MAX_PEERS, + g_param_spec_uint ("max-peers", + "Max Peers", + "The maximum number of peer ports", + 1, G_MAXUINT, G_MAXUINT, + G_PARAM_READWRITE | + G_PARAM_STATIC_STRINGS)); + + g_object_class_install_property (gobject_class, + PROP_PEERS, + g_param_spec_boxed ("peers", + "Peers", + "The peer ports of the port", + G_TYPE_STRV, + G_PARAM_READWRITE | + G_PARAM_STATIC_STRINGS)); + + g_object_class_install_property (gobject_class, + PROP_POSSIBLE_FORMATS, + g_param_spec_boxed ("possible-formats", + "Possible Formats", + "The possbile formats of the port", + G_TYPE_BYTES, + G_PARAM_READWRITE | + G_PARAM_CONSTRUCT | + G_PARAM_STATIC_STRINGS)); + + g_object_class_install_property (gobject_class, + PROP_FORMAT, + g_param_spec_boxed ("format", + "Format", + "The format of the port", + G_TYPE_BYTES, + G_PARAM_READWRITE | + G_PARAM_CONSTRUCT_ONLY | + G_PARAM_STATIC_STRINGS)); + + g_object_class_install_property (gobject_class, + PROP_PROPERTIES, + g_param_spec_boxed ("properties", + "Properties", + "The properties of the port", + PINOS_TYPE_PROPERTIES, + G_PARAM_READWRITE | + G_PARAM_CONSTRUCT_ONLY | + G_PARAM_STATIC_STRINGS)); + + + signals[SIGNAL_FORMAT_REQUEST] = g_signal_new ("format-request", + G_TYPE_FROM_CLASS (klass), + G_SIGNAL_RUN_LAST, + 0, + NULL, + NULL, + g_cclosure_marshal_generic, + G_TYPE_NONE, + 0, + G_TYPE_NONE); + + signals[SIGNAL_REMOVE] = g_signal_new ("remove", + G_TYPE_FROM_CLASS (klass), + G_SIGNAL_RUN_LAST, + 0, + NULL, + NULL, + g_cclosure_marshal_generic, + G_TYPE_NONE, + 0, + G_TYPE_NONE); + signals[SIGNAL_LINKED] = g_signal_new ("linked", + G_TYPE_FROM_CLASS (klass), + G_SIGNAL_RUN_LAST, + 0, + NULL, + NULL, + g_cclosure_marshal_generic, + G_TYPE_BOOLEAN, + 1, + PINOS_TYPE_PORT); + signals[SIGNAL_UNLINKED] = g_signal_new ("unlinked", + G_TYPE_FROM_CLASS (klass), + G_SIGNAL_RUN_LAST, + 0, + NULL, + NULL, + g_cclosure_marshal_generic, + G_TYPE_NONE, + 1, + PINOS_TYPE_PORT); + +} + +static void +pinos_port_init (PinosPort * port) +{ + PinosPortPrivate *priv = port->priv = PINOS_PORT_GET_PRIVATE (port); + + g_debug ("port %p: new", port); + priv->direction = PINOS_DIRECTION_INVALID; + priv->peers = g_ptr_array_new_full (64, NULL); +} + /** * pinos_port_remove: * @port: a #PinosPort @@ -159,44 +435,6 @@ pinos_port_get_node (PinosPort *port) return priv->node; } -/** - * pinos_port_get_socket: - * @port: a #PinosPort - * - * Get the socket of @port - * - * Returns: the socket or %NULL - */ -GSocket * -pinos_port_get_socket (PinosPort *port) -{ - PinosPortPrivate *priv; - - g_return_val_if_fail (PINOS_IS_PORT (port), NULL); - priv = port->priv; - - return priv->sockets[0]; -} - -/** - * pinos_port_get_name: - * @port: a #PinosPort - * - * Get the name of @port - * - * Returns: the name or %NULL - */ -const gchar * -pinos_port_get_name (PinosPort *port) -{ - PinosPortPrivate *priv; - - g_return_val_if_fail (PINOS_IS_PORT (port), NULL); - priv = port->priv; - - return priv->name; -} - /** * pinos_port_get_direction: * @port: a #PinosPort @@ -387,166 +625,12 @@ parse_control_buffer (PinosPort *port, PinosBuffer *buffer) } } -static PinosBuffer * -read_buffer (PinosPort *port, - GError **error) -{ - PinosPortPrivate *priv = port->priv; - gssize len; - PinosStackHeader *hdr; - PinosStackBuffer *sb = (PinosStackBuffer *) &priv->recv_buffer; - gsize need; - struct cmsghdr *cmsg; - struct msghdr msg = {0}; - struct iovec iov[1]; - char cmsgbuf[CMSG_SPACE (MAX_FDS * sizeof (int))]; - - g_assert (sb->refcount == 0); - - sb->data = priv->recv_data; - sb->max_size = MAX_BUFFER_SIZE; - sb->size = 0; - sb->free_data = NULL; - sb->fds = priv->recv_fds; - sb->max_fds = 0; - sb->n_fds = 0; - sb->free_fds = NULL; - - hdr = sb->data; - - /* read header and control messages first */ - iov[0].iov_base = hdr; - iov[0].iov_len = sizeof (PinosStackHeader);; - msg.msg_iov = iov; - msg.msg_iovlen = 1; - msg.msg_control = cmsgbuf; - msg.msg_controllen = sizeof (cmsgbuf); - msg.msg_flags = MSG_CMSG_CLOEXEC; - - while (TRUE) { - len = recvmsg (priv->fd, &msg, msg.msg_flags); - if (len < 0) { - if (errno == EINTR) - continue; - else - goto recv_error; - } - break; - } - g_assert (len == sizeof (PinosStackHeader)); - - /* now we know the total length */ - need = sizeof (PinosStackHeader) + hdr->length; - - if (sb->max_size < need) { - g_warning ("port %p: realloc receive memory %" G_GSIZE_FORMAT" -> %" G_GSIZE_FORMAT, port, sb->max_size, need); - sb->max_size = need; - hdr = sb->data = sb->free_data = g_realloc (sb->free_data, need); - } - sb->size = need; - - if (hdr->length > 0) { - /* read data */ - while (TRUE) { - len = recv (priv->fd, (gchar *)sb->data + sizeof (PinosStackHeader), hdr->length, 0); - if (len < 0) { - if (errno == EINTR) - continue; - else - goto recv_error; - } - break; - } - g_assert (len == hdr->length); - } - - /* handle control messages */ - for (cmsg = CMSG_FIRSTHDR (&msg); cmsg != NULL; cmsg = CMSG_NXTHDR (&msg, cmsg)) { - if (cmsg->cmsg_level != SOL_SOCKET || cmsg->cmsg_type != SCM_RIGHTS) - continue; - - sb->n_fds = (cmsg->cmsg_len - ((char *)CMSG_DATA (cmsg) - (char *)cmsg)) / sizeof (int); - memcpy (sb->fds, CMSG_DATA (cmsg), sb->n_fds * sizeof (int)); - } - sb->refcount = 1; - sb->magic = PSB_MAGIC; - - PINOS_DEBUG_TRANSPORT ("port %p: buffer %p init", &priv->recv_buffer, sb); - - return &priv->recv_buffer; - - /* ERRORS */ -recv_error: - { - g_set_error (error, - G_IO_ERROR, - g_io_error_from_errno (errno), - "could not recvmsg: %s", strerror (errno)); - return NULL; - } -} - - -static gboolean -write_buffer (PinosPort *port, - PinosBuffer *buffer, - GError **error) -{ - PinosPortPrivate *priv = port->priv; - PinosStackBuffer *sb = (PinosStackBuffer *) buffer; - gssize len; - struct msghdr msg = {0}; - struct iovec iov[1]; - struct cmsghdr *cmsg; - char cmsgbuf[CMSG_SPACE (MAX_FDS * sizeof (int))]; - gint fds_len = sb->n_fds * sizeof (int); - - iov[0].iov_base = sb->data; - iov[0].iov_len = sb->size; - msg.msg_iov = iov; - msg.msg_iovlen = 1; - msg.msg_control = cmsgbuf; - msg.msg_controllen = CMSG_SPACE (fds_len); - cmsg = CMSG_FIRSTHDR(&msg); - cmsg->cmsg_level = SOL_SOCKET; - cmsg->cmsg_type = SCM_RIGHTS; - cmsg->cmsg_len = CMSG_LEN (fds_len); - memcpy(CMSG_DATA(cmsg), sb->fds, fds_len); - msg.msg_controllen = cmsg->cmsg_len; - - while (TRUE) { - len = sendmsg (priv->fd, &msg, 0); - if (len < 0) { - if (errno == EINTR) - continue; - else - goto send_error; - } - break; - } - g_assert (len == (gssize) sb->size); - - return TRUE; - - /* ERRORS */ -send_error: - { - g_set_error (error, - G_IO_ERROR, - g_io_error_from_errno (errno), - "could not sendmsg: %s", strerror (errno)); - return FALSE; - } -} - - static gboolean pinos_port_receive_buffer (PinosPort *port, PinosBuffer *buffer, GError **error) { PinosPortPrivate *priv = port->priv; - gboolean res; if (priv->buffer) goto buffer_queued; @@ -555,19 +639,12 @@ pinos_port_receive_buffer (PinosPort *port, if (pinos_buffer_get_flags (buffer) & PINOS_BUFFER_FLAG_CONTROL) parse_control_buffer (port, buffer); - if (priv->sockets[0]) { - PINOS_DEBUG_TRANSPORT ("port %p: write buffer %p", port, buffer); - res = write_buffer (port, buffer, error); - } - else { - res = TRUE; - priv->buffer = buffer; - if (priv->received_buffer_cb) - priv->received_buffer_cb (port, priv->received_buffer_data); - priv->buffer = NULL; - } + priv->buffer = buffer; + if (priv->received_buffer_cb) + priv->received_buffer_cb (port, priv->received_buffer_data); + priv->buffer = NULL; - return res; + return TRUE; /* ERRORS */ buffer_queued: @@ -601,7 +678,6 @@ update_peer_paths (PinosPort *port) g_object_set (port, "peers", paths, NULL); g_strfreev (paths); } - /** * pinos_port_link: * @source: a source #PinosPort @@ -646,6 +722,7 @@ pinos_port_link (PinosPort *source, PinosPort *destination) update_peer_paths (source); update_peer_paths (destination); + if (source->priv->format) { PinosBufferBuilder builder; PinosBuffer pbuf; @@ -695,7 +772,6 @@ pinos_port_unlink (PinosPort *source, PinosPort *destination) return TRUE; } - static void pinos_port_unlink_all (PinosPort *port) { @@ -736,90 +812,6 @@ pinos_port_get_links (PinosPort *port, guint *n_links) return (PinosPort *) priv->peers->pdata; } - -static gboolean -on_socket_condition (GSocket *socket, - GIOCondition condition, - gpointer user_data) -{ - PinosPort *port = user_data; - PinosPortPrivate *priv = port->priv; - GError *error = NULL; - - switch (condition) { - case G_IO_IN: - { - guint i; - PinosBuffer *buffer; - - buffer = read_buffer (port, &error); - if (buffer == NULL) { - g_warning ("port %p: failed to read buffer: %s", port, error->message); - g_clear_error (&error); - return TRUE; - } - - if (pinos_buffer_get_flags (buffer) & PINOS_BUFFER_FLAG_CONTROL) - parse_control_buffer (port, buffer); - - PINOS_DEBUG_TRANSPORT ("port %p: read buffer %p", port, buffer); - - if (priv->received_buffer_cb) { - PINOS_DEBUG_TRANSPORT ("port %p: notify buffer %p", port, buffer); - priv->buffer = buffer; - priv->received_buffer_cb (port, priv->received_buffer_data); - priv->buffer = NULL; - } - PINOS_DEBUG_TRANSPORT ("port %p: send to peer buffer %p", port, buffer); - for (i = 0; i < priv->peers->len; i++) { - PinosPort *peer = g_ptr_array_index (priv->peers, i); - - if (!pinos_port_receive_buffer (peer, buffer, &error)) { - g_warning ("peer %p: failed to receive buffer: %s", peer, error->message); - g_clear_error (&error); - } - } - g_assert (pinos_buffer_unref (buffer) == FALSE); - break; - } - - case G_IO_OUT: - g_warning ("can do IO OUT\n"); - break; - - default: - break; - } - return TRUE; -} - - -static void -handle_socket (PinosPort *port, GSocket *socket) -{ - PinosPortPrivate *priv = port->priv; - GMainContext *context = g_main_context_get_thread_default(); - - g_debug ("port %p: handle socket in context %p", port, context); - priv->fd = g_socket_get_fd (socket); - priv->socket_source = g_socket_create_source (socket, G_IO_IN, NULL); - g_source_set_callback (priv->socket_source, (GSourceFunc) on_socket_condition, port, NULL); - g_source_attach (priv->socket_source, context); -} - -static void -unhandle_socket (PinosPort *port) -{ - PinosPortPrivate *priv = port->priv; - - g_debug ("port %p: unhandle socket", port); - if (priv->socket_source) { - g_source_destroy (priv->socket_source); - g_clear_pointer (&priv->socket_source, g_source_unref); - priv->fd = -1; - } -} - /** * pinos_port_peek_buffer: * @port: a #PinosPort @@ -881,10 +873,7 @@ pinos_port_send_buffer (PinosPort *port, parse_control_buffer (port, buffer); PINOS_DEBUG_TRANSPORT ("port %p: send buffer %p", port, buffer); - if (priv->sockets[0]) { - PINOS_DEBUG_TRANSPORT ("port %p: write buffer %p", port, buffer); - res = write_buffer (port, buffer, &err); - } + for (i = 0; i < priv->peers->len; i++) { peer = g_ptr_array_index (priv->peers, i); res = pinos_port_receive_buffer (peer, buffer, &err); @@ -897,401 +886,3 @@ pinos_port_send_buffer (PinosPort *port, return res; } - -/** - * pinos_port_get_socket_pair: - * @port: a #PinosPort - * @error: a #GError - * - * Create or return a previously create socket pair for @port. The - * Socket for the other end is returned. - * - * Returns: a #GSocket that can be used to send buffers to port. - */ -GSocket * -pinos_port_get_socket_pair (PinosPort *port, - GError **error) -{ - PinosPortPrivate *priv; - - g_return_val_if_fail (PINOS_IS_PORT (port), FALSE); - priv = port->priv; - - if (priv->sockets[1] == NULL) { - int fd[2]; - - if (socketpair (AF_UNIX, SOCK_STREAM, 0, fd) != 0) - goto no_sockets; - - priv->sockets[0] = g_socket_new_from_fd (fd[0], error); - if (priv->sockets[0] == NULL) - goto create_failed; - - priv->sockets[1] = g_socket_new_from_fd (fd[1], error); - if (priv->sockets[1] == NULL) - goto create_failed; - - handle_socket (port, priv->sockets[0]); - } - return g_object_ref (priv->sockets[1]); - - /* ERRORS */ -no_sockets: - { - g_set_error (error, - G_IO_ERROR, - g_io_error_from_errno (errno), - "could not create socketpair: %s", strerror (errno)); - return NULL; - } -create_failed: - { - g_clear_object (&priv->sockets[0]); - g_clear_object (&priv->sockets[1]); - return NULL; - } -} - -static void -pinos_port_get_property (GObject *_object, - guint prop_id, - GValue *value, - GParamSpec *pspec) -{ - PinosPort *port = PINOS_PORT (_object); - PinosPortPrivate *priv = port->priv; - - switch (prop_id) { - case PROP_NODE: - g_value_set_object (value, priv->node); - break; - - case PROP_SOCKET: - g_value_set_object (value, priv->sockets[0]); - break; - - case PROP_NAME: - g_value_set_string (value, priv->name); - break; - - case PROP_MAX_PEERS: - g_value_set_uint (value, priv->max_peers); - break; - - case PROP_PEERS: - g_value_set_boxed (value, priv->peer_paths); - break; - - case PROP_DIRECTION: - g_value_set_enum (value, priv->direction); - break; - - case PROP_POSSIBLE_FORMATS: - g_value_set_boxed (value, priv->possible_formats); - break; - - case PROP_FORMAT: - g_value_set_boxed (value, priv->format); - break; - - case PROP_PROPERTIES: - g_value_set_boxed (value, priv->properties); - break; - - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (port, prop_id, pspec); - break; - } -} - -static void -pinos_port_set_property (GObject *_object, - guint prop_id, - const GValue *value, - GParamSpec *pspec) -{ - PinosPort *port = PINOS_PORT (_object); - PinosPortPrivate *priv = port->priv; - - switch (prop_id) { - case PROP_NODE: - priv->node = g_value_get_object (value); - break; - - case PROP_SOCKET: - priv->sockets[0] = g_value_dup_object (value); - break; - - case PROP_NAME: - priv->name = g_value_dup_string (value); - break; - - case PROP_DIRECTION: - priv->direction = g_value_get_enum (value); - break; - - case PROP_MAX_PEERS: - priv->max_peers = g_value_get_uint (value); - break; - - case PROP_PEERS: - if (priv->peer_paths) - g_strfreev (priv->peer_paths); - priv->peer_paths = g_value_dup_boxed (value); - break; - - case PROP_POSSIBLE_FORMATS: - if (priv->possible_formats) - g_bytes_unref (priv->possible_formats); - priv->possible_formats = g_value_dup_boxed (value); - break; - - case PROP_FORMAT: - if (priv->format) - g_bytes_unref (priv->format); - priv->format = g_value_dup_boxed (value); - break; - - case PROP_PROPERTIES: - if (priv->properties) - pinos_properties_free (priv->properties); - priv->properties = g_value_dup_boxed (value); - break; - - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (port, prop_id, pspec); - break; - } -} - -static void -pinos_port_constructed (GObject * object) -{ - PinosPort *port = PINOS_PORT (object); - PinosPortPrivate *priv = port->priv; - - g_debug ("port %p: %s port constructed, node %p", - port, pinos_direction_as_string (priv->direction), priv->node); - - if (priv->sockets[0]) - handle_socket (port, priv->sockets[0]); - - if (priv->direction == PINOS_DIRECTION_OUTPUT) - priv->max_peers = G_MAXUINT; - else - priv->max_peers = 1; - - G_OBJECT_CLASS (pinos_port_parent_class)->constructed (object); -} - -static void -pinos_port_dispose (GObject * object) -{ - PinosPort *port = PINOS_PORT (object); - PinosPortPrivate *priv = port->priv; - - g_debug ("port %p: dispose", port); - if (priv->sockets[0]) { - unhandle_socket (port); - g_clear_object (&priv->sockets[0]); - } - g_clear_object (&priv->sockets[1]); - pinos_port_unlink_all (port); - - G_OBJECT_CLASS (pinos_port_parent_class)->dispose (object); -} - -static void -pinos_port_finalize (GObject * object) -{ - PinosPort *port = PINOS_PORT (object); - PinosPortPrivate *priv = port->priv; - - g_debug ("port %p: finalize", port); - - g_free (priv->name); - g_clear_pointer (&priv->possible_formats, g_bytes_unref); - g_clear_pointer (&priv->format, g_bytes_unref); - g_clear_pointer (&priv->properties, pinos_properties_free); - if (priv->received_buffer_notify) - priv->received_buffer_notify (priv->received_buffer_data); - g_ptr_array_unref (priv->peers); - - G_OBJECT_CLASS (pinos_port_parent_class)->finalize (object); -} - -static gboolean -signal_linked_handler (PinosPort *port, PinosPort *peer, gpointer user_data) -{ - return TRUE; -} - -static gboolean -signal_linked_accum (GSignalInvocationHint *ihint, - GValue *return_accu, - const GValue *handler_return, - gpointer data) -{ - if (!g_value_get_boolean (handler_return)) { - g_value_set_boolean (return_accu, FALSE); - return FALSE; - } - g_value_set_boolean (return_accu, TRUE); - return TRUE; -} - - -static void -pinos_port_class_init (PinosPortClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - - g_type_class_add_private (klass, sizeof (PinosPortPrivate)); - - gobject_class->constructed = pinos_port_constructed; - gobject_class->dispose = pinos_port_dispose; - gobject_class->finalize = pinos_port_finalize; - gobject_class->set_property = pinos_port_set_property; - gobject_class->get_property = pinos_port_get_property; - - g_object_class_install_property (gobject_class, - PROP_NODE, - g_param_spec_object ("node", - "Node", - "The Node", - PINOS_TYPE_NODE, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_SOCKET, - g_param_spec_object ("socket", - "Socket", - "The socket for this port", - G_TYPE_SOCKET, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_NAME, - g_param_spec_string ("name", - "Name", - "The port name", - NULL, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_DIRECTION, - g_param_spec_enum ("direction", - "Direction", - "The direction of the port", - PINOS_TYPE_DIRECTION, - PINOS_DIRECTION_INVALID, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_MAX_PEERS, - g_param_spec_uint ("max-peers", - "Max Peers", - "The maximum number of peer ports", - 1, G_MAXUINT, G_MAXUINT, - G_PARAM_READWRITE | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_PEERS, - g_param_spec_boxed ("peers", - "Peers", - "The peer ports of the port", - G_TYPE_STRV, - G_PARAM_READWRITE | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_POSSIBLE_FORMATS, - g_param_spec_boxed ("possible-formats", - "Possible Formats", - "The possbile formats of the port", - G_TYPE_BYTES, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_FORMAT, - g_param_spec_boxed ("format", - "Format", - "The format of the port", - G_TYPE_BYTES, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_PROPERTIES, - g_param_spec_boxed ("properties", - "Properties", - "The properties of the port", - PINOS_TYPE_PROPERTIES, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - - - signals[SIGNAL_FORMAT_REQUEST] = g_signal_new ("format-request", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - 0, - NULL, - NULL, - g_cclosure_marshal_generic, - G_TYPE_NONE, - 0, - G_TYPE_NONE); - - signals[SIGNAL_REMOVE] = g_signal_new ("remove", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - 0, - NULL, - NULL, - g_cclosure_marshal_generic, - G_TYPE_NONE, - 0, - G_TYPE_NONE); - signals[SIGNAL_LINKED] = g_signal_new_class_handler ("linked", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - (GCallback) signal_linked_handler, - signal_linked_accum, - NULL, - g_cclosure_marshal_generic, - G_TYPE_BOOLEAN, - 1, - PINOS_TYPE_PORT); - signals[SIGNAL_UNLINKED] = g_signal_new ("unlinked", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - 0, - NULL, - NULL, - g_cclosure_marshal_generic, - G_TYPE_NONE, - 1, - PINOS_TYPE_PORT); -} - -static void -pinos_port_init (PinosPort * port) -{ - PinosPortPrivate *priv = port->priv = PINOS_PORT_GET_PRIVATE (port); - - priv->direction = PINOS_DIRECTION_INVALID; - priv->peers = g_ptr_array_new_full (64, NULL); -} diff --git a/pinos/client/port.h b/pinos/server/port.h similarity index 84% rename from pinos/client/port.h rename to pinos/server/port.h index a7605a4f3..9fbc2f4b6 100644 --- a/pinos/client/port.h +++ b/pinos/server/port.h @@ -30,15 +30,16 @@ typedef struct _PinosPortPrivate PinosPortPrivate; #include #include +#include -#define PINOS_TYPE_PORT (pinos_port_get_type ()) -#define PINOS_IS_PORT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), PINOS_TYPE_PORT)) -#define PINOS_IS_PORT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), PINOS_TYPE_PORT)) -#define PINOS_PORT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), PINOS_TYPE_PORT, PinosPortClass)) -#define PINOS_PORT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), PINOS_TYPE_PORT, PinosPort)) -#define PINOS_PORT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), PINOS_TYPE_PORT, PinosPortClass)) -#define PINOS_PORT_CAST(obj) ((PinosPort*)(obj)) -#define PINOS_PORT_CLASS_CAST(klass) ((PinosPortClass*)(klass)) +#define PINOS_TYPE_PORT (pinos_port_get_type ()) +#define PINOS_IS_PORT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), PINOS_TYPE_PORT)) +#define PINOS_IS_PORT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), PINOS_TYPE_PORT)) +#define PINOS_PORT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), PINOS_TYPE_PORT, PinosPortClass)) +#define PINOS_PORT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), PINOS_TYPE_PORT, PinosPort)) +#define PINOS_PORT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), PINOS_TYPE_PORT, PinosPortClass)) +#define PINOS_PORT_CAST(obj) ((PinosPort*)(obj)) +#define PINOS_PORT_CLASS_CAST(klass)((PinosPortClass*)(klass)) /** * PinosPort: @@ -62,7 +63,6 @@ struct _PinosPortClass { typedef void (*PinosReceivedBufferCallback) (PinosPort *port, gpointer user_data); - /* normal GObject stuff */ GType pinos_port_get_type (void); diff --git a/pinos/server/server-node.c b/pinos/server/server-node.c deleted file mode 100644 index 77b908757..000000000 --- a/pinos/server/server-node.c +++ /dev/null @@ -1,627 +0,0 @@ -/* Pinos - * Copyright (C) 2015 Wim Taymans - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, - * Boston, MA 02110-1301, USA. - */ - -#include -#include - -#include -#include - -#include "pinos/client/pinos.h" -#include "pinos/client/enumtypes.h" - -#include "pinos/server/server-node.h" -#include "pinos/server/daemon.h" - -#include "pinos/dbus/org-pinos.h" - - -#define PINOS_SERVER_NODE_GET_PRIVATE(node) \ - (G_TYPE_INSTANCE_GET_PRIVATE ((node), PINOS_TYPE_SERVER_NODE, PinosServerNodePrivate)) - -struct _PinosServerNodePrivate -{ - PinosDaemon *daemon; - PinosNode1 *iface; - - gchar *sender; - gchar *object_path; -}; - -G_DEFINE_TYPE (PinosServerNode, pinos_server_node, PINOS_TYPE_NODE); - -enum -{ - PROP_0, - PROP_DAEMON, - PROP_SENDER, - PROP_OBJECT_PATH, -}; - -static gboolean -server_node_set_state (PinosNode *node, - PinosNodeState state) -{ - return FALSE; -} - -static PinosServerPort * -server_node_create_port_sync (PinosServerNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props) -{ - PinosServerNodePrivate *priv = node->priv; - PinosServerPort *port; - - port = g_object_new (PINOS_TYPE_SERVER_PORT, - "daemon", priv->daemon, - "node", node, - "direction", direction, - "name", name, - "possible-formats", possible_formats, - "properties", props, - NULL); - pinos_node_add_port (PINOS_NODE (node), PINOS_PORT (port)); - - return port; -} - -static void -server_node_create_port (PinosNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props, - GTask *task) - { - PinosServerPort *port; - - port = pinos_server_node_create_port_sync (PINOS_SERVER_NODE (node), - direction, - name, - possible_formats, - props); - - g_task_return_pointer (task, port, (GDestroyNotify) g_object_unref); - g_object_unref (task); -} - -static void -server_node_remove_port (PinosNode *node, - PinosPort *port) -{ -} - -static void -remove_port (PinosPort *port) -{ - guint n_links; - - pinos_port_get_links (port, &n_links); - if (n_links == 0) { - pinos_port_remove (port); - } - g_object_unref (port); -} - -static void -on_port_created (GObject *source_object, - GAsyncResult *res, - gpointer user_data) -{ - PinosNode *node = PINOS_NODE (source_object); - PinosServerNodePrivate *priv = PINOS_SERVER_NODE (node)->priv; - GDBusMethodInvocation *invocation = user_data; - PinosPort *port, *peer; - const gchar *object_path, *val; - GError *error = NULL; - GUnixFDList *fdlist; - GSocket *socket; - int fd, fdidx; - PinosDirection direction; - PinosProperties *props; - gboolean autoconnect = FALSE; - - port = pinos_node_create_port_finish (node, res, &error); - if (port == NULL) - goto no_port; - - g_debug ("server-node %p: port %p created", node, port); - - socket = pinos_port_get_socket_pair (port, &error); - if (socket == NULL) - goto no_sockets; - - fd = g_socket_get_fd (socket); - fdlist = g_unix_fd_list_new (); - fdidx = g_unix_fd_list_append (fdlist, fd, &error); - g_object_unref (socket); - - if (fdidx == -1) - goto no_fdlist; - - props = pinos_port_get_properties (port); - - if ((val = pinos_properties_get (props, "autoconnect"))) { - autoconnect = atoi (val); - } else - autoconnect = TRUE; - - if (autoconnect) { - direction = pinos_port_get_direction (port); - direction = pinos_direction_reverse (direction); - - val = pinos_properties_get (props, "target-path"); - - peer = pinos_daemon_find_port (priv->daemon, - direction, - val, - pinos_port_get_properties (port), - pinos_port_get_possible_formats (port), - &error); - if (peer == NULL) - goto no_port_found; - - if (!pinos_port_link (port, peer)) - goto link_failed; - - g_object_set_data_full (G_OBJECT (port), - "autoconnect-peer-port", - peer, - (GDestroyNotify) remove_port); - } - - object_path = pinos_server_port_get_object_path (PINOS_SERVER_PORT (port)); - g_debug ("server-node %p: add port %p, remote fd %d, %s", node, port, fd, object_path); - g_dbus_method_invocation_return_value_with_unix_fd_list (invocation, - g_variant_new ("(oh)", - object_path, - fdidx), - fdlist); - - return; - -no_port: - { - g_debug ("server-node %p: could create port", node); - g_dbus_method_invocation_return_dbus_error (invocation, - "org.pinos.Error", "can't create port"); - return; - } -no_sockets: - { - g_debug ("server-node %p: could create socketpair %s", node, error->message); - g_dbus_method_invocation_return_gerror (invocation, error); - g_clear_error (&error); - g_object_unref (port); - return; - } -no_fdlist: - { - g_debug ("server-node %p: could add to fdlist", node); - g_dbus_method_invocation_return_gerror (invocation, error); - g_clear_error (&error); - g_object_unref (fdlist); - g_object_unref (port); - return; - } -no_port_found: - { - g_debug ("server-node %p: could not find matching port", node); - g_dbus_method_invocation_return_gerror (invocation, error); - g_clear_error (&error); - g_object_unref (fdlist); - return; - } -link_failed: - { - g_debug ("server-node %p: could not link port", node); - g_dbus_method_invocation_return_dbus_error (invocation, - "org.pinos.Error", "can't link port"); - g_object_unref (peer); - g_object_unref (fdlist); - return; - } -} - - -static gboolean -handle_create_port (PinosNode1 *interface, - GDBusMethodInvocation *invocation, - PinosDirection arg_direction, - const gchar *arg_name, - GVariant *arg_properties, - const gchar *arg_possible_formats, - gpointer user_data) -{ - PinosNode *node = user_data; - PinosServerNodePrivate *priv = PINOS_SERVER_NODE (node)->priv; - const gchar *sender; - PinosProperties *props; - GBytes *formats; - - sender = g_dbus_method_invocation_get_sender (invocation); - if (g_strcmp0 (priv->sender, sender) != 0) - goto not_allowed; - - formats = g_bytes_new (arg_possible_formats, strlen (arg_possible_formats) + 1); - props = pinos_properties_from_variant (arg_properties); - - g_debug ("server-node %p: create port", node); - pinos_node_create_port (node, - arg_direction, - arg_name, - formats, - props, - NULL, - on_port_created, - invocation); - - g_bytes_unref (formats); - pinos_properties_free (props); - - return TRUE; - - /* ERRORS */ -not_allowed: - { - g_debug ("sender %s is not owner of node with sender %s", sender, priv->sender); - g_dbus_method_invocation_return_dbus_error (invocation, - "org.pinos.Error", "not node owner"); - return TRUE; - } -} - -static gboolean -handle_remove (PinosNode1 *interface, - GDBusMethodInvocation *invocation, - gpointer user_data) -{ - PinosNode *node = user_data; - - g_debug ("server-node %p: remove", node); - pinos_node_remove (node); - - g_dbus_method_invocation_return_value (invocation, - g_variant_new ("()")); - return TRUE; -} - -static void -pinos_server_node_get_property (GObject *_object, - guint prop_id, - GValue *value, - GParamSpec *pspec) -{ - PinosServerNode *node = PINOS_SERVER_NODE (_object); - PinosServerNodePrivate *priv = node->priv; - - switch (prop_id) { - case PROP_DAEMON: - g_value_set_object (value, priv->daemon); - break; - - case PROP_SENDER: - g_value_set_string (value, priv->sender); - break; - - case PROP_OBJECT_PATH: - g_value_set_string (value, priv->object_path); - break; - - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (node, prop_id, pspec); - break; - } -} - -static void -pinos_server_node_set_property (GObject *_object, - guint prop_id, - const GValue *value, - GParamSpec *pspec) -{ - PinosServerNode *node = PINOS_SERVER_NODE (_object); - PinosServerNodePrivate *priv = node->priv; - - switch (prop_id) { - case PROP_DAEMON: - priv->daemon = g_value_dup_object (value); - break; - - case PROP_SENDER: - priv->sender = g_value_dup_string (value); - break; - - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (node, prop_id, pspec); - break; - } -} - -static void -node_register_object (PinosServerNode *node) -{ - PinosServerNodePrivate *priv = node->priv; - PinosDaemon *daemon = priv->daemon; - PinosObjectSkeleton *skel; - - skel = pinos_object_skeleton_new (PINOS_DBUS_OBJECT_NODE); - - pinos_object_skeleton_set_node1 (skel, priv->iface); - - g_free (priv->object_path); - priv->object_path = pinos_daemon_export_uniquely (daemon, G_DBUS_OBJECT_SKELETON (skel)); - g_object_unref (skel); - - g_debug ("server-node %p: register object %s", node, priv->object_path); - pinos_daemon_add_node (daemon, node); - - return; -} - -static void -node_unregister_object (PinosServerNode *node) -{ - PinosServerNodePrivate *priv = node->priv; - - g_debug ("server-node %p: unregister object %s", node, priv->object_path); - pinos_daemon_unexport (priv->daemon, priv->object_path); - pinos_daemon_remove_node (priv->daemon, node); -} - -static void -on_property_notify (GObject *obj, - GParamSpec *pspec, - gpointer user_data) -{ - PinosNode *node = user_data; - PinosServerNodePrivate *priv = PINOS_SERVER_NODE (node)->priv; - - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "sender") == 0) { - pinos_node1_set_owner (priv->iface, priv->sender); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "name") == 0) { - pinos_node1_set_name (priv->iface, pinos_node_get_name (node)); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "properties") == 0) { - PinosProperties *props = pinos_node_get_properties (node); - pinos_node1_set_properties (priv->iface, props ? pinos_properties_to_variant (props) : NULL); - } -} - -static void -pinos_server_node_constructed (GObject * obj) -{ - PinosServerNode *node = PINOS_SERVER_NODE (obj); - PinosServerNodePrivate *priv = node->priv; - - g_debug ("server-node %p: constructed", node); - - g_signal_connect (node, "notify", (GCallback) on_property_notify, node); - G_OBJECT_CLASS (pinos_server_node_parent_class)->constructed (obj); - - if (priv->sender == NULL) { - priv->sender = g_strdup (pinos_daemon_get_sender (priv->daemon)); - pinos_node1_set_owner (priv->iface, priv->sender); - } - - node_register_object (node); -} - -static void -pinos_server_node_dispose (GObject * obj) -{ - PinosServerNode *node = PINOS_SERVER_NODE (obj); - - g_debug ("server-node %p: dispose", node); - node_unregister_object (node); - - G_OBJECT_CLASS (pinos_server_node_parent_class)->dispose (obj); -} - -static void -pinos_server_node_finalize (GObject * obj) -{ - PinosServerNode *node = PINOS_SERVER_NODE (obj); - PinosServerNodePrivate *priv = node->priv; - - g_debug ("server-node %p: finalize", node); - g_clear_object (&priv->daemon); - g_clear_object (&priv->iface); - g_free (priv->sender); - - G_OBJECT_CLASS (pinos_server_node_parent_class)->finalize (obj); -} - -static void -pinos_server_node_class_init (PinosServerNodeClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - PinosNodeClass *node_class = PINOS_NODE_CLASS (klass); - - g_type_class_add_private (klass, sizeof (PinosServerNodePrivate)); - - gobject_class->constructed = pinos_server_node_constructed; - gobject_class->dispose = pinos_server_node_dispose; - gobject_class->finalize = pinos_server_node_finalize; - gobject_class->set_property = pinos_server_node_set_property; - gobject_class->get_property = pinos_server_node_get_property; - - g_object_class_install_property (gobject_class, - PROP_DAEMON, - g_param_spec_object ("daemon", - "Daemon", - "The Daemon", - PINOS_TYPE_DAEMON, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_SENDER, - g_param_spec_string ("sender", - "Sender", - "The Sender", - NULL, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - - g_object_class_install_property (gobject_class, - PROP_OBJECT_PATH, - g_param_spec_string ("object-path", - "Object Path", - "The object path", - NULL, - G_PARAM_READABLE | - G_PARAM_STATIC_STRINGS)); - node_class->set_state = server_node_set_state; - node_class->create_port = server_node_create_port; - node_class->remove_port = server_node_remove_port; - - klass->create_port_sync = server_node_create_port_sync; -} - -static void -pinos_server_node_init (PinosServerNode * node) -{ - PinosServerNodePrivate *priv = node->priv = PINOS_SERVER_NODE_GET_PRIVATE (node); - - g_debug ("server-node %p: new", node); - priv->iface = pinos_node1_skeleton_new (); - g_signal_connect (priv->iface, "handle-create-port", - (GCallback) handle_create_port, - node); - g_signal_connect (priv->iface, "handle-remove", - (GCallback) handle_remove, - node); - pinos_node1_set_state (priv->iface, PINOS_NODE_STATE_SUSPENDED); -} - -/** - * pinos_server_node_new: - * @daemon: a #PinosDaemon - * @sender: the path of the owner - * @name: a name - * @properties: extra properties - * - * Create a new #PinosServerNode. - * - * Returns: a new #PinosServerNode - */ -PinosNode * -pinos_server_node_new (PinosDaemon *daemon, - const gchar *sender, - const gchar *name, - PinosProperties *properties) -{ - g_return_val_if_fail (PINOS_IS_DAEMON (daemon), NULL); - - return g_object_new (PINOS_TYPE_SERVER_NODE, - "daemon", daemon, - "sender", sender, - "name", name, - "properties", properties, - NULL); -} - -/** - * pinos_server_node_get_daemon: - * @node: a #PinosServerNode - * - * Get the daemon of @node. - * - * Returns: the daemon of @node. - */ -PinosDaemon * -pinos_server_node_get_daemon (PinosServerNode *node) -{ - PinosServerNodePrivate *priv; - - g_return_val_if_fail (PINOS_IS_SERVER_NODE (node), NULL); - priv = node->priv; - - return priv->daemon; -} - -/** - * pinos_server_node_get_sender: - * @node: a #PinosServerNode - * - * Get the owner path of @node. - * - * Returns: the owner path of @node. - */ -const gchar * -pinos_server_node_get_sender (PinosServerNode *node) -{ - PinosServerNodePrivate *priv; - - g_return_val_if_fail (PINOS_IS_SERVER_NODE (node), NULL); - priv = node->priv; - - return priv->sender; -} -/** - * pinos_server_node_get_object_path: - * @node: a #PinosServerNode - * - * Get the object path of @node. - * - * Returns: the object path of @node. - */ -const gchar * -pinos_server_node_get_object_path (PinosServerNode *node) -{ - PinosServerNodePrivate *priv; - - g_return_val_if_fail (PINOS_IS_SERVER_NODE (node), NULL); - priv = node->priv; - - return priv->object_path; -} - -PinosServerPort * -pinos_server_node_create_port_sync (PinosServerNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props) -{ - PinosServerNodeClass *klass; - PinosServerPort *port; - - g_return_val_if_fail (PINOS_IS_SERVER_NODE (node), NULL); - - klass = PINOS_SERVER_NODE_GET_CLASS (node); - if (!klass->create_port_sync) - return NULL; - - g_debug ("server-node %p: create port", node); - port = klass->create_port_sync (node, - direction, - name, - possible_formats, - props); - - return port; -} diff --git a/pinos/server/server-node.h b/pinos/server/server-node.h deleted file mode 100644 index 75acf1850..000000000 --- a/pinos/server/server-node.h +++ /dev/null @@ -1,91 +0,0 @@ -/* Pinos - * Copyright (C) 2015 Wim Taymans - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, - * Boston, MA 02110-1301, USA. - */ - -#ifndef __PINOS_SERVER_NODE_H__ -#define __PINOS_SERVER_NODE_H__ - -#include - -G_BEGIN_DECLS - -typedef struct _PinosServerNode PinosServerNode; -typedef struct _PinosServerNodeClass PinosServerNodeClass; -typedef struct _PinosServerNodePrivate PinosServerNodePrivate; - -#include -#include -#include - -#define PINOS_TYPE_SERVER_NODE (pinos_server_node_get_type ()) -#define PINOS_IS_SERVER_NODE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), PINOS_TYPE_SERVER_NODE)) -#define PINOS_IS_SERVER_NODE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), PINOS_TYPE_SERVER_NODE)) -#define PINOS_SERVER_NODE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), PINOS_TYPE_SERVER_NODE, PinosServerNodeClass)) -#define PINOS_SERVER_NODE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), PINOS_TYPE_SERVER_NODE, PinosServerNode)) -#define PINOS_SERVER_NODE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), PINOS_TYPE_SERVER_NODE, PinosServerNodeClass)) -#define PINOS_SERVER_NODE_CAST(obj) ((PinosServerNode*)(obj)) -#define PINOS_SERVER_NODE_CLASS_CAST(klass) ((PinosServerNodeClass*)(klass)) - -/** - * PinosServerServerNode: - * - * Pinos node class. - */ -struct _PinosServerNode { - PinosNode object; - - PinosServerNodePrivate *priv; -}; - -/** - * PinosServerNodeClass: - * @set_state: called to change the current state of the node - * - * Pinos node class. - */ -struct _PinosServerNodeClass { - PinosNodeClass parent_class; - - PinosServerPort * (*create_port_sync) (PinosServerNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props); -}; - -/* normal GObject stuff */ -GType pinos_server_node_get_type (void); - -PinosNode * pinos_server_node_new (PinosDaemon *daemon, - const gchar *sender, - const gchar *name, - PinosProperties *properties); - -PinosDaemon * pinos_server_node_get_daemon (PinosServerNode *node); -const gchar * pinos_server_node_get_sender (PinosServerNode *node); -const gchar * pinos_server_node_get_object_path (PinosServerNode *node); - -PinosServerPort * pinos_server_node_create_port_sync (PinosServerNode *node, - PinosDirection direction, - const gchar *name, - GBytes *possible_formats, - PinosProperties *props); - -G_END_DECLS - -#endif /* __PINOS_SERVER_NODE_H__ */ diff --git a/pinos/server/server-port.c b/pinos/server/server-port.c deleted file mode 100644 index 1835e4bcb..000000000 --- a/pinos/server/server-port.c +++ /dev/null @@ -1,278 +0,0 @@ -/* Pinos - * Copyright (C) 2015 Wim Taymans - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, - * Boston, MA 02110-1301, USA. - */ - -#include -#include - - -#include -#include - -#include "pinos/client/pinos.h" -#include "pinos/client/enumtypes.h" - -#include "pinos/server/server-port.h" -#include "pinos/server/server-node.h" - -#include "pinos/dbus/org-pinos.h" - -#define PINOS_SERVER_PORT_GET_PRIVATE(obj) \ - (G_TYPE_INSTANCE_GET_PRIVATE ((obj), PINOS_TYPE_SERVER_PORT, PinosServerPortPrivate)) - -struct _PinosServerPortPrivate -{ - PinosDaemon *daemon; - PinosPort1 *iface; - gchar *object_path; - gboolean have_sockets; -}; - -G_DEFINE_TYPE (PinosServerPort, pinos_server_port, PINOS_TYPE_PORT); - -enum -{ - PROP_0, - PROP_DAEMON, - PROP_OBJECT_PATH, -}; - -const gchar * -pinos_server_port_get_object_path (PinosServerPort *port) -{ - PinosServerPortPrivate *priv; - - g_return_val_if_fail (PINOS_IS_SERVER_PORT (port), NULL); - priv = port->priv; - - return priv->object_path; -} - -static gboolean -handle_remove (PinosPort1 *interface, - GDBusMethodInvocation *invocation, - gpointer user_data) -{ - PinosPort *port = user_data; - - g_debug ("server-port %p: remove", port); - pinos_port_remove (port); - - g_dbus_method_invocation_return_value (invocation, - g_variant_new ("()")); - return TRUE; -} - -static void -pinos_server_port_get_property (GObject *_object, - guint prop_id, - GValue *value, - GParamSpec *pspec) -{ - PinosServerPort *port = PINOS_SERVER_PORT (_object); - PinosServerPortPrivate *priv = port->priv; - - switch (prop_id) { - case PROP_DAEMON: - g_value_set_object (value, priv->daemon); - break; - - case PROP_OBJECT_PATH: - g_value_set_string (value, priv->object_path); - break; - - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (port, prop_id, pspec); - break; - } -} - -static void -pinos_server_port_set_property (GObject *_object, - guint prop_id, - const GValue *value, - GParamSpec *pspec) -{ - PinosServerPort *port = PINOS_SERVER_PORT (_object); - PinosServerPortPrivate *priv = port->priv; - - switch (prop_id) { - case PROP_DAEMON: - priv->daemon = g_value_dup_object (value); - break; - - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (port, prop_id, pspec); - break; - } -} - -static void -port_register_object (PinosServerPort *port) -{ - PinosServerPortPrivate *priv = port->priv; - PinosObjectSkeleton *skel; - gchar *name; - PinosNode *node; - - node = pinos_port_get_node (PINOS_PORT (port)); - - name = g_strdup_printf ("%s/port", pinos_server_node_get_object_path (PINOS_SERVER_NODE (node))); - skel = pinos_object_skeleton_new (name); - g_free (name); - - pinos_object_skeleton_set_port1 (skel, priv->iface); - - g_free (priv->object_path); - priv->object_path = pinos_daemon_export_uniquely (priv->daemon, - G_DBUS_OBJECT_SKELETON (skel)); - g_object_unref (skel); - g_debug ("server-port %p: register object %s", port, priv->object_path); - - return; -} - -static void -port_unregister_object (PinosServerPort *port) -{ - PinosServerPortPrivate *priv = port->priv; - - g_debug ("server-port %p: unregister object %s", port, priv->object_path); - pinos_daemon_unexport (priv->daemon, priv->object_path); -} - -static void -on_property_notify (GObject *obj, - GParamSpec *pspec, - gpointer user_data) -{ - PinosPort *port = PINOS_PORT (obj); - PinosServerPortPrivate *priv = PINOS_SERVER_PORT (port)->priv; - - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "node") == 0) { - PinosServerNode *node = PINOS_SERVER_NODE (pinos_port_get_node (port)); - pinos_port1_set_node (priv->iface, pinos_server_node_get_object_path (node)); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "direction") == 0) { - pinos_port1_set_direction (priv->iface, pinos_port_get_direction (port)); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "name") == 0) { - pinos_port1_set_name (priv->iface, pinos_port_get_name (port)); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "properties") == 0) { - PinosProperties *props = pinos_port_get_properties (port); - pinos_port1_set_properties (priv->iface, props ? pinos_properties_to_variant (props) : NULL); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "possible-formats") == 0) { - GBytes *bytes = pinos_port_get_possible_formats (port); - pinos_port1_set_possible_formats (priv->iface, bytes ? g_bytes_get_data (bytes, NULL) : NULL); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "format") == 0) { - GBytes *bytes = pinos_port_get_format (port); - pinos_port1_set_format (priv->iface, bytes ? g_bytes_get_data (bytes, NULL) : NULL); - } - if (pspec == NULL || strcmp (g_param_spec_get_name (pspec), "peers") == 0) { - const gchar *const *paths; - g_object_get (port, "peers", &paths, NULL); - pinos_port1_set_peers (priv->iface, paths); - } -} - -static void -pinos_server_port_constructed (GObject * object) -{ - PinosServerPort *port = PINOS_SERVER_PORT (object); - - g_debug ("server-port %p: constructed", port); - - g_signal_connect (port, "notify", (GCallback) on_property_notify, port); - G_OBJECT_CLASS (pinos_server_port_parent_class)->constructed (object); - - port_register_object (port); -} - -static void -pinos_server_port_dispose (GObject * object) -{ - PinosServerPort *port = PINOS_SERVER_PORT (object); - - g_debug ("server-port %p: dispose", port); - port_unregister_object (port); - - G_OBJECT_CLASS (pinos_server_port_parent_class)->dispose (object); -} - -static void -pinos_server_port_finalize (GObject * object) -{ - PinosServerPort *port = PINOS_SERVER_PORT (object); - PinosServerPortPrivate *priv = port->priv; - - g_debug ("server-port %p: finalize", port); - g_free (priv->object_path); - g_clear_object (&priv->iface); - g_clear_object (&priv->daemon); - - G_OBJECT_CLASS (pinos_server_port_parent_class)->finalize (object); -} - -static void -pinos_server_port_class_init (PinosServerPortClass * klass) -{ - GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - //PinosPortClass *port_class = PINOS_PORT_CLASS (klass); - - g_type_class_add_private (klass, sizeof (PinosServerPortPrivate)); - - gobject_class->constructed = pinos_server_port_constructed; - gobject_class->dispose = pinos_server_port_dispose; - gobject_class->finalize = pinos_server_port_finalize; - gobject_class->set_property = pinos_server_port_set_property; - gobject_class->get_property = pinos_server_port_get_property; - - g_object_class_install_property (gobject_class, - PROP_DAEMON, - g_param_spec_object ("daemon", - "Daemon", - "The Daemon", - PINOS_TYPE_DAEMON, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY | - G_PARAM_STATIC_STRINGS)); - g_object_class_install_property (gobject_class, - PROP_OBJECT_PATH, - g_param_spec_string ("object-path", - "Object Path", - "The object path", - NULL, - G_PARAM_READABLE | - G_PARAM_STATIC_STRINGS)); -} - -static void -pinos_server_port_init (PinosServerPort * port) -{ - PinosServerPortPrivate *priv = port->priv = PINOS_SERVER_PORT_GET_PRIVATE (port); - - g_debug ("server-port %p: new", port); - priv->iface = pinos_port1_skeleton_new (); - g_signal_connect (priv->iface, "handle-remove", - (GCallback) handle_remove, - port); - -} diff --git a/pinos/server/server-port.h b/pinos/server/server-port.h deleted file mode 100644 index e1bed7052..000000000 --- a/pinos/server/server-port.h +++ /dev/null @@ -1,71 +0,0 @@ -/* Pinos - * Copyright (C) 2015 Wim Taymans - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, - * Boston, MA 02110-1301, USA. - */ - -#ifndef __PINOS_SERVER_PORT_H__ -#define __PINOS_SERVER_PORT_H__ - -#include - -G_BEGIN_DECLS - -typedef struct _PinosServerPort PinosServerPort; -typedef struct _PinosServerPortClass PinosServerPortClass; -typedef struct _PinosServerPortPrivate PinosServerPortPrivate; - -#include -#include -#include - -#define PINOS_TYPE_SERVER_PORT (pinos_server_port_get_type ()) -#define PINOS_IS_SERVER_PORT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), PINOS_TYPE_SERVER_PORT)) -#define PINOS_IS_SERVER_PORT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), PINOS_TYPE_SERVER_PORT)) -#define PINOS_SERVER_PORT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), PINOS_TYPE_SERVER_PORT, PinosServerPortClass)) -#define PINOS_SERVER_PORT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), PINOS_TYPE_SERVER_PORT, PinosServerPort)) -#define PINOS_SERVER_PORT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), PINOS_TYPE_SERVER_PORT, PinosServerPortClass)) -#define PINOS_SERVER_PORT_CAST(obj) ((PinosServerPort*)(obj)) -#define PINOS_SERVER_PORT_CLASS_CAST(klass)((PinosServerPortClass*)(klass)) - -/** - * PinosServerPort: - * - * Pinos port object class. - */ -struct _PinosServerPort { - PinosPort object; - - PinosServerPortPrivate *priv; -}; - -/** - * PinosServerPortClass: - * - * Pinos port object class. - */ -struct _PinosServerPortClass { - PinosPortClass parent_class; -}; - -/* normal GObject stuff */ -GType pinos_server_port_get_type (void); - -const gchar * pinos_server_port_get_object_path (PinosServerPort *port); - -G_END_DECLS - -#endif /* __PINOS_SERVER_PORT_H__ */