driver.c revision a16e83f45d33ae5f3bd5966416c57c8ad4448ae8
1aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson/* -*- mode: C; c-file-style: "gnu" -*- */
2c414488fe62605ebda5e875fc2db05c6b3dd199fHavoc Pennington/* driver.c  Bus client (driver)
3aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson *
4aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * Copyright (C) 2003  CodeFactory AB
5aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson *
6aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * Licensed under the Academic Free License version 1.2
7aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson *
8aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * This program is free software; you can redistribute it and/or modify
9aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * it under the terms of the GNU General Public License as published by
10aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * the Free Software Foundation; either version 2 of the License, or
11aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * (at your option) any later version.
12aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson *
13aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * This program is distributed in the hope that it will be useful,
14aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * but WITHOUT ANY WARRANTY; without even the implied warranty of
15aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * GNU General Public License for more details.
17aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson *
18aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * You should have received a copy of the GNU General Public License
19aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * along with this program; if not, write to the Free Software
20aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
21aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson *
22aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson */
23aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
24aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#include "connection.h"
25aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#include "driver.h"
26aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#include "services.h"
27a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson#include <dbus/dbus-message-internal.h>
28aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#include <dbus/dbus-internals.h>
29aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#include <dbus/dbus-string.h>
30aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#include <string.h>
31aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
32aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#define BUS_DRIVER_SERVICE_NAME "org.freedesktop.DBus"
33aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#define BUS_DRIVER_HELLO_NAME "org.freedesktop.DBus.Hello"
34aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson#define BUS_DRIVER_WELCOME_NAME "org.freedesktop.DBus.Welcome"
35a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson#define BUS_DRIVER_LIST_SERVICES_NAME "org.freedesktop.DBus.ListServices"
36a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson#define BUS_DRIVER_SERVICES_NAME "org.freedesktop.DBus.Services"
37a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
38a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson#define BUS_DRIVER_SERVICE_CREATED_NAME "org.freedesktop.DBus.ServiceCreated"
39a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson#define BUS_DRIVER_SERVICE_DELETED_NAME "org.freedesktop.DBus.ServiceDeleted"
40aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
41aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonstatic dbus_bool_t  bus_driver_send_welcome_message (DBusConnection *connection,
42aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson						     DBusMessage    *hello_message);
43aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
44a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonstatic void
45a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonsend_one_message (DBusConnection *connection, void *data)
46a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson{
47a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  dbus_connection_send_message (connection, data, NULL, NULL);
48a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson}
49a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
50a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonstatic void
51a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonbus_driver_broadcast_message (DBusMessage *message)
52a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson{
53a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  bus_connection_foreach (send_one_message, message);
54a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson}
55a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
56a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonstatic dbus_bool_t
57a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonbus_driver_send_service_created (DBusConnection *connection, const char *name)
58a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson{
59a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  DBusMessage *message;
60a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
61a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  message = dbus_message_new (NULL, BUS_DRIVER_SERVICE_CREATED_NAME);
62a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
63a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  if (!message)
64a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    return FALSE;
65a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
66a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  if (!dbus_message_append_fields (message,
67a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson				   DBUS_TYPE_STRING, name,
68a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson				   0))
69a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    {
70a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson      dbus_message_unref (message);
71a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson      return FALSE;
72a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    }
73a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
74a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  dbus_message_set_sender (message, BUS_DRIVER_SERVICE_NAME);
75a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  bus_driver_broadcast_message (message);
76a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  dbus_message_unref (message);
77a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
78a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  return TRUE;
79a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson}
80a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
81aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonstatic dbus_bool_t
82d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Penningtoncreate_unique_client_name (const char *name,
83d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington                           DBusString *str)
84aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson{
85d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington  /* We never want to use the same unique client name twice, because
86d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington   * we want to guarantee that if you send a message to a given unique
87d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington   * name, you always get the same application. So we use two numbers
88d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington   * for INT_MAX * INT_MAX combinations, should be pretty safe against
89d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington   * wraparound.
90d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington   */
91d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington  static int next_major_number = 0;
92d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington  static int next_minor_number = 0;
93d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington  int len;
94aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
95aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (!_dbus_string_append (str, name))
96aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    return FALSE;
97aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
98aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  len = _dbus_string_get_length (str);
99aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
100d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington  while (TRUE)
101aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    {
102d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      /* start out with 1-0, go to 1-1, 1-2, 1-3,
103d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington       * up to 1-MAXINT, then 2-0, 2-1, etc.
104d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington       */
105d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      if (next_minor_number <= 0)
106d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington        {
107d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington          next_major_number += 1;
108d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington          next_minor_number = 0;
109d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington          if (next_major_number <= 0)
110d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington            _dbus_assert_not_reached ("INT_MAX * INT_MAX clients were added");
111d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington        }
112d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington
113d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      _dbus_assert (next_major_number > 0);
114d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      _dbus_assert (next_minor_number >= 0);
115d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington
116d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      /* appname:MAJOR-MINOR */
117d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington
118d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      if (!_dbus_string_append (str, ":"))
119d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington        return FALSE;
120d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington
121d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      if (!_dbus_string_append_int (str, next_major_number))
122d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington        return FALSE;
123d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington
124d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      if (!_dbus_string_append (str, "-"))
125d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington        return FALSE;
126d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington
127d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      if (!_dbus_string_append_int (str, next_minor_number))
128d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington        return FALSE;
129d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington
130d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      next_minor_number += 1;
131aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
132aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      /* Check if a client with the name exists */
133aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      if (bus_service_lookup (str, FALSE) == NULL)
134aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson	break;
135aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
136d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      /* drop the number again, try the next one. */
137aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      _dbus_string_set_length (str, len);
138aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    }
139aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
140aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  return TRUE;
141aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson}
142aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
143aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonstatic dbus_bool_t
144a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonbus_driver_handle_hello (DBusConnection *connection,
145a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson			 DBusMessage    *message)
146aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson{
147aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  DBusResultCode result;
148aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  char *name;
149aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  DBusString unique_name;
150aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  BusService *service;
151aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  dbus_bool_t retval;
152aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
153aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  result = dbus_message_get_fields (message,
154aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson				    DBUS_TYPE_STRING, &name,
155aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson				    0);
156aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
157aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  /* FIXME: Handle this in a better way */
158aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (result != DBUS_RESULT_SUCCESS)
159aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    return FALSE;
160aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
161d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington  if (!_dbus_string_init (&unique_name, _DBUS_INT_MAX))
162aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    return FALSE;
163d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington
164d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington  if (!create_unique_client_name (name, &unique_name))
165d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington    {
166d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      _dbus_string_free (&unique_name);
167d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington      return FALSE;
168d6d50a29945ded04a17b3f42a3a1074449250ec0Havoc Pennington    }
169aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
170aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  /* Create the service */
171aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  service = bus_service_lookup (&unique_name, TRUE);
172aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (!service)
173aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    {
174aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      _dbus_string_free (&unique_name);
175aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      return FALSE;
176aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    }
177aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
178aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  /* FIXME: Error checks from this point */
179aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
180aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  /* Add the connection as the owner */
181aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  bus_service_add_owner (service, connection);
182aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  bus_connection_set_name (connection, &unique_name);
183aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
184aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  /* We need to assign the sender to the message here */
185a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  dbus_message_set_sender (message,
186a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson			   bus_connection_get_name (connection));
187aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
188aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  _dbus_string_free (&unique_name);
189aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
190aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  retval = bus_driver_send_welcome_message (connection, message);
191aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
192a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  if (!retval)
193a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    return FALSE;
194a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
195a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  /* Broadcast a ServiceCreated message */
196a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  retval = bus_driver_send_service_created (connection, bus_connection_get_name (connection));
197a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
198aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  return retval;
199aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson}
200aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
201aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonstatic dbus_bool_t
202aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonbus_driver_send_welcome_message (DBusConnection *connection,
203aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson				 DBusMessage    *hello_message)
204aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson{
205aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  DBusMessage *welcome;
206aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  const char *name;
207aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  dbus_bool_t retval;
208aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
209aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
210aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  name = bus_connection_get_name (connection);
211aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  _dbus_assert (name != NULL);
212aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
213aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  welcome = dbus_message_new_reply (BUS_DRIVER_WELCOME_NAME,
214aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson				    hello_message);
215aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (welcome == NULL)
216aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    return FALSE;
217aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
218aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  /* FIXME: Return value */
219a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  dbus_message_set_sender (welcome, BUS_DRIVER_SERVICE_NAME);
220aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
221aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (!dbus_message_append_fields (welcome,
222aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson				   DBUS_TYPE_STRING, name,
223aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson				   NULL))
224aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    {
225aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      dbus_message_unref (welcome);
226aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      return FALSE;
227aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    }
228aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
229aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  retval = dbus_connection_send_message (connection, welcome, NULL, NULL);
230aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  dbus_message_unref (welcome);
231aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
232aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  return retval;
233aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson}
234aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
235a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonstatic void
236a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlssonbus_driver_handle_list_services (DBusConnection *connection,
237a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson				 DBusMessage    *message)
238a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson{
239a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  DBusMessage *reply;
240a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  int len, i;
241a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  char **services;
242a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
243a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  reply = dbus_message_new_reply (BUS_DRIVER_SERVICES_NAME, message);
244a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
245a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  if (reply == NULL)
246a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    return;
247a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
248a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  services = bus_services_list (&len);
249a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
250a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  if (!services)
251a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    return;
252a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
253a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  if (!dbus_message_append_fields (reply,
254a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson				   DBUS_TYPE_STRING_ARRAY, services, len,
255a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson				   0))
256a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    goto error;
257a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
258a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  if (!dbus_connection_send_message (connection, reply, NULL, NULL))
259a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    goto error;
260a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
261a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson error:
262a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  dbus_message_unref (reply);
263a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  for (i = 0; i < len; i++)
264a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson    dbus_free (services[i]);
265a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  dbus_free (services);
266a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson}
267a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson
268aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson/* This is where all the magic occurs */
269aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonstatic DBusHandlerResult
270aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonbus_driver_message_handler (DBusMessageHandler *handler,
271aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson			    DBusConnection     *connection,
272aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson			    DBusMessage        *message,
273aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson			    void               *user_data)
274aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson{
275aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  const char *service, *name;
276aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
277aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  service = dbus_message_get_service (message);
278aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  name = dbus_message_get_name (message);
279aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
280a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson  dbus_message_set_sender (message,
281a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson			   bus_connection_get_name (connection));
282aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
283aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (strcmp (service, BUS_DRIVER_SERVICE_NAME) == 0)
284aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    {
285aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      if (strcmp (name, BUS_DRIVER_HELLO_NAME) == 0)
286a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson	bus_driver_handle_hello (connection, message);
287a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson      else if (strcmp (name, BUS_DRIVER_LIST_SERVICES_NAME) == 0)
288a16e83f45d33ae5f3bd5966416c57c8ad4448ae8Anders Carlsson	bus_driver_handle_list_services (connection, message);
289aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    }
290aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  else
291aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    {
292aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      /* FIXME: Dispatch the message :-) */
293aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    }
294aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
295aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  return DBUS_HANDLER_RESULT_ALLOW_MORE_HANDLERS;
296aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson}
297aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
298aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssondbus_bool_t
299aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonbus_driver_add_connection (DBusConnection *connection)
300aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson{
301aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  DBusMessageHandler *handler;
302aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
303aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  handler = dbus_message_handler_new (bus_driver_message_handler, NULL, NULL);
304aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
305aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (!dbus_connection_add_filter (connection, handler))
306aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    {
307aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      dbus_message_handler_unref (handler);
308aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
309aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson      return FALSE;
310aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    }
311aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
312c414488fe62605ebda5e875fc2db05c6b3dd199fHavoc Pennington  /* FIXME we are leaking the DBusMessageHandler */
313c414488fe62605ebda5e875fc2db05c6b3dd199fHavoc Pennington
314aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  _dbus_verbose ("D-Bus driver on board...\n");
315aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
316aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  return TRUE;
317aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson}
318aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
319aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonvoid
320aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlssonbus_driver_remove_connection (DBusConnection *connection)
321aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson{
322aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  BusService *service;
323aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  DBusString service_name;
324aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  const char *name;
325aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
326aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  name = bus_connection_get_name (connection);
327aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
328aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (name == NULL)
329aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    return;
330aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
331aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  _dbus_string_init_const (&service_name, name);
332aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
333aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  service = bus_service_lookup (&service_name, FALSE);
334aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson
335aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson  if (service)
336aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson    bus_service_free (service);
337aff24a72c18a43dbb6f2d85e6d2226a3c2ea8f10Anders Carlsson}
338