LCOV - code coverage report
Current view: top level - gio/tests - gdbus-example-export.c (source / functions) Coverage Total Hit
Test: unnamed Lines: 0.0 % 102 0
Test Date: 2024-11-26 05:23:01 Functions: 0.0 % 17 0
Branches: - 0 0

             Branch data     Line data    Source code
       1                 :             : #include <gio/gio.h>
       2                 :             : #include <stdlib.h>
       3                 :             : 
       4                 :             : #define DBUS_INTERFACE_PROPERTIES "org.freedesktop.DBus.Properties"
       5                 :             : 
       6                 :             : /* ---------------------------------------------------------------------------------------------------- */
       7                 :             : 
       8                 :             : /* The object we want to export */
       9                 :             : typedef struct _MyObjectClass MyObjectClass;
      10                 :             : typedef struct _MyObject MyObject;
      11                 :             : 
      12                 :             : struct _MyObjectClass
      13                 :             : {
      14                 :             :   GObjectClass parent_class;
      15                 :             : };
      16                 :             : 
      17                 :             : struct _MyObject
      18                 :             : {
      19                 :             :   GObject parent_instance;
      20                 :             : 
      21                 :             :   gint count;
      22                 :             :   gchar *name;
      23                 :             : };
      24                 :             : 
      25                 :             : enum
      26                 :             : {
      27                 :             :   PROP_0,
      28                 :             :   PROP_COUNT,
      29                 :             :   PROP_NAME
      30                 :             : };
      31                 :             : 
      32                 :             : static GType my_object_get_type (void);
      33                 :           0 : G_DEFINE_TYPE (MyObject, my_object, G_TYPE_OBJECT)
      34                 :             : 
      35                 :             : static void
      36                 :           0 : my_object_finalize (GObject *object)
      37                 :             : {
      38                 :           0 :   MyObject *myobj = (MyObject*)object;
      39                 :             : 
      40                 :           0 :   g_free (myobj->name);
      41                 :             : 
      42                 :           0 :   G_OBJECT_CLASS (my_object_parent_class)->finalize (object);
      43                 :           0 : }
      44                 :             : 
      45                 :             : static void
      46                 :           0 : my_object_init (MyObject *object)
      47                 :             : {
      48                 :           0 :   object->count = 0;
      49                 :           0 :   object->name = NULL;
      50                 :           0 : }
      51                 :             : 
      52                 :             : static void
      53                 :           0 : my_object_get_property (GObject    *object,
      54                 :             :                         guint       prop_id,
      55                 :             :                         GValue     *value,
      56                 :             :                         GParamSpec *pspec)
      57                 :             : {
      58                 :           0 :   MyObject *myobj = (MyObject*)object;
      59                 :             : 
      60                 :           0 :   switch (prop_id)
      61                 :             :     {
      62                 :           0 :     case PROP_COUNT:
      63                 :           0 :       g_value_set_int (value, myobj->count);
      64                 :           0 :       break;
      65                 :             : 
      66                 :           0 :     case PROP_NAME:
      67                 :           0 :       g_value_set_string (value, myobj->name);
      68                 :           0 :       break;
      69                 :             : 
      70                 :           0 :     default:
      71                 :           0 :       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
      72                 :             :     }
      73                 :           0 : }
      74                 :             : 
      75                 :             : static void
      76                 :           0 : my_object_set_property (GObject      *object,
      77                 :             :                         guint         prop_id,
      78                 :             :                         const GValue *value,
      79                 :             :                         GParamSpec   *pspec)
      80                 :             : {
      81                 :           0 :   MyObject *myobj = (MyObject*)object;
      82                 :             : 
      83                 :           0 :   switch (prop_id)
      84                 :             :     {
      85                 :           0 :     case PROP_COUNT:
      86                 :           0 :       myobj->count = g_value_get_int (value);
      87                 :           0 :       break;
      88                 :             : 
      89                 :           0 :     case PROP_NAME:
      90                 :           0 :       g_free (myobj->name);
      91                 :           0 :       myobj->name = g_value_dup_string (value);
      92                 :           0 :       break;
      93                 :             : 
      94                 :           0 :     default:
      95                 :           0 :       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
      96                 :             :     }
      97                 :           0 : }
      98                 :             : 
      99                 :             : static void
     100                 :           0 : my_object_class_init (MyObjectClass *class)
     101                 :             : {
     102                 :           0 :   GObjectClass *gobject_class = G_OBJECT_CLASS (class);
     103                 :             : 
     104                 :           0 :   gobject_class->finalize = my_object_finalize;
     105                 :           0 :   gobject_class->set_property = my_object_set_property;
     106                 :           0 :   gobject_class->get_property = my_object_get_property;
     107                 :             : 
     108                 :           0 :   g_object_class_install_property (gobject_class,
     109                 :             :                                    PROP_COUNT,
     110                 :             :                                    g_param_spec_int ("count",
     111                 :             :                                                      "Count",
     112                 :             :                                                      "Count",
     113                 :             :                                                      0, 99999, 0,
     114                 :             :                                                      G_PARAM_READWRITE));
     115                 :             : 
     116                 :           0 :   g_object_class_install_property (gobject_class,
     117                 :             :                                    PROP_NAME,
     118                 :             :                                    g_param_spec_string ("name",
     119                 :             :                                                         "Name",
     120                 :             :                                                         "Name",
     121                 :             :                                                         NULL,
     122                 :             :                                                         G_PARAM_READWRITE));
     123                 :           0 : }
     124                 :             : 
     125                 :             : /* A method that we want to export */
     126                 :             : static void
     127                 :           0 : my_object_change_count (MyObject *myobj,
     128                 :             :                         gint      change)
     129                 :             : {
     130                 :           0 :   myobj->count = 2 * myobj->count + change;
     131                 :             : 
     132                 :           0 :   g_object_notify (G_OBJECT (myobj), "count");
     133                 :           0 : }
     134                 :             : 
     135                 :             : /* ---------------------------------------------------------------------------------------------------- */
     136                 :             : 
     137                 :             : static GDBusNodeInfo *introspection_data = NULL;
     138                 :             : 
     139                 :             : /* Introspection data for the service we are exporting */
     140                 :             : static const gchar introspection_xml[] =
     141                 :             :   "<node>"
     142                 :             :   "  <interface name='org.myorg.MyObject'>"
     143                 :             :   "    <method name='ChangeCount'>"
     144                 :             :   "      <arg type='i' name='change' direction='in'/>"
     145                 :             :   "    </method>"
     146                 :             :   "    <property type='i' name='Count' access='read'/>"
     147                 :             :   "    <property type='s' name='Name' access='readwrite'/>"
     148                 :             :   "  </interface>"
     149                 :             :   "</node>";
     150                 :             : 
     151                 :             : 
     152                 :             : static void
     153                 :           0 : handle_method_call (GDBusConnection       *connection,
     154                 :             :                     const gchar           *sender,
     155                 :             :                     const gchar           *object_path,
     156                 :             :                     const gchar           *interface_name,
     157                 :             :                     const gchar           *method_name,
     158                 :             :                     GVariant              *parameters,
     159                 :             :                     GDBusMethodInvocation *invocation,
     160                 :             :                     gpointer               user_data)
     161                 :             : {
     162                 :           0 :   MyObject *myobj = user_data;
     163                 :             : 
     164                 :           0 :   if (g_strcmp0 (method_name, "ChangeCount") == 0)
     165                 :             :     {
     166                 :             :       gint change;
     167                 :           0 :       g_variant_get (parameters, "(i)", &change);
     168                 :             : 
     169                 :           0 :       my_object_change_count (myobj, change);
     170                 :             : 
     171                 :           0 :       g_dbus_method_invocation_return_value (invocation, NULL);
     172                 :             :     }
     173                 :           0 : }
     174                 :             : 
     175                 :             : static GVariant *
     176                 :           0 : handle_get_property (GDBusConnection  *connection,
     177                 :             :                      const gchar      *sender,
     178                 :             :                      const gchar      *object_path,
     179                 :             :                      const gchar      *interface_name,
     180                 :             :                      const gchar      *property_name,
     181                 :             :                      GError          **error,
     182                 :             :                      gpointer          user_data)
     183                 :             : {
     184                 :             :   GVariant *ret;
     185                 :           0 :   MyObject *myobj = user_data;
     186                 :             : 
     187                 :           0 :   ret = NULL;
     188                 :           0 :   if (g_strcmp0 (property_name, "Count") == 0)
     189                 :             :     {
     190                 :           0 :       ret = g_variant_new_int32 (myobj->count);
     191                 :             :     }
     192                 :           0 :   else if (g_strcmp0 (property_name, "Name") == 0)
     193                 :             :     {
     194                 :           0 :       ret = g_variant_new_string (myobj->name ? myobj->name : "");
     195                 :             :     }
     196                 :             : 
     197                 :           0 :   return ret;
     198                 :             : }
     199                 :             : 
     200                 :             : static gboolean
     201                 :           0 : handle_set_property (GDBusConnection  *connection,
     202                 :             :                      const gchar      *sender,
     203                 :             :                      const gchar      *object_path,
     204                 :             :                      const gchar      *interface_name,
     205                 :             :                      const gchar      *property_name,
     206                 :             :                      GVariant         *value,
     207                 :             :                      GError          **error,
     208                 :             :                      gpointer          user_data)
     209                 :             : {
     210                 :           0 :   MyObject *myobj = user_data;
     211                 :             : 
     212                 :           0 :   if (g_strcmp0 (property_name, "Count") == 0)
     213                 :             :     {
     214                 :           0 :       g_object_set (myobj, "count", g_variant_get_int32 (value), NULL);
     215                 :             :     }
     216                 :           0 :   else if (g_strcmp0 (property_name, "Name") == 0)
     217                 :             :     {
     218                 :           0 :       g_object_set (myobj, "name", g_variant_get_string (value, NULL), NULL);
     219                 :             :     }
     220                 :             : 
     221                 :           0 :   return TRUE;
     222                 :             : }
     223                 :             : 
     224                 :             : 
     225                 :             : /* for now */
     226                 :             : static const GDBusInterfaceVTable interface_vtable =
     227                 :             : {
     228                 :             :   handle_method_call,
     229                 :             :   handle_get_property,
     230                 :             :   handle_set_property,
     231                 :             :   { 0 }
     232                 :             : };
     233                 :             : 
     234                 :             : static void
     235                 :           0 : send_property_change (GObject         *obj,
     236                 :             :                       GParamSpec      *pspec,
     237                 :             :                       GDBusConnection *connection)
     238                 :             : {
     239                 :             :   GVariantBuilder *builder;
     240                 :             :   GVariantBuilder *invalidated_builder;
     241                 :           0 :   MyObject *myobj = (MyObject *)obj;
     242                 :             : 
     243                 :           0 :   builder = g_variant_builder_new (G_VARIANT_TYPE_ARRAY);
     244                 :           0 :   invalidated_builder = g_variant_builder_new (G_VARIANT_TYPE ("as"));
     245                 :             : 
     246                 :           0 :   if (g_strcmp0 (pspec->name, "count") == 0)
     247                 :           0 :     g_variant_builder_add (builder,
     248                 :             :                            "{sv}",
     249                 :             :                            "Count", g_variant_new_int32 (myobj->count));
     250                 :           0 :   else if (g_strcmp0 (pspec->name, "name") == 0)
     251                 :           0 :     g_variant_builder_add (builder,
     252                 :             :                            "{sv}",
     253                 :           0 :                            "Name", g_variant_new_string (myobj->name ? myobj->name : ""));
     254                 :             : 
     255                 :           0 :   g_dbus_connection_emit_signal (connection,
     256                 :             :                                  NULL,
     257                 :             :                                  "/org/myorg/MyObject",
     258                 :             :                                  DBUS_INTERFACE_PROPERTIES,
     259                 :             :                                  "PropertiesChanged",
     260                 :             :                                  g_variant_new ("(sa{sv}as)",
     261                 :             :                                                 "org.myorg.MyObject",
     262                 :             :                                                 builder,
     263                 :             :                                                 invalidated_builder),
     264                 :             :                                  NULL);
     265                 :           0 : }
     266                 :             : 
     267                 :             : static void
     268                 :           0 : on_bus_acquired (GDBusConnection *connection,
     269                 :             :                  const gchar     *name,
     270                 :             :                  gpointer         user_data)
     271                 :             : {
     272                 :           0 :   MyObject *myobj = user_data;
     273                 :             :   guint registration_id;
     274                 :             : 
     275                 :           0 :   g_signal_connect (myobj, "notify",
     276                 :             :                     G_CALLBACK (send_property_change), connection);
     277                 :           0 :   registration_id = g_dbus_connection_register_object (connection,
     278                 :             :                                                        "/org/myorg/MyObject",
     279                 :           0 :                                                        introspection_data->interfaces[0],
     280                 :             :                                                        &interface_vtable,
     281                 :             :                                                        myobj,
     282                 :             :                                                        NULL,  /* user_data_free_func */
     283                 :             :                                                        NULL); /* GError** */
     284                 :           0 :   g_assert (registration_id > 0);
     285                 :           0 : }
     286                 :             : 
     287                 :             : static void
     288                 :           0 : on_name_acquired (GDBusConnection *connection,
     289                 :             :                   const gchar     *name,
     290                 :             :                   gpointer         user_data)
     291                 :             : {
     292                 :           0 : }
     293                 :             : 
     294                 :             : static void
     295                 :           0 : on_name_lost (GDBusConnection *connection,
     296                 :             :               const gchar     *name,
     297                 :             :               gpointer         user_data)
     298                 :             : {
     299                 :           0 :   exit (1);
     300                 :             : }
     301                 :             : 
     302                 :             : int
     303                 :           0 : main (int argc, char *argv[])
     304                 :             : {
     305                 :             :   guint owner_id;
     306                 :             :   GMainLoop *loop;
     307                 :             :   MyObject *myobj;
     308                 :             : 
     309                 :             :   /* We are lazy here - we don't want to manually provide
     310                 :             :    * the introspection data structures - so we just build
     311                 :             :    * them from XML.
     312                 :             :    */
     313                 :           0 :   introspection_data = g_dbus_node_info_new_for_xml (introspection_xml, NULL);
     314                 :           0 :   g_assert (introspection_data != NULL);
     315                 :             : 
     316                 :           0 :   myobj = g_object_new (my_object_get_type (), NULL);
     317                 :             : 
     318                 :           0 :   owner_id = g_bus_own_name (G_BUS_TYPE_SESSION,
     319                 :             :                              "org.myorg.MyObject",
     320                 :             :                              G_BUS_NAME_OWNER_FLAGS_NONE,
     321                 :             :                              on_bus_acquired,
     322                 :             :                              on_name_acquired,
     323                 :             :                              on_name_lost,
     324                 :             :                              myobj,
     325                 :             :                              NULL);
     326                 :             : 
     327                 :           0 :   loop = g_main_loop_new (NULL, FALSE);
     328                 :           0 :   g_main_loop_run (loop);
     329                 :             : 
     330                 :           0 :   g_bus_unown_name (owner_id);
     331                 :             : 
     332                 :           0 :   g_dbus_node_info_unref (introspection_data);
     333                 :             : 
     334                 :           0 :   g_object_unref (myobj);
     335                 :             : 
     336                 :           0 :   return 0;
     337                 :             : }
        

Generated by: LCOV version 2.0-1