/*
 *
 *  BlueZ - Bluetooth protocol stack for Linux
 *
 *  Copyright (C) 2008-2010  Nokia Corporation
 *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
 *
 *
 *  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 St, Fifth Floor, Boston, MA  02110-1301  USA
 *
 */

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <stdint.h>
#include <string.h>
#include <glib.h>
#include <dbus/dbus.h>
#include <gdbus.h>

#include "log.h"
#include "telephony.h"
#include "error.h"

/* SSC D-Bus definitions */
#define SSC_DBUS_NAME  "com.nokia.phone.SSC"
#define SSC_DBUS_IFACE "com.nokia.phone.SSC"
#define SSC_DBUS_PATH  "/com/nokia/phone/SSC"

/* libcsnet D-Bus definitions */
#define CSD_CSNET_BUS_NAME	"com.nokia.csd.CSNet"
#define CSD_CSNET_PATH		"/com/nokia/csd/csnet"
#define CSD_CSNET_IFACE		"com.nokia.csd.CSNet"
#define CSD_CSNET_REGISTRATION	"com.nokia.csd.CSNet.NetworkRegistration"
#define CSD_CSNET_OPERATOR	"com.nokia.csd.CSNet.NetworkOperator"
#define CSD_CSNET_SIGNAL	"com.nokia.csd.CSNet.SignalStrength"

enum net_registration_status {
	NETWORK_REG_STATUS_HOME,
	NETWORK_REG_STATUS_ROAMING,
	NETWORK_REG_STATUS_OFFLINE,
	NETWORK_REG_STATUS_SEARCHING,
	NETWORK_REG_STATUS_NO_SIM,
	NETWORK_REG_STATUS_POWEROFF,
	NETWORK_REG_STATUS_POWERSAFE,
	NETWORK_REG_STATUS_NO_COVERAGE,
	NETWORK_REG_STATUS_REJECTED,
	NETWORK_REG_STATUS_UNKOWN
};

/* CSD CALL plugin D-Bus definitions */
#define CSD_CALL_BUS_NAME	"com.nokia.csd.Call"
#define CSD_CALL_INTERFACE	"com.nokia.csd.Call"
#define CSD_CALL_INSTANCE	"com.nokia.csd.Call.Instance"
#define CSD_CALL_CONFERENCE	"com.nokia.csd.Call.Conference"
#define CSD_CALL_PATH		"/com/nokia/csd/call"
#define CSD_CALL_CONFERENCE_PATH "/com/nokia/csd/call/conference"

/* Call status values as exported by the CSD CALL plugin */
#define CSD_CALL_STATUS_IDLE			0
#define CSD_CALL_STATUS_CREATE			1
#define CSD_CALL_STATUS_COMING			2
#define CSD_CALL_STATUS_PROCEEDING		3
#define CSD_CALL_STATUS_MO_ALERTING		4
#define CSD_CALL_STATUS_MT_ALERTING		5
#define CSD_CALL_STATUS_WAITING			6
#define CSD_CALL_STATUS_ANSWERED		7
#define CSD_CALL_STATUS_ACTIVE			8
#define CSD_CALL_STATUS_MO_RELEASE		9
#define CSD_CALL_STATUS_MT_RELEASE		10
#define CSD_CALL_STATUS_HOLD_INITIATED		11
#define CSD_CALL_STATUS_HOLD			12
#define CSD_CALL_STATUS_RETRIEVE_INITIATED	13
#define CSD_CALL_STATUS_RECONNECT_PENDING	14
#define CSD_CALL_STATUS_TERMINATED		15
#define CSD_CALL_STATUS_SWAP_INITIATED		16

#define CALL_FLAG_NONE				0
#define CALL_FLAG_PRESENTATION_ALLOWED		0x01
#define CALL_FLAG_PRESENTATION_RESTRICTED	0x02

/* SIM Phonebook D-Bus definitions */
#define CSD_SIMPB_BUS_NAME			"com.nokia.csd.SIM"
#define CSD_SIMPB_INTERFACE			"com.nokia.csd.SIM.Phonebook"
#define CSD_SIMPB_PATH				"/com/nokia/csd/sim/phonebook"

#define CSD_SIMPB_TYPE_ADN			"ADN"
#define CSD_SIMPB_TYPE_FDN			"FDN"
#define CSD_SIMPB_TYPE_SDN			"SDN"
#define CSD_SIMPB_TYPE_VMBX			"VMBX"
#define CSD_SIMPB_TYPE_MBDN			"MBDN"
#define CSD_SIMPB_TYPE_EN			"EN"
#define CSD_SIMPB_TYPE_MSISDN			"MSISDN"

struct csd_call {
	char *object_path;
	int status;
	gboolean originating;
	gboolean emergency;
	gboolean on_hold;
	gboolean conference;
	char *number;
	gboolean setup;
};

static struct {
	char *operator_name;
	uint8_t status;
	int32_t signal_bars;
} net = {
	.operator_name = NULL,
	.status = NETWORK_REG_STATUS_UNKOWN,
	/* Init as 0 meaning inactive mode. In modem power off state
	 * can be be -1, but we treat all values as 0s regardless
	 * inactive or power off. */
	.signal_bars = 0,
};

struct pending_req {
	DBusPendingCall *call;
	void *user_data;
};

static int get_property(const char *iface, const char *prop);

static DBusConnection *connection = NULL;

static GSList *calls = NULL;
static GSList *watches = NULL;
static GSList *pending = NULL;

/* Reference count for determining the call indicator status */
static GSList *active_calls = NULL;

static char *msisdn = NULL;	/* Subscriber number */
static char *vmbx = NULL;	/* Voice mailbox number */

/* HAL battery namespace key values */
static int battchg_cur = -1;	/* "battery.charge_level.current" */
static int battchg_last = -1;	/* "battery.charge_level.last_full" */
static int battchg_design = -1;	/* "battery.charge_level.design" */

static gboolean get_calls_active = FALSE;

static gboolean events_enabled = FALSE;

/* Supported set of call hold operations */
static const char *chld_str = "0,1,1x,2,2x,3,4";

/* Timer for tracking call creation requests */
static guint create_request_timer = 0;

static struct indicator maemo_indicators[] =
{
	{ "battchg",	"0-5",	5,	TRUE },
	/* signal strength in terms of bars */
	{ "signal",	"0-5",	0,	TRUE },
	{ "service",	"0,1",	0,	TRUE },
	{ "call",	"0,1",	0,	TRUE },
	{ "callsetup",	"0-3",	0,	TRUE },
	{ "callheld",	"0-2",	0,	FALSE },
	{ "roam",	"0,1",	0,	TRUE },
	{ NULL }
};

static char *call_status_str[] = {
	"IDLE",
	"CREATE",
	"COMING",
	"PROCEEDING",
	"MO_ALERTING",
	"MT_ALERTING",
	"WAITING",
	"ANSWERED",
	"ACTIVE",
	"MO_RELEASE",
	"MT_RELEASE",
	"HOLD_INITIATED",
	"HOLD",
	"RETRIEVE_INITIATED",
	"RECONNECT_PENDING",
	"TERMINATED",
	"SWAP_INITIATED",
	"???"
};

static struct csd_call *find_call(const char *path)
{
	GSList *l;

	for (l = calls; l != NULL; l = l->next) {
		struct csd_call *call = l->data;

		if (g_str_equal(call->object_path, path))
			return call;
	}

	return NULL;
}

static struct csd_call *find_non_held_call(void)
{
	GSList *l;

	for (l = calls; l != NULL; l = l->next) {
		struct csd_call *call = l->data;

		if (call->status == CSD_CALL_STATUS_IDLE)
			continue;

		if (call->status != CSD_CALL_STATUS_HOLD)
			return call;
	}

	return NULL;
}

static struct csd_call *find_non_idle_call(void)
{
	GSList *l;

	for (l = calls; l != NULL; l = l->next) {
		struct csd_call *call = l->data;

		if (call->status != CSD_CALL_STATUS_IDLE)
			return call;
	}

	return NULL;
}

static struct csd_call *find_call_with_status(int status)
{
	GSList *l;

	for (l = calls; l != NULL; l = l->next) {
		struct csd_call *call = l->data;

		if (call->status == status)
			return call;
	}

	return NULL;
}

static int release_conference(void)
{
	DBusMessage *msg;

	DBG("telephony-maemo6: releasing conference call");

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
						CSD_CALL_CONFERENCE_PATH,
						CSD_CALL_INSTANCE,
						"Release");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int release_call(struct csd_call *call)
{
	DBusMessage *msg;

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
						call->object_path,
						CSD_CALL_INSTANCE,
						"Release");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int answer_call(struct csd_call *call)
{
	DBusMessage *msg;

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
						call->object_path,
						CSD_CALL_INSTANCE,
						"Answer");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int split_call(struct csd_call *call)
{
	DBusMessage *msg;

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME,
						call->object_path,
						CSD_CALL_INSTANCE,
						"Split");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int unhold_call(struct csd_call *call)
{
	DBusMessage *msg;

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
						CSD_CALL_INTERFACE,
						"Unhold");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int hold_call(struct csd_call *call)
{
	DBusMessage *msg;

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
						CSD_CALL_INTERFACE,
						"Hold");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int swap_calls(void)
{
	DBusMessage *msg;

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
						CSD_CALL_INTERFACE,
						"Swap");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int create_conference(void)
{
	DBusMessage *msg;

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
						CSD_CALL_INTERFACE,
						"Conference");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int call_transfer(void)
{
	DBusMessage *msg;

	msg = dbus_message_new_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
						CSD_CALL_INTERFACE,
						"Transfer");
	if (!msg) {
		error("Unable to allocate new D-Bus message");
		return -ENOMEM;
	}

	g_dbus_send_message(connection, msg);

	return 0;
}

static int number_type(const char *number)
{
	if (number == NULL)
		return NUMBER_TYPE_TELEPHONY;

	if (number[0] == '+' || strncmp(number, "00", 2) == 0)
		return NUMBER_TYPE_INTERNATIONAL;

	return NUMBER_TYPE_TELEPHONY;
}

void telephony_device_connected(void *telephony_device)
{
	struct csd_call *coming;

	DBG("telephony-maemo6: device %p connected", telephony_device);

	coming = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);
	if (coming) {
		if (find_call_with_status(CSD_CALL_STATUS_ACTIVE))
			telephony_call_waiting_ind(coming->number,
						number_type(coming->number));
		else
			telephony_incoming_call_ind(coming->number,
						number_type(coming->number));
	}
}

static void pending_req_finalize(struct pending_req *req)
{
	if (!dbus_pending_call_get_completed(req->call))
		dbus_pending_call_cancel(req->call);

	dbus_pending_call_unref(req->call);
	g_free(req);
}

static void remove_pending_by_data(gpointer data, gpointer user_data)
{
	struct pending_req *req = data;

	if (req->user_data == user_data) {
		pending = g_slist_remove(pending, req);
		pending_req_finalize(req);
	}
}

void telephony_device_disconnected(void *telephony_device)
{
	DBG("telephony-maemo6: device %p disconnected", telephony_device);
	events_enabled = FALSE;

	g_slist_foreach(pending, remove_pending_by_data, telephony_device);
}

void telephony_event_reporting_req(void *telephony_device, int ind)
{
	events_enabled = ind == 1 ? TRUE : FALSE;

	telephony_event_reporting_rsp(telephony_device, CME_ERROR_NONE);
}

void telephony_response_and_hold_req(void *telephony_device, int rh)
{
	telephony_response_and_hold_rsp(telephony_device,
						CME_ERROR_NOT_SUPPORTED);
}

void telephony_terminate_call_req(void *telephony_device)
{
	struct csd_call *call;
	struct csd_call *alerting;
	int err;

	call = find_call_with_status(CSD_CALL_STATUS_ACTIVE);
	if (!call)
		call = find_non_idle_call();

	if (!call) {
		error("No active call");
		telephony_terminate_call_rsp(telephony_device,
						CME_ERROR_NOT_ALLOWED);
		return;
	}

	alerting = find_call_with_status(CSD_CALL_STATUS_MO_ALERTING);
	if (call->on_hold && alerting)
		err = release_call(alerting);
	else if (call->conference)
		err = release_conference();
	else
		err = release_call(call);

	if (err < 0)
		telephony_terminate_call_rsp(telephony_device,
						CME_ERROR_AG_FAILURE);
	else
		telephony_terminate_call_rsp(telephony_device, CME_ERROR_NONE);
}

void telephony_answer_call_req(void *telephony_device)
{
	struct csd_call *call;

	call = find_call_with_status(CSD_CALL_STATUS_COMING);
	if (!call)
		call = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);

	if (!call)
		call = find_call_with_status(CSD_CALL_STATUS_PROCEEDING);

	if (!call)
		call = find_call_with_status(CSD_CALL_STATUS_WAITING);

	if (!call) {
		telephony_answer_call_rsp(telephony_device,
						CME_ERROR_NOT_ALLOWED);
		return;
	}

	if (answer_call(call) < 0)
		telephony_answer_call_rsp(telephony_device,
						CME_ERROR_AG_FAILURE);
	else
		telephony_answer_call_rsp(telephony_device, CME_ERROR_NONE);
}

static int send_method_call(const char *dest, const char *path,
				const char *interface, const char *method,
				DBusPendingCallNotifyFunction cb,
				void *user_data, int type, ...)
{
	DBusMessage *msg;
	DBusPendingCall *call;
	va_list args;
	struct pending_req *req;

	msg = dbus_message_new_method_call(dest, path, interface, method);
	if (!msg) {
		error("Unable to allocate new D-Bus %s message", method);
		return -ENOMEM;
	}

	va_start(args, type);

	if (!dbus_message_append_args_valist(msg, type, args)) {
		dbus_message_unref(msg);
		va_end(args);
		return -EIO;
	}

	va_end(args);

	if (!cb) {
		g_dbus_send_message(connection, msg);
		return 0;
	}

	if (!dbus_connection_send_with_reply(connection, msg, &call, -1)) {
		error("Sending %s failed", method);
		dbus_message_unref(msg);
		return -EIO;
	}

	dbus_pending_call_set_notify(call, cb, user_data, NULL);

	req = g_new0(struct pending_req, 1);
	req->call = call;
	req->user_data = user_data;

	pending = g_slist_prepend(pending, req);
	dbus_message_unref(msg);

	return 0;
}

static struct pending_req *find_request(const DBusPendingCall *call)
{
	GSList *l;

	for (l = pending; l; l = l->next) {
		struct pending_req *req = l->data;

		if (req->call == call)
			return req;
	}

	return NULL;
}

static void remove_pending(DBusPendingCall *call)
{
	struct pending_req *req = find_request(call);

	pending = g_slist_remove(pending, req);
	pending_req_finalize(req);
}

static void create_call_reply(DBusPendingCall *call, void *user_data)
{
	DBusError err;
	DBusMessage *reply;
	void *telephony_device = user_data;

	reply = dbus_pending_call_steal_reply(call);

	dbus_error_init(&err);
	if (dbus_set_error_from_message(&err, reply)) {
		error("csd replied with an error: %s, %s",
				err.name, err.message);
		if (g_strcmp0(err.name,
				"com.nokia.csd.Call.Error.CSInactive") == 0)
			telephony_dial_number_rsp(telephony_device,
						CME_ERROR_NO_NETWORK_SERVICE);
		else
			telephony_dial_number_rsp(telephony_device,
							CME_ERROR_AG_FAILURE);
		dbus_error_free(&err);
	} else
		telephony_dial_number_rsp(telephony_device, CME_ERROR_NONE);

	dbus_message_unref(reply);
	remove_pending(call);
}

void telephony_last_dialed_number_req(void *telephony_device)
{
	int ret;

	DBG("telephony-maemo6: last dialed number request");

	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
				CSD_CALL_INTERFACE, "CreateFromLast",
				create_call_reply, telephony_device,
				DBUS_TYPE_INVALID);
	if (ret < 0)
		telephony_dial_number_rsp(telephony_device,
						CME_ERROR_AG_FAILURE);
}

static const char *memory_dial_lookup(int location)
{
	if (location == 1)
		return vmbx;
	else
		return NULL;
}

void telephony_dial_number_req(void *telephony_device, const char *number)
{
	int ret;

	DBG("telephony-maemo6: dial request to %s", number);

	if (strncmp(number, "*31#", 4) == 0)
		number += 4;
	else if (strncmp(number, "#31#", 4) == 0)
		number += 4;
	else if (number[0] == '>') {
		const char *location = &number[1];

		number = memory_dial_lookup(strtol(&number[1], NULL, 0));
		if (!number) {
			error("No number at memory location %s", location);
			telephony_dial_number_rsp(telephony_device,
						CME_ERROR_INVALID_INDEX);
			return;
		}
	}

	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
				CSD_CALL_INTERFACE, "Create",
				create_call_reply, telephony_device,
				DBUS_TYPE_STRING, &number,
				DBUS_TYPE_INVALID);
	if (ret < 0)
		telephony_dial_number_rsp(telephony_device,
						CME_ERROR_AG_FAILURE);
}

void telephony_transmit_dtmf_req(void *telephony_device, char tone)
{
	int ret;
	char buf[2] = { tone, '\0' }, *buf_ptr = buf;

	DBG("telephony-maemo6: transmit dtmf: %s", buf);

	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
				CSD_CALL_INTERFACE, "SendDTMF",
				NULL, NULL,
				DBUS_TYPE_STRING, &buf_ptr,
				DBUS_TYPE_INVALID);
	if (ret < 0) {
		telephony_transmit_dtmf_rsp(telephony_device,
						CME_ERROR_AG_FAILURE);
		return;
	}

	telephony_transmit_dtmf_rsp(telephony_device, CME_ERROR_NONE);
}

void telephony_subscriber_number_req(void *telephony_device)
{
	DBG("telephony-maemo6: subscriber number request");
	if (msisdn)
		telephony_subscriber_number_ind(msisdn,
						number_type(msisdn),
						SUBSCRIBER_SERVICE_VOICE);
	telephony_subscriber_number_rsp(telephony_device, CME_ERROR_NONE);
}

static int csd_status_to_hfp(struct csd_call *call)
{
	switch (call->status) {
	case CSD_CALL_STATUS_IDLE:
	case CSD_CALL_STATUS_MO_RELEASE:
	case CSD_CALL_STATUS_MT_RELEASE:
	case CSD_CALL_STATUS_TERMINATED:
		return -1;
	case CSD_CALL_STATUS_CREATE:
		return CALL_STATUS_DIALING;
	case CSD_CALL_STATUS_WAITING:
		return CALL_STATUS_WAITING;
	case CSD_CALL_STATUS_PROCEEDING:
		/* PROCEEDING can happen in outgoing/incoming */
		if (call->originating)
			return CALL_STATUS_DIALING;
		else
			return CALL_STATUS_INCOMING;
	case CSD_CALL_STATUS_COMING:
		return CALL_STATUS_INCOMING;
	case CSD_CALL_STATUS_MO_ALERTING:
		return CALL_STATUS_ALERTING;
	case CSD_CALL_STATUS_MT_ALERTING:
		return CALL_STATUS_INCOMING;
	case CSD_CALL_STATUS_ANSWERED:
	case CSD_CALL_STATUS_ACTIVE:
	case CSD_CALL_STATUS_RECONNECT_PENDING:
	case CSD_CALL_STATUS_SWAP_INITIATED:
	case CSD_CALL_STATUS_HOLD_INITIATED:
		return CALL_STATUS_ACTIVE;
	case CSD_CALL_STATUS_RETRIEVE_INITIATED:
	case CSD_CALL_STATUS_HOLD:
		return CALL_STATUS_HELD;
	default:
		return -1;
	}
}

void telephony_list_current_calls_req(void *telephony_device)
{
	GSList *l;
	int i;

	DBG("telephony-maemo6: list current calls request");

	for (l = calls, i = 1; l != NULL; l = l->next, i++) {
		struct csd_call *call = l->data;
		int status, direction, multiparty;

		status = csd_status_to_hfp(call);
		if (status < 0)
			continue;

		direction = call->originating ?
				CALL_DIR_OUTGOING : CALL_DIR_INCOMING;

		multiparty = call->conference ?
				CALL_MULTIPARTY_YES : CALL_MULTIPARTY_NO;

		telephony_list_current_call_ind(i, direction, status,
						CALL_MODE_VOICE, multiparty,
						call->number,
						number_type(call->number));
	}

	telephony_list_current_calls_rsp(telephony_device, CME_ERROR_NONE);
}

void telephony_operator_selection_req(void *telephony_device)
{
	telephony_operator_selection_ind(OPERATOR_MODE_AUTO,
				net.operator_name ? net.operator_name : "");
	telephony_operator_selection_rsp(telephony_device, CME_ERROR_NONE);
}

static void foreach_call_with_status(int status,
					int (*func)(struct csd_call *call))
{
	GSList *l;

	for (l = calls; l != NULL; l = l->next) {
		struct csd_call *call = l->data;

		if (call->status == status)
			func(call);
	}
}

void telephony_call_hold_req(void *telephony_device, const char *cmd)
{
	const char *idx;
	struct csd_call *call;
	int err = 0;

	DBG("telephony-maemo6: got call hold request %s", cmd);

	if (strlen(cmd) > 1)
		idx = &cmd[1];
	else
		idx = NULL;

	if (idx)
		call = g_slist_nth_data(calls, strtol(idx, NULL, 0) - 1);
	else
		call = NULL;

	switch (cmd[0]) {
	case '0':
		if (find_call_with_status(CSD_CALL_STATUS_WAITING))
			foreach_call_with_status(CSD_CALL_STATUS_WAITING,
								release_call);
		else
			foreach_call_with_status(CSD_CALL_STATUS_HOLD,
								release_call);
		break;
	case '1':
		if (idx) {
			if (call)
				err = release_call(call);
			break;
		}
		foreach_call_with_status(CSD_CALL_STATUS_ACTIVE, release_call);
		call = find_call_with_status(CSD_CALL_STATUS_WAITING);
		if (call)
			err = answer_call(call);
		break;
	case '2':
		if (idx) {
			if (call)
				err = split_call(call);
		} else {
			struct csd_call *held, *wait;

			call = find_call_with_status(CSD_CALL_STATUS_ACTIVE);
			held = find_call_with_status(CSD_CALL_STATUS_HOLD);
			wait = find_call_with_status(CSD_CALL_STATUS_WAITING);

			if (wait)
				err = answer_call(wait);
			else if (call && held)
				err = swap_calls();
			else {
				if (call)
					err = hold_call(call);
				if (held)
					err = unhold_call(held);
			}
		}
		break;
	case '3':
		if (find_call_with_status(CSD_CALL_STATUS_HOLD) ||
				find_call_with_status(CSD_CALL_STATUS_WAITING))
			err = create_conference();
		break;
	case '4':
		err = call_transfer();
		break;
	default:
		DBG("Unknown call hold request");
		break;
	}

	if (err)
		telephony_call_hold_rsp(telephony_device,
					CME_ERROR_AG_FAILURE);
	else
		telephony_call_hold_rsp(telephony_device, CME_ERROR_NONE);
}

void telephony_nr_and_ec_req(void *telephony_device, gboolean enable)
{
	DBG("telephony-maemo6: got %s NR and EC request",
			enable ? "enable" : "disable");
	telephony_nr_and_ec_rsp(telephony_device, CME_ERROR_NONE);
}

void telephony_key_press_req(void *telephony_device, const char *keys)
{
	struct csd_call *active, *waiting;
	int err;

	DBG("telephony-maemo6: got key press request for %s", keys);

	waiting = find_call_with_status(CSD_CALL_STATUS_COMING);
	if (!waiting)
		waiting = find_call_with_status(CSD_CALL_STATUS_MT_ALERTING);
	if (!waiting)
		waiting = find_call_with_status(CSD_CALL_STATUS_PROCEEDING);

	active = find_call_with_status(CSD_CALL_STATUS_ACTIVE);

	if (waiting)
		err = answer_call(waiting);
	else if (active)
		err = release_call(active);
	else
		err = 0;

	if (err < 0)
		telephony_key_press_rsp(telephony_device,
							CME_ERROR_AG_FAILURE);
	else
		telephony_key_press_rsp(telephony_device, CME_ERROR_NONE);
}

void telephony_voice_dial_req(void *telephony_device, gboolean enable)
{
	DBG("telephony-maemo6: got %s voice dial request",
			enable ? "enable" : "disable");

	telephony_voice_dial_rsp(telephony_device, CME_ERROR_NOT_SUPPORTED);
}

static void handle_incoming_call(DBusMessage *msg)
{
	const char *number, *call_path;
	struct csd_call *call;

	if (!dbus_message_get_args(msg, NULL,
					DBUS_TYPE_OBJECT_PATH, &call_path,
					DBUS_TYPE_STRING, &number,
					DBUS_TYPE_INVALID)) {
		error("Unexpected parameters in Call.Coming() signal");
		return;
	}

	call = find_call(call_path);
	if (!call) {
		error("Didn't find any matching call object for %s",
				call_path);
		return;
	}

	DBG("Incoming call to %s from number %s", call_path, number);

	g_free(call->number);
	call->number = g_strdup(number);

	if (find_call_with_status(CSD_CALL_STATUS_ACTIVE) ||
			find_call_with_status(CSD_CALL_STATUS_HOLD))
		telephony_call_waiting_ind(call->number,
						number_type(call->number));
	else
		telephony_incoming_call_ind(call->number,
						number_type(call->number));

	telephony_update_indicator(maemo_indicators, "callsetup",
					EV_CALLSETUP_INCOMING);
}

static void handle_outgoing_call(DBusMessage *msg)
{
	const char *number, *call_path;
	struct csd_call *call;

	if (!dbus_message_get_args(msg, NULL,
					DBUS_TYPE_OBJECT_PATH, &call_path,
					DBUS_TYPE_STRING, &number,
					DBUS_TYPE_INVALID)) {
		error("Unexpected parameters in Call.Created() signal");
		return;
	}

	call = find_call(call_path);
	if (!call) {
		error("Didn't find any matching call object for %s",
				call_path);
		return;
	}

	DBG("Outgoing call from %s to number %s", call_path, number);

	g_free(call->number);
	call->number = g_strdup(number);

	if (create_request_timer) {
		g_source_remove(create_request_timer);
		create_request_timer = 0;
	}
}

static gboolean create_timeout(gpointer user_data)
{
	telephony_update_indicator(maemo_indicators, "callsetup",
					EV_CALLSETUP_INACTIVE);
	create_request_timer = 0;
	return FALSE;
}

static void handle_create_requested(DBusMessage *msg)
{
	DBG("Call.CreateRequested()");

	if (create_request_timer)
		g_source_remove(create_request_timer);

	create_request_timer = g_timeout_add_seconds(5, create_timeout, NULL);

	telephony_update_indicator(maemo_indicators, "callsetup",
					EV_CALLSETUP_OUTGOING);
}

static void call_set_status(struct csd_call *call, dbus_uint32_t status)
{
	dbus_uint32_t prev_status;
	int callheld = telephony_get_indicator(maemo_indicators, "callheld");

	prev_status = call->status;
	DBG("Call %s changed from %s to %s", call->object_path,
		call_status_str[prev_status], call_status_str[status]);

	if (prev_status == status) {
		DBG("Ignoring CSD Call state change to existing state");
		return;
	}

	call->status = (int) status;

	switch (status) {
	case CSD_CALL_STATUS_IDLE:
		if (call->setup) {
			telephony_update_indicator(maemo_indicators,
							"callsetup",
							EV_CALLSETUP_INACTIVE);
			if (!call->originating)
				telephony_calling_stopped_ind();
		}

		g_free(call->number);
		call->number = NULL;
		call->originating = FALSE;
		call->emergency = FALSE;
		call->on_hold = FALSE;
		call->conference = FALSE;
		call->setup = FALSE;
		break;
	case CSD_CALL_STATUS_CREATE:
		call->originating = TRUE;
		call->setup = TRUE;
		break;
	case CSD_CALL_STATUS_COMING:
		call->originating = FALSE;
		call->setup = TRUE;
		break;
	case CSD_CALL_STATUS_PROCEEDING:
		break;
	case CSD_CALL_STATUS_MO_ALERTING:
		telephony_update_indicator(maemo_indicators, "callsetup",
						EV_CALLSETUP_ALERTING);
		break;
	case CSD_CALL_STATUS_MT_ALERTING:
		/* Some headsets expect incoming call notification before they
		 * can send ATA command. When call changed status from waiting
		 * to alerting we need to send missing notification. Otherwise
		 * headsets like Nokia BH-108 or BackBeat 903 are unable to
		 * answer incoming call that was previously waiting. */
		if (prev_status == CSD_CALL_STATUS_WAITING)
			telephony_incoming_call_ind(call->number,
						number_type(call->number));
		break;
	case CSD_CALL_STATUS_WAITING:
		break;
	case CSD_CALL_STATUS_ANSWERED:
		break;
	case CSD_CALL_STATUS_ACTIVE:
		if (call->on_hold) {
			call->on_hold = FALSE;
			if (find_call_with_status(CSD_CALL_STATUS_HOLD))
				telephony_update_indicator(maemo_indicators,
							"callheld",
							EV_CALLHELD_MULTIPLE);
			else
				telephony_update_indicator(maemo_indicators,
							"callheld",
							EV_CALLHELD_NONE);
		} else {
			if (!g_slist_find(active_calls, call))
				active_calls = g_slist_prepend(active_calls, call);
			if (g_slist_length(active_calls) == 1)
				telephony_update_indicator(maemo_indicators,
								"call",
								EV_CALL_ACTIVE);
			/* Upgrade callheld status if necessary */
			if (callheld == EV_CALLHELD_ON_HOLD)
				telephony_update_indicator(maemo_indicators,
							"callheld",
							EV_CALLHELD_MULTIPLE);
			telephony_update_indicator(maemo_indicators,
							"callsetup",
							EV_CALLSETUP_INACTIVE);
			if (!call->originating)
				telephony_calling_stopped_ind();
			call->setup = FALSE;
		}
		break;
	case CSD_CALL_STATUS_MO_RELEASE:
	case CSD_CALL_STATUS_MT_RELEASE:
		active_calls = g_slist_remove(active_calls, call);
		if (g_slist_length(active_calls) == 0)
			telephony_update_indicator(maemo_indicators, "call",
							EV_CALL_INACTIVE);
		break;
	case CSD_CALL_STATUS_HOLD_INITIATED:
		break;
	case CSD_CALL_STATUS_HOLD:
		call->on_hold = TRUE;
		if (find_non_held_call())
			telephony_update_indicator(maemo_indicators,
							"callheld",
							EV_CALLHELD_MULTIPLE);
		else
			telephony_update_indicator(maemo_indicators,
							"callheld",
							EV_CALLHELD_ON_HOLD);
		break;
	case CSD_CALL_STATUS_RETRIEVE_INITIATED:
		break;
	case CSD_CALL_STATUS_RECONNECT_PENDING:
		break;
	case CSD_CALL_STATUS_TERMINATED:
		if (call->on_hold &&
				!find_call_with_status(CSD_CALL_STATUS_HOLD))
			telephony_update_indicator(maemo_indicators,
							"callheld",
							EV_CALLHELD_NONE);
		else if (callheld == EV_CALLHELD_MULTIPLE &&
				find_call_with_status(CSD_CALL_STATUS_HOLD))
			telephony_update_indicator(maemo_indicators,
							"callheld",
							EV_CALLHELD_ON_HOLD);
		break;
	case CSD_CALL_STATUS_SWAP_INITIATED:
		break;
	default:
		error("Unknown call status %u", status);
		break;
	}
}

static void handle_call_status(DBusMessage *msg, const char *call_path)
{
	struct csd_call *call;
	dbus_uint32_t status, cause_type, cause;

	if (!dbus_message_get_args(msg, NULL,
					DBUS_TYPE_UINT32, &status,
					DBUS_TYPE_UINT32, &cause_type,
					DBUS_TYPE_UINT32, &cause,
					DBUS_TYPE_INVALID)) {
		error("Unexpected paramters in Instance.CallStatus() signal");
		return;
	}

	call = find_call(call_path);
	if (!call) {
		error("Didn't find any matching call object for %s",
				call_path);
		return;
	}

	if (status > 16) {
		error("Invalid call status %u", status);
		return;
	}

	call_set_status(call, status);
}

static void handle_conference(DBusMessage *msg, gboolean joined)
{
	const char *path;
	struct csd_call *call;

	if (!dbus_message_get_args(msg, NULL,
					DBUS_TYPE_OBJECT_PATH, &path,
					DBUS_TYPE_INVALID)) {
		error("Unexpected parameters in Conference.%s",
					dbus_message_get_member(msg));
		return;
	}

	call = find_call(path);
	if (!call) {
		error("Conference signal for unknown call %s", path);
		return;
	}

	DBG("Call %s %s the conference", path, joined ? "joined" : "left");

	call->conference = joined;
}

static uint8_t str2status(const char *state)
{
	if (g_strcmp0(state, "Home") == 0)
		return NETWORK_REG_STATUS_HOME;
	else if (g_strcmp0(state, "Roaming") == 0)
		return NETWORK_REG_STATUS_ROAMING;
	else if (g_strcmp0(state, "Offline") == 0)
		return NETWORK_REG_STATUS_OFFLINE;
	else if (g_strcmp0(state, "Searching") == 0)
		return NETWORK_REG_STATUS_SEARCHING;
	else if (g_strcmp0(state, "NoSim") == 0)
		return NETWORK_REG_STATUS_NO_SIM;
	else if (g_strcmp0(state, "Poweroff") == 0)
		return NETWORK_REG_STATUS_POWEROFF;
	else if (g_strcmp0(state, "Powersafe") == 0)
		return NETWORK_REG_STATUS_POWERSAFE;
	else if (g_strcmp0(state, "NoCoverage") == 0)
		return NETWORK_REG_STATUS_NO_COVERAGE;
	else if (g_strcmp0(state, "Reject") == 0)
		return NETWORK_REG_STATUS_REJECTED;
	else
		return NETWORK_REG_STATUS_UNKOWN;
}

static void update_registration_status(const char *status)
{
	uint8_t new_status;

	new_status = str2status(status);

	if (net.status == new_status)
		return;

	switch (new_status) {
	case NETWORK_REG_STATUS_HOME:
		telephony_update_indicator(maemo_indicators, "roam",
							EV_ROAM_INACTIVE);
		if (net.status > NETWORK_REG_STATUS_ROAMING)
			telephony_update_indicator(maemo_indicators,
							"service",
							EV_SERVICE_PRESENT);
		break;
	case NETWORK_REG_STATUS_ROAMING:
		telephony_update_indicator(maemo_indicators, "roam",
							EV_ROAM_ACTIVE);
		if (net.status > NETWORK_REG_STATUS_ROAMING)
			telephony_update_indicator(maemo_indicators,
							"service",
							EV_SERVICE_PRESENT);
		break;
	case NETWORK_REG_STATUS_OFFLINE:
	case NETWORK_REG_STATUS_SEARCHING:
	case NETWORK_REG_STATUS_NO_SIM:
	case NETWORK_REG_STATUS_POWEROFF:
	case NETWORK_REG_STATUS_POWERSAFE:
	case NETWORK_REG_STATUS_NO_COVERAGE:
	case NETWORK_REG_STATUS_REJECTED:
	case NETWORK_REG_STATUS_UNKOWN:
		if (net.status < NETWORK_REG_STATUS_OFFLINE)
			telephony_update_indicator(maemo_indicators,
							"service",
							EV_SERVICE_NONE);
		break;
	}

	net.status = new_status;

	DBG("telephony-maemo6: registration status changed: %s", status);
}

static void handle_registration_changed(DBusMessage *msg)
{
	const char *status;

	if (!dbus_message_get_args(msg, NULL,
					DBUS_TYPE_STRING, &status,
					DBUS_TYPE_INVALID)) {
		error("Unexpected parameters in RegistrationChanged");
		return;
	}

	update_registration_status(status);
}

static void update_signal_strength(int32_t signal_bars)
{
	if (signal_bars < 0) {
		DBG("signal strength smaller than expected: %d < 0",
								signal_bars);
		signal_bars = 0;
	} else if (signal_bars > 5) {
		DBG("signal strength greater than expected: %d > 5",
								signal_bars);
		signal_bars = 5;
	}

	if (net.signal_bars == signal_bars)
		return;

	telephony_update_indicator(maemo_indicators, "signal", signal_bars);

	net.signal_bars = signal_bars;
	DBG("telephony-maemo6: signal strength updated: %d/5", signal_bars);
}

static void handle_signal_bars_changed(DBusMessage *msg)
{
	int32_t signal_bars;

	if (!dbus_message_get_args(msg, NULL,
					DBUS_TYPE_INT32, &signal_bars,
					DBUS_TYPE_INVALID)) {
		error("Unexpected parameters in SignalBarsChanged");
		return;
	}

	update_signal_strength(signal_bars);
}

static gboolean iter_get_basic_args(DBusMessageIter *iter,
					int first_arg_type, ...)
{
	int type;
	va_list ap;

	va_start(ap, first_arg_type);

	for (type = first_arg_type; type != DBUS_TYPE_INVALID;
			type = va_arg(ap, int)) {
		void *value = va_arg(ap, void *);
		int real_type = dbus_message_iter_get_arg_type(iter);

		if (real_type != type) {
			error("iter_get_basic_args: expected %c but got %c",
					(char) type, (char) real_type);
			break;
		}

		dbus_message_iter_get_basic(iter, value);
		dbus_message_iter_next(iter);
	}

	va_end(ap);

	return type == DBUS_TYPE_INVALID ? TRUE : FALSE;
}

static void hal_battery_level_reply(DBusPendingCall *call, void *user_data)
{
	DBusError err;
	DBusMessage *reply;
	dbus_int32_t level;
	int *value = user_data;

	reply = dbus_pending_call_steal_reply(call);

	dbus_error_init(&err);
	if (dbus_set_error_from_message(&err, reply)) {
		error("hald replied with an error: %s, %s",
				err.name, err.message);
		dbus_error_free(&err);
		goto done;
	}

	if (!dbus_message_get_args(reply, NULL,
				DBUS_TYPE_INT32, &level,
				DBUS_TYPE_INVALID)) {
		error("Unexpected args in hald reply");
		goto done;
	}

	*value = (int) level;

	if (value == &battchg_last)
		DBG("telephony-maemo6: battery.charge_level.last_full is %d",
				*value);
	else if (value == &battchg_design)
		DBG("telephony-maemo6: battery.charge_level.design is %d",
				*value);
	else
		DBG("telephony-maemo6: battery.charge_level.current is %d",
				*value);

	if ((battchg_design > 0 || battchg_last > 0) && battchg_cur >= 0) {
		int new, max;

		if (battchg_last > 0)
			max = battchg_last;
		else
			max = battchg_design;

		new = battchg_cur * 5 / max;

		telephony_update_indicator(maemo_indicators, "battchg", new);
	}

done:
	dbus_message_unref(reply);
	remove_pending(call);
}

static void hal_get_integer(const char *path, const char *key, void *user_data)
{
	send_method_call("org.freedesktop.Hal", path,
				"org.freedesktop.Hal.Device",
				"GetPropertyInteger",
				hal_battery_level_reply, user_data,
				DBUS_TYPE_STRING, &key,
				DBUS_TYPE_INVALID);
}

static void handle_hal_property_modified(DBusMessage *msg)
{
	DBusMessageIter iter, array;
	dbus_int32_t num_changes;
	const char *path;

	path = dbus_message_get_path(msg);

	dbus_message_iter_init(msg, &iter);

	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_INT32) {
		error("Unexpected signature in hal PropertyModified signal");
		return;
	}

	dbus_message_iter_get_basic(&iter, &num_changes);
	dbus_message_iter_next(&iter);

	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
		error("Unexpected signature in hal PropertyModified signal");
		return;
	}

	dbus_message_iter_recurse(&iter, &array);

	while (dbus_message_iter_get_arg_type(&array) != DBUS_TYPE_INVALID) {
		DBusMessageIter prop;
		const char *name;
		dbus_bool_t added, removed;

		dbus_message_iter_recurse(&array, &prop);

		if (!iter_get_basic_args(&prop,
					DBUS_TYPE_STRING, &name,
					DBUS_TYPE_BOOLEAN, &added,
					DBUS_TYPE_BOOLEAN, &removed,
					DBUS_TYPE_INVALID)) {
			error("Invalid hal PropertyModified parameters");
			break;
		}

		if (g_str_equal(name, "battery.charge_level.last_full"))
			hal_get_integer(path, name, &battchg_last);
		else if (g_str_equal(name, "battery.charge_level.current"))
			hal_get_integer(path, name, &battchg_cur);
		else if (g_str_equal(name, "battery.charge_level.design"))
			hal_get_integer(path, name, &battchg_design);

		dbus_message_iter_next(&array);
	}
}

static void csd_call_free(struct csd_call *call)
{
	if (!call)
		return;

	g_free(call->object_path);
	g_free(call->number);

	g_free(call);
}

static void parse_call_list(DBusMessageIter *iter)
{
	do {
		DBusMessageIter call_iter;
		struct csd_call *call;
		const char *object_path, *number;
		dbus_uint32_t status;
		dbus_bool_t originating, terminating, emerg, on_hold, conf;

		if (dbus_message_iter_get_arg_type(iter) != DBUS_TYPE_STRUCT) {
			error("Unexpected signature in GetCallInfoAll reply");
			break;
		}

		dbus_message_iter_recurse(iter, &call_iter);

		if (!iter_get_basic_args(&call_iter,
					DBUS_TYPE_OBJECT_PATH, &object_path,
					DBUS_TYPE_UINT32, &status,
					DBUS_TYPE_BOOLEAN, &originating,
					DBUS_TYPE_BOOLEAN, &terminating,
					DBUS_TYPE_BOOLEAN, &emerg,
					DBUS_TYPE_BOOLEAN, &on_hold,
					DBUS_TYPE_BOOLEAN, &conf,
					DBUS_TYPE_STRING, &number,
					DBUS_TYPE_INVALID)) {
			error("Parsing call D-Bus parameters failed");
			break;
		}

		call = find_call(object_path);
		if (!call) {
			call = g_new0(struct csd_call, 1);
			call->object_path = g_strdup(object_path);
			calls = g_slist_append(calls, call);
			DBG("telephony-maemo6: new csd call instance at %s",
								object_path);
		}

		if (status == CSD_CALL_STATUS_IDLE)
			continue;

		/* CSD gives incorrect call_hold property sometimes */
		if ((call->status != CSD_CALL_STATUS_HOLD && on_hold) ||
				(call->status == CSD_CALL_STATUS_HOLD &&
								!on_hold)) {
			error("Conflicting call status and on_hold property!");
			on_hold = call->status == CSD_CALL_STATUS_HOLD;
		}

		call->originating = originating;
		call->on_hold = on_hold;
		call->conference = conf;
		g_free(call->number);
		call->number = g_strdup(number);

		/* Update indicators */
		call_set_status(call, status);

	} while (dbus_message_iter_next(iter));
}

static void update_operator_name(const char *name)
{
	if (name == NULL)
		return;

	g_free(net.operator_name);
	net.operator_name = g_strndup(name, 16);
	DBG("telephony-maemo6: operator name updated: %s", name);
}

static void get_property_reply(DBusPendingCall *call, void *user_data)
{
	char *prop = user_data;
	DBusError err;
	DBusMessage *reply;
	DBusMessageIter iter, sub;

	reply = dbus_pending_call_steal_reply(call);

	dbus_error_init(&err);
	if (dbus_set_error_from_message(&err, reply)) {
		error("csd replied with an error: %s, %s",
				err.name, err.message);
		dbus_error_free(&err);
		goto done;
	}

	dbus_message_iter_init(reply, &iter);

	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) {
		error("Unexpected signature in Get return");
		goto done;
	}

	dbus_message_iter_recurse(&iter, &sub);

	if (g_strcmp0(prop, "RegistrationStatus") == 0) {
		const char *status;

		dbus_message_iter_get_basic(&sub, &status);
		update_registration_status(status);

		get_property(CSD_CSNET_OPERATOR, "OperatorName");
		get_property(CSD_CSNET_SIGNAL, "SignalBars");
	} else if (g_strcmp0(prop, "OperatorName") == 0) {
		const char *name;

		dbus_message_iter_get_basic(&sub, &name);
		update_operator_name(name);
	} else if (g_strcmp0(prop, "SignalBars") == 0) {
		int32_t signal_bars;

		dbus_message_iter_get_basic(&sub, &signal_bars);
		update_signal_strength(signal_bars);
	}

done:
	g_free(prop);
	dbus_message_unref(reply);
	remove_pending(call);
}

static int get_property(const char *iface, const char *prop)
{
	return send_method_call(CSD_CSNET_BUS_NAME, CSD_CSNET_PATH,
				DBUS_INTERFACE_PROPERTIES, "Get",
				get_property_reply, g_strdup(prop),
				DBUS_TYPE_STRING, &iface,
				DBUS_TYPE_STRING, &prop,
				DBUS_TYPE_INVALID);
}

static void handle_operator_name_changed(DBusMessage *msg)
{
	const char *name;

	if (!dbus_message_get_args(msg, NULL,
					DBUS_TYPE_STRING, &name,
					DBUS_TYPE_INVALID)) {
		error("Unexpected parameters in OperatorNameChanged");
		return;
	}

	update_operator_name(name);
}

static void call_info_reply(DBusPendingCall *call, void *user_data)
{
	DBusError err;
	DBusMessage *reply;
	DBusMessageIter iter, sub;;

	get_calls_active = FALSE;

	reply = dbus_pending_call_steal_reply(call);

	dbus_error_init(&err);
	if (dbus_set_error_from_message(&err, reply)) {
		error("csd replied with an error: %s, %s",
				err.name, err.message);
		dbus_error_free(&err);
		goto done;
	}

	dbus_message_iter_init(reply, &iter);

	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
		error("Unexpected signature in GetCallInfoAll return");
		goto done;
	}

	dbus_message_iter_recurse(&iter, &sub);

	parse_call_list(&sub);

	get_property(CSD_CSNET_REGISTRATION, "RegistrationStatus");

done:
	dbus_message_unref(reply);
	remove_pending(call);
}


static void phonebook_read_reply(DBusPendingCall *call, void *user_data)
{
	DBusError derr;
	DBusMessage *reply;
	const char *name, *number, *secondname, *additionalnumber, *email;
	int index;
	char **number_type = user_data;

	reply = dbus_pending_call_steal_reply(call);

	dbus_error_init(&derr);
	if (dbus_set_error_from_message(&derr, reply)) {
		error("%s.ReadFirst replied with an error: %s, %s",
				CSD_SIMPB_INTERFACE, derr.name, derr.message);
		dbus_error_free(&derr);
		if (number_type == &vmbx)
			vmbx = g_strdup(getenv("VMBX_NUMBER"));
		goto done;
	}

	dbus_error_init(&derr);
	if (dbus_message_get_args(reply, NULL,
				DBUS_TYPE_INT32, &index,
				DBUS_TYPE_STRING, &name,
				DBUS_TYPE_STRING, &number,
				DBUS_TYPE_STRING, &secondname,
				DBUS_TYPE_STRING, &additionalnumber,
				DBUS_TYPE_STRING, &email,
				DBUS_TYPE_INVALID) == FALSE) {
		error("Unable to parse %s.ReadFirst arguments: %s, %s",
				CSD_SIMPB_INTERFACE, derr.name, derr.message);
		dbus_error_free(&derr);
		goto done;
	}

	if (number_type == &msisdn) {
		g_free(msisdn);
		msisdn = g_strdup(number);
		DBG("Got MSISDN %s (%s)", number, name);
	} else {
		g_free(vmbx);
		vmbx = g_strdup(number);
		DBG("Got voice mailbox number %s (%s)", number, name);
	}

done:
	dbus_message_unref(reply);
	remove_pending(call);
}

static void csd_init(void)
{
	const char *pb_type;
	int ret;

	ret = send_method_call(CSD_CALL_BUS_NAME, CSD_CALL_PATH,
				CSD_CALL_INTERFACE, "GetCallInfoAll",
				call_info_reply, NULL, DBUS_TYPE_INVALID);
	if (ret < 0) {
		error("Unable to sent GetCallInfoAll method call");
		return;
	}

	get_calls_active = TRUE;

	pb_type = CSD_SIMPB_TYPE_MSISDN;

	ret = send_method_call(CSD_SIMPB_BUS_NAME, CSD_SIMPB_PATH,
				CSD_SIMPB_INTERFACE, "ReadFirst",
				phonebook_read_reply, &msisdn,
				DBUS_TYPE_STRING, &pb_type,
				DBUS_TYPE_INVALID);
	if (ret < 0) {
		error("Unable to send " CSD_SIMPB_INTERFACE ".read()");
		return;
	}

	/* Voicemail should be in MBDN index 0 */
	pb_type = CSD_SIMPB_TYPE_MBDN;

	ret = send_method_call(CSD_SIMPB_BUS_NAME, CSD_SIMPB_PATH,
				CSD_SIMPB_INTERFACE, "ReadFirst",
				phonebook_read_reply, &vmbx,
				DBUS_TYPE_STRING, &pb_type,
				DBUS_TYPE_INVALID);
	if (ret < 0) {
		error("Unable to send " CSD_SIMPB_INTERFACE ".read()");
		return;
	}
}

static void handle_modem_state(DBusMessage *msg)
{
	const char *state;

	if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &state,
							DBUS_TYPE_INVALID)) {
		error("Unexpected modem state parameters");
		return;
	}

	DBG("SSC modem state: %s", state);

	if (calls != NULL || get_calls_active)
		return;

	if (g_str_equal(state, "cmt_ready") || g_str_equal(state, "online"))
		csd_init();
}

static void modem_state_reply(DBusPendingCall *call, void *user_data)
{
	DBusMessage *reply = dbus_pending_call_steal_reply(call);
	DBusError err;

	dbus_error_init(&err);
	if (dbus_set_error_from_message(&err, reply)) {
		error("get_modem_state: %s, %s", err.name, err.message);
		dbus_error_free(&err);
	} else
		handle_modem_state(reply);

	dbus_message_unref(reply);
	remove_pending(call);
}

static gboolean signal_filter(DBusConnection *conn, DBusMessage *msg,
								void *data)
{
	const char *path = dbus_message_get_path(msg);

	if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE, "Coming"))
		handle_incoming_call(msg);
	else if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE, "Created"))
		handle_outgoing_call(msg);
	else if (dbus_message_is_signal(msg, CSD_CALL_INTERFACE,
							"CreateRequested"))
		handle_create_requested(msg);
	else if (dbus_message_is_signal(msg, CSD_CALL_INSTANCE, "CallStatus"))
		handle_call_status(msg, path);
	else if (dbus_message_is_signal(msg, CSD_CALL_CONFERENCE, "Joined"))
		handle_conference(msg, TRUE);
	else if (dbus_message_is_signal(msg, CSD_CALL_CONFERENCE, "Left"))
		handle_conference(msg, FALSE);
	else if (dbus_message_is_signal(msg, CSD_CSNET_REGISTRATION,
				"RegistrationChanged"))
		handle_registration_changed(msg);
	else if (dbus_message_is_signal(msg, CSD_CSNET_OPERATOR,
				"OperatorNameChanged"))
		handle_operator_name_changed(msg);
	else if (dbus_message_is_signal(msg, CSD_CSNET_SIGNAL,
				"SignalBarsChanged"))
		handle_signal_bars_changed(msg);
	else if (dbus_message_is_signal(msg, "org.freedesktop.Hal.Device",
					"PropertyModified"))
		handle_hal_property_modified(msg);
	else if (dbus_message_is_signal(msg, SSC_DBUS_IFACE,
						"modem_state_changed_ind"))
		handle_modem_state(msg);

	return TRUE;
}

static void add_watch(const char *sender, const char *path,
				const char *interface, const char *member)
{
	guint watch;

	watch = g_dbus_add_signal_watch(connection, sender, path, interface,
					member, signal_filter, NULL, NULL);

	watches = g_slist_prepend(watches, GUINT_TO_POINTER(watch));
}

static void hal_find_device_reply(DBusPendingCall *call, void *user_data)
{
	DBusError err;
	DBusMessage *reply;
	DBusMessageIter iter, sub;
	const char *path;
	int type;

	reply = dbus_pending_call_steal_reply(call);

	dbus_error_init(&err);
	if (dbus_set_error_from_message(&err, reply)) {
		error("hald replied with an error: %s, %s",
				err.name, err.message);
		dbus_error_free(&err);
		goto done;
	}

	dbus_message_iter_init(reply, &iter);

	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) {
		error("Unexpected signature in FindDeviceByCapability return");
		goto done;
	}

	dbus_message_iter_recurse(&iter, &sub);

	type = dbus_message_iter_get_arg_type(&sub);

	if (type != DBUS_TYPE_OBJECT_PATH && type != DBUS_TYPE_STRING) {
		error("No hal device with battery capability found");
		goto done;
	}

	dbus_message_iter_get_basic(&sub, &path);

	DBG("telephony-maemo6: found battery device at %s", path);

	add_watch(NULL, path, "org.freedesktop.Hal.Device",
							"PropertyModified");

	hal_get_integer(path, "battery.charge_level.last_full", &battchg_last);
	hal_get_integer(path, "battery.charge_level.current", &battchg_cur);
	hal_get_integer(path, "battery.charge_level.design", &battchg_design);

done:
	dbus_message_unref(reply);
	remove_pending(call);
}

int telephony_init(void)
{
	const char *battery_cap = "battery";
	uint32_t features = AG_FEATURE_EC_ANDOR_NR |
				AG_FEATURE_INBAND_RINGTONE |
				AG_FEATURE_REJECT_A_CALL |
				AG_FEATURE_ENHANCED_CALL_STATUS |
				AG_FEATURE_ENHANCED_CALL_CONTROL |
				AG_FEATURE_EXTENDED_ERROR_RESULT_CODES |
				AG_FEATURE_THREE_WAY_CALLING;
	int i;

	DBG("");

	connection = dbus_bus_get(DBUS_BUS_SYSTEM, NULL);

	add_watch(NULL, NULL, CSD_CALL_INTERFACE, NULL);
	add_watch(NULL, NULL, CSD_CALL_INSTANCE, NULL);
	add_watch(NULL, NULL, CSD_CALL_CONFERENCE, NULL);
	add_watch(NULL, NULL, CSD_CSNET_REGISTRATION, "RegistrationChanged");
	add_watch(NULL, NULL, CSD_CSNET_OPERATOR, "OperatorNameChanged");
	add_watch(NULL, NULL, CSD_CSNET_SIGNAL, "SignalBarsChanged");
	add_watch(NULL, NULL, SSC_DBUS_IFACE, "modem_state_changed_ind");

	if (send_method_call(SSC_DBUS_NAME, SSC_DBUS_PATH, SSC_DBUS_IFACE,
					"get_modem_state", modem_state_reply,
					NULL, DBUS_TYPE_INVALID) < 0)
		error("Unable to send " SSC_DBUS_IFACE ".get_modem_state()");

	/* Reset indicators */
	for (i = 0; maemo_indicators[i].desc != NULL; i++) {
		if (g_str_equal(maemo_indicators[i].desc, "battchg"))
			maemo_indicators[i].val = 5;
		else
			maemo_indicators[i].val = 0;
	}

	telephony_ready_ind(features, maemo_indicators, BTRH_NOT_SUPPORTED,
								chld_str);
	if (send_method_call("org.freedesktop.Hal",
				"/org/freedesktop/Hal/Manager",
				"org.freedesktop.Hal.Manager",
				"FindDeviceByCapability",
				hal_find_device_reply, NULL,
				DBUS_TYPE_STRING, &battery_cap,
				DBUS_TYPE_INVALID) < 0)
		error("Unable to send HAL method call");

	return 0;
}

static void remove_watch(gpointer data)
{
	g_dbus_remove_watch(connection, GPOINTER_TO_UINT(data));
}

void telephony_exit(void)
{
	DBG("");

	g_free(net.operator_name);
	net.operator_name = NULL;

	net.status = NETWORK_REG_STATUS_UNKOWN;
	net.signal_bars = 0;

	g_slist_free(active_calls);
	active_calls = NULL;

	g_slist_foreach(calls, (GFunc) csd_call_free, NULL);
	g_slist_free(calls);
	calls = NULL;

	g_slist_foreach(pending, (GFunc) pending_req_finalize, NULL);
	g_slist_free(pending);
	pending = NULL;

	g_slist_foreach(watches, (GFunc) remove_watch, NULL);
	g_slist_free(watches);
	watches = NULL;

	dbus_connection_unref(connection);
	connection = NULL;

	telephony_deinit();
}
