/* -*- mode: C; c-file-style: "gnu"; indent-tabs-mode: nil; -*- */
/* dbus-server-debug-pipe.c In-proc debug server implementation 
 *
 * Copyright (C) 2003  CodeFactory AB
 * Copyright (C) 2003, 2004  Red Hat, Inc.
 *
 * Licensed under the Academic Free License version 2.1
 * 
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program 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 General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 *
 */

#include <config.h>
#include "dbus-internals.h"
#include "dbus-server-debug-pipe.h"
#include "dbus-transport-socket.h"
#include "dbus-connection-internal.h"
#include "dbus-hash.h"
#include "dbus-string.h"
#include "dbus-protocol.h"

#ifdef DBUS_BUILD_TESTS

/**
 * @defgroup DBusServerDebugPipe DBusServerDebugPipe
 * @ingroup  DBusInternals
 * @brief In-process pipe debug server used in unit tests.
 *
 * Types and functions related to DBusServerDebugPipe.
 * This is used for unit testing.
 *
 * @{
 */

/**
 * Opaque object representing a debug server implementation.
 */
typedef struct DBusServerDebugPipe DBusServerDebugPipe;

/**
 * Implementation details of DBusServerDebugPipe. All members
 * are private.
 */
struct DBusServerDebugPipe
{
  DBusServer base;  /**< Parent class members. */

  char *name; /**< Server name. */

  dbus_bool_t disconnected; /**< TRUE if disconnect has been called */
};

/* FIXME not threadsafe (right now the test suite doesn't use threads anyhow ) */
static DBusHashTable *server_pipe_hash;
static int server_pipe_hash_refcount = 0;

static dbus_bool_t
pipe_hash_ref (void)
{
  if (!server_pipe_hash)
    {
      _dbus_assert (server_pipe_hash_refcount == 0);
      
      server_pipe_hash = _dbus_hash_table_new (DBUS_HASH_STRING, NULL, NULL);

      if (!server_pipe_hash)
        return FALSE;
    }

  server_pipe_hash_refcount = 1;

  return TRUE;
}

static void
pipe_hash_unref (void)
{
  _dbus_assert (server_pipe_hash != NULL);
  _dbus_assert (server_pipe_hash_refcount > 0);

  server_pipe_hash_refcount -= 1;
  if (server_pipe_hash_refcount == 0)
    {
      _dbus_hash_table_unref (server_pipe_hash);
      server_pipe_hash = NULL;
    }
}

static void
debug_finalize (DBusServer *server)
{
  DBusServerDebugPipe *debug_server = (DBusServerDebugPipe*) server;

  pipe_hash_unref ();
  
  _dbus_server_finalize_base (server);

  dbus_free (debug_server->name);
  dbus_free (server);
}

static void
debug_disconnect (DBusServer *server)
{
  ((DBusServerDebugPipe*)server)->disconnected = TRUE;
}

static DBusServerVTable debug_vtable = {
  debug_finalize,
  debug_disconnect
};

/**
 * Creates a new debug server using an in-process pipe
 *
 * @param server_name the name of the server.
 * @param error address where an error can be returned.
 * @returns a new server, or #NULL on failure.
 */
DBusServer*
_dbus_server_debug_pipe_new (const char     *server_name,
                             DBusError      *error)
{
  DBusServerDebugPipe *debug_server;
  DBusString address;
  DBusString name_str;
  
  _DBUS_ASSERT_ERROR_IS_CLEAR (error);
  
  if (!pipe_hash_ref ())
    return NULL;
  
  if (_dbus_hash_table_lookup_string (server_pipe_hash, server_name) != NULL)
    {
      dbus_set_error (error, DBUS_ERROR_ADDRESS_IN_USE, NULL);
      pipe_hash_unref ();
      return NULL;
    }
  
  debug_server = dbus_new0 (DBusServerDebugPipe, 1);
  if (debug_server == NULL)
    goto nomem_0;

  if (!_dbus_string_init (&address))
    goto nomem_1;

  _dbus_string_init_const (&name_str, server_name);
  if (!_dbus_string_append (&address, "debug-pipe:name=") ||
      !_dbus_address_append_escaped (&address, &name_str))
    goto nomem_2;
  
  debug_server->name = _dbus_strdup (server_name);
  if (debug_server->name == NULL)
    goto nomem_2;
  
  if (!_dbus_server_init_base (&debug_server->base,
			       &debug_vtable, &address))
    goto nomem_3;

  if (!_dbus_hash_table_insert_string (server_pipe_hash,
				       debug_server->name,
				       debug_server))
    goto nomem_4;

  _dbus_string_free (&address);

  /* server keeps the pipe hash ref */

  _dbus_server_trace_ref (&debug_server->base, 0, 1, "debug_pipe_new");
  return (DBusServer *)debug_server;

 nomem_4:
  _dbus_server_finalize_base (&debug_server->base);
 nomem_3:
  dbus_free (debug_server->name);
 nomem_2:
  _dbus_string_free (&address);
 nomem_1:
  dbus_free (debug_server);
 nomem_0:
  pipe_hash_unref ();
  dbus_set_error (error, DBUS_ERROR_NO_MEMORY, NULL);
  return NULL;
}

/**
 * Creates the client-side transport for
 * a debug-pipe connection connected to the
 * given debug-pipe server name.
 * 
 * @param server_name name of server to connect to
 * @param error address where an error can be returned.
 * @returns #NULL on no memory or transport
 */
DBusTransport*
_dbus_transport_debug_pipe_new (const char     *server_name,
                                DBusError      *error)
{
  DBusTransport *client_transport;
  DBusTransport *server_transport;
  DBusConnection *connection;
  int client_fd, server_fd;
  DBusServer *server;
  DBusString address;
  
  _DBUS_ASSERT_ERROR_IS_CLEAR (error);

  if (server_pipe_hash == NULL)
    {
      dbus_set_error (error, DBUS_ERROR_NO_SERVER, NULL);
      return NULL;
    }
  
  server = _dbus_hash_table_lookup_string (server_pipe_hash,
                                           server_name);
  if (server == NULL ||
      ((DBusServerDebugPipe*)server)->disconnected)
    {
      dbus_set_error (error, DBUS_ERROR_NO_SERVER, NULL);
      return NULL;
    }

  if (!_dbus_string_init (&address))
    {
      dbus_set_error (error, DBUS_ERROR_NO_MEMORY, NULL);
      return NULL;
    }

  if (!_dbus_string_append (&address, "debug-pipe:name=") ||
      !_dbus_string_append (&address, server_name))
    {
      dbus_set_error (error, DBUS_ERROR_NO_MEMORY, NULL);
      _dbus_string_free (&address);
      return NULL;
    }
  
  if (!_dbus_full_duplex_pipe (&client_fd, &server_fd, FALSE,
                               NULL))
    {
      _dbus_verbose ("failed to create full duplex pipe\n");
      dbus_set_error (error, DBUS_ERROR_FAILED, "Could not create full-duplex pipe");
      _dbus_string_free (&address);
      return NULL;
    }

  client_transport = _dbus_transport_new_for_socket (client_fd,
                                                     NULL, &address);
  if (client_transport == NULL)
    {
      _dbus_close_socket (client_fd, NULL);
      _dbus_close_socket (server_fd, NULL);
      dbus_set_error (error, DBUS_ERROR_NO_MEMORY, NULL);
      _dbus_string_free (&address);
      return NULL;
    }

  _dbus_string_free (&address);
  
  client_fd = -1;

  server_transport = _dbus_transport_new_for_socket (server_fd,
                                                     &server->guid_hex, NULL);
  if (server_transport == NULL)
    {
      _dbus_transport_unref (client_transport);
      _dbus_close_socket (server_fd, NULL);
      dbus_set_error (error, DBUS_ERROR_NO_MEMORY, NULL);
      return NULL;
    }

  server_fd = -1;

  if (!_dbus_transport_set_auth_mechanisms (server_transport,
                                            (const char**) server->auth_mechanisms))
    {
      dbus_set_error (error, DBUS_ERROR_NO_MEMORY, NULL);
      _dbus_transport_unref (server_transport);
      _dbus_transport_unref (client_transport);
      return NULL;
    }
  
  connection = _dbus_connection_new_for_transport (server_transport);
  _dbus_transport_unref (server_transport);
  server_transport = NULL;
  
  if (connection == NULL)
    {
      _dbus_transport_unref (client_transport);
      dbus_set_error (error, DBUS_ERROR_NO_MEMORY, NULL);
      return NULL;
    }

  /* See if someone wants to handle this new connection,
   * self-referencing for paranoia
   */
  if (server->new_connection_function)
    {
      dbus_server_ref (server);
      (* server->new_connection_function) (server, connection,
                                           server->new_connection_data);
      dbus_server_unref (server);
    }
  
  /* If no one grabbed a reference, the connection will die,
   * and the client transport will get an immediate disconnect
   */
  _dbus_connection_close_if_only_one_ref (connection);
  dbus_connection_unref (connection);

  return client_transport;
}

/**
 * Tries to interpret the address entry as a debug pipe entry.
 * 
 * Sets error if the result is not OK.
 * 
 * @param entry an address entry
 * @param server_p location to store a new DBusServer, or #NULL on failure.
 * @param error location to store rationale for failure on bad address
 * @returns the outcome
 * 
 */
DBusServerListenResult
_dbus_server_listen_debug_pipe (DBusAddressEntry *entry,
                                DBusServer      **server_p,
                                DBusError        *error)
{
  const char *method;

  *server_p = NULL;
  
  method = dbus_address_entry_get_method (entry);
  
  if (strcmp (method, "debug-pipe") == 0)
    {
      const char *name = dbus_address_entry_get_value (entry, "name");
      
      if (name == NULL)
        {
          _dbus_set_bad_address(error, "debug-pipe", "name",
                                NULL);
          return DBUS_SERVER_LISTEN_BAD_ADDRESS;
        }

      *server_p = _dbus_server_debug_pipe_new (name, error);
      
      if (*server_p)
        {
          _DBUS_ASSERT_ERROR_IS_CLEAR(error);
          return DBUS_SERVER_LISTEN_OK;
        }
      else
        {
          _DBUS_ASSERT_ERROR_IS_SET(error);
          return DBUS_SERVER_LISTEN_DID_NOT_CONNECT;
        }
    }
  else
    {
      _DBUS_ASSERT_ERROR_IS_CLEAR(error);
      return DBUS_SERVER_LISTEN_NOT_HANDLED;
    }
}

/**
 * Opens a debug pipe transport, used in the test suite.
 * 
 * @param entry the address entry to try opening as debug-pipe
 * @param transport_p return location for the opened transport
 * @param error error to be set
 * @returns result of the attempt
 */
DBusTransportOpenResult
_dbus_transport_open_debug_pipe (DBusAddressEntry  *entry,
                                 DBusTransport    **transport_p,
                                 DBusError         *error)
{
  const char *method;
  
  method = dbus_address_entry_get_method (entry);
  _dbus_assert (method != NULL);

  if (strcmp (method, "debug-pipe") == 0)
    {
      const char *name = dbus_address_entry_get_value (entry, "name");

      if (name == NULL)
        {
          _dbus_set_bad_address (error, "debug-pipe", "name",
                                 NULL);
          return DBUS_TRANSPORT_OPEN_BAD_ADDRESS;
        }
          
      *transport_p = _dbus_transport_debug_pipe_new (name, error);

      if (*transport_p == NULL)
        {
          _DBUS_ASSERT_ERROR_IS_SET (error);
          return DBUS_TRANSPORT_OPEN_DID_NOT_CONNECT;
        }
      else
        {
          _DBUS_ASSERT_ERROR_IS_CLEAR (error);
          return DBUS_TRANSPORT_OPEN_OK;
        }      
    }
  else
    {
      _DBUS_ASSERT_ERROR_IS_CLEAR (error);
      return DBUS_TRANSPORT_OPEN_NOT_HANDLED;
    }
}


/** @} */

#endif /* DBUS_BUILD_TESTS */

