/* (C) 2020 by Harald Welte <laforge@gnumonks.org>
 *
 * All Rights Reserved
 *
 * SPDX-License-Identifier: GPL-2.0+
 *
 * 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.
 *
 */

/* This is a remsim-client that provides an IFD_Handler (reader driver)
 * towards the PC/SC services.  This effectively allows any local PC/SC client
 * application to use a remote smartcard via osmo-remsim.
 *
 * In order to use this, you will need an /etc/reader.conf.d/osmo-remsim-client
 * file with the following content:
 *
 * 	FRIENDLYNAME "osmo-remsim-client"
 * 	DEVICENAME   0:0:192.168.11.10:9998
 *	LIBPATH      /usr/lib/pcsc/drivers/serial/libifd_remsim_client.so
 *
 * Where  DEVICENAME has the following format:
 * 	[ClientID:[SlotNr:[ServerIp:[ServerPort]]]]
 *
 */

#include <errno.h>
#include <unistd.h>
#include <pthread.h>

#include <osmocom/core/select.h>
#include <osmocom/core/application.h>
extern int osmo_ctx_init(const char *id);

#include "client.h"

/* ensure this current thread has an osmo_ctx and hence can use OTC_GLOBAL and friends */
static void ensure_osmo_ctx(void)
{
	if (!osmo_ctx)
		osmo_ctx_init("");
}

/* inter-thread messages between IFD thread and remsim-client thread */
enum itmsg_type {
	ITMSG_TYPE_NONE,

	/* card present? */
	ITMSG_TYPE_CARD_PRES_REQ,
	ITMSG_TYPE_CARD_PRES_RESP,

	/* obtain ATR */
	ITMSG_TYPE_ATR_REQ,
	ITMSG_TYPE_ATR_RESP,

	/* transceive APDU: Send C-APDU, receive R-APDU */
	ITMSG_TYPE_C_APDU_REQ,
	ITMSG_TYPE_R_APDU_IND,

	/* power off the card */
	ITMSG_TYPE_POWER_OFF_REQ,
	ITMSG_TYPE_POWER_OFF_RESP,

	/* power on the card */
	ITMSG_TYPE_POWER_ON_REQ,
	ITMSG_TYPE_POWER_ON_RESP,

	/* reset the card */
	ITMSG_TYPE_RESET_REQ,
	ITMSG_TYPE_RESET_RESP,
};

struct itmsg {
	enum itmsg_type type;
	uint16_t status;	/* 0 == success */
	uint16_t len;		/* length of 'data' */
	uint8_t data[0];
};

/* allocate + initialize msgb-wrapped inter-thread message (struct itmsg) */
struct msgb *itmsg_alloc(enum itmsg_type type, uint16_t status, const uint8_t *data, uint16_t len)
{
	struct msgb *msg = msgb_alloc_c(OTC_GLOBAL, sizeof(struct itmsg)+len, "Tx itmsg");
	struct itmsg *im;

	if (!msg)
		return NULL;

	im = (struct itmsg *) msgb_put(msg, sizeof(struct itmsg) + len);
	im->type = type;
	im->status = status;
	im->len = len;
	if (len)
		memcpy(im->data, data, len);

	return msg;
}

/***********************************************************************
 * remsim_client thread
 ***********************************************************************/

void __thread *talloc_asn1_ctx;

struct client_thread {
	/* bankd client runningi inside this thread */
	struct bankd_client *bc;

	/* inter-thread osmo-fd; communication with IFD/PCSC thread */
	struct osmo_fd it_ofd;
	struct llist_head it_msgq;

	/* ATR as received from remsim-bankd */
	uint8_t atr[ATR_SIZE_MAX];
	uint8_t atr_len;
};

/* configuration of client thread; passed in from IFD thread */
struct client_thread_cfg {
	const char *name;
	const char *server_host;
	int server_port;
	int client_id;
	int client_slot;
	int it_sock_fd;
};

/* enqueue a msgb (containg 'struct itmsg') towards the IFD-handler thread */
static void enqueue_to_ifd(struct client_thread *ct, struct msgb *msg)
{
	if (!msg)
		return;

	msgb_enqueue(&ct->it_msgq, msg);
	ct->it_ofd.when |= OSMO_FD_WRITE;
}

/***********************************************************************
 * frontend to remsim-client main FSM code
 ***********************************************************************/

int frontend_request_card_insert(struct bankd_client *bc)
{
	return 0;
}

int frontend_request_card_remove(struct bankd_client *bc)
{
	return 0;
}

int frontend_request_sim_remote(struct bankd_client *bc)
{
	return 0;
}

int frontend_request_sim_local(struct bankd_client *bc)
{
	return 0;
}

int frontend_request_modem_reset(struct bankd_client *bc)
{
	return 0;
}

int frontend_handle_card2modem(struct bankd_client *bc, const uint8_t *data, size_t len)
{
	struct client_thread *ct = bc->data;
	struct msgb *msg;

	OSMO_ASSERT(data);

	DEBUGP(DMAIN, "R-APDU: %s\n", osmo_hexdump(data, len));
	/* enqueue towards IFD thread */
	msg = itmsg_alloc(ITMSG_TYPE_R_APDU_IND, 0, data, len);
	OSMO_ASSERT(msg);
	enqueue_to_ifd(ct, msg);

	return 0;
}

int frontend_handle_set_atr(struct bankd_client *bc, const uint8_t *data, size_t len)
{
	struct client_thread *ct = bc->data;
	unsigned int atr_len;

	OSMO_ASSERT(data);

	DEBUGP(DMAIN, "SET_ATR: %s\n", osmo_hexdump(data, len));

	/* store ATR in local data structure until somebody needs it */
	atr_len = len;
	if (atr_len > sizeof(ct->atr))
		atr_len = sizeof(ct->atr);
	memcpy(ct->atr, data, atr_len);
	ct->atr_len = atr_len;

	return 0;
}

int frontend_handle_slot_status(struct bankd_client *bc, const SlotPhysStatus_t *sts)
{
	return 0;
}

int frontend_append_script_env(struct bankd_client *bc, char **env, int idx, size_t max_env)
{
	return idx;
}

/***********************************************************************
 * Incoming command from the user application
 ***********************************************************************/

/* handle a single msgb-wrapped 'struct itmsg' from the IFD-handler thread */
static void handle_it_msg(struct client_thread *ct, struct itmsg *itmsg)
{
	struct bankd_client *bc = ct->bc;
	struct msgb *tx = NULL;
	RsproPDU_t *pdu;
	BankSlot_t bslot;

	bank_slot2rspro(&bslot, &ct->bc->bankd_slot);

	switch (itmsg->type) {
	case ITMSG_TYPE_CARD_PRES_REQ:
		if (bc->bankd_conn.fi->state == 2 /*SRVC_ST_CONNECTED*/)
			tx = itmsg_alloc(ITMSG_TYPE_CARD_PRES_RESP, 0, NULL, 0);
		else
			tx = itmsg_alloc(ITMSG_TYPE_CARD_PRES_RESP, 0xffff, NULL, 0);
		OSMO_ASSERT(tx);
		break;

	case ITMSG_TYPE_ATR_REQ:
		/* respond to IFD */
		tx = itmsg_alloc(ITMSG_TYPE_ATR_RESP, 0, ct->atr, ct->atr_len);
		OSMO_ASSERT(tx);
		break;

	case ITMSG_TYPE_POWER_OFF_REQ:
		pdu = rspro_gen_ClientSlotStatusInd(bc->srv_conn.clslot, &bslot,
						    true, false, false, true);
		server_conn_send_rspro(&bc->bankd_conn, pdu);
		/* respond to IFD */
		tx = itmsg_alloc(ITMSG_TYPE_POWER_OFF_RESP, 0, NULL, 0);
		OSMO_ASSERT(tx);
		break;

	case ITMSG_TYPE_POWER_ON_REQ:
		pdu = rspro_gen_ClientSlotStatusInd(bc->srv_conn.clslot, &bslot,
						    false, true, true, true);
		server_conn_send_rspro(&bc->bankd_conn, pdu);
		/* respond to IFD */
		tx = itmsg_alloc(ITMSG_TYPE_POWER_ON_RESP, 0, NULL, 0);
		OSMO_ASSERT(tx);
		break;

	case ITMSG_TYPE_RESET_REQ:
		/* reset the [remote] card */
		pdu = rspro_gen_ClientSlotStatusInd(bc->srv_conn.clslot, &bslot,
						    true, true, true, true);
		server_conn_send_rspro(&bc->bankd_conn, pdu);
		/* and take it out of reset again */
		pdu = rspro_gen_ClientSlotStatusInd(bc->srv_conn.clslot, &bslot,
						    false, true, true, true);
		server_conn_send_rspro(&bc->bankd_conn, pdu);
		/* respond to IFD */
		tx = itmsg_alloc(ITMSG_TYPE_RESET_RESP, 0, NULL, 0);
		OSMO_ASSERT(tx);
		break;
	case ITMSG_TYPE_C_APDU_REQ:
		if (!bc->srv_conn.clslot) {
			LOGP(DMAIN, LOGL_ERROR, "Cannot send command; no client slot\n");
			/* FIXME: Response? */
			return;
		}

		/* Send CMD APDU to [remote] card */
		pdu = rspro_gen_TpduModem2Card(bc->srv_conn.clslot, &bslot, itmsg->data, itmsg->len);
		server_conn_send_rspro(&bc->bankd_conn, pdu);
		/* response will come in asynchronously */
		break;
	default:
		LOGP(DMAIN, LOGL_ERROR, "Unknown inter-thread msg type %u\n", itmsg->type);
		break;
	}

	if (tx)
		enqueue_to_ifd(ct, tx);

}

/* call-back function for inter-thread socket */
static int it_sock_fd_cb(struct osmo_fd *ofd, unsigned int what)
{
	struct client_thread *ct = ofd->data;
	int rc;

	if (what & OSMO_FD_READ) {
		struct msgb *msg = msgb_alloc_c(OTC_GLOBAL, 1024, "Rx it_fd");
		struct itmsg *itmsg;

		OSMO_ASSERT(msg);
		rc = read(ofd->fd, msg->tail, msgb_tailroom(msg));
		if (rc <= 0) {
			LOGP(DMAIN, LOGL_ERROR, "Error reading from inter-thread fd: %d\n", rc);
			pthread_exit(NULL);
		}
		msgb_put(msg, rc);
		itmsg = (struct itmsg *) msgb_data(msg);
		if (msgb_length(msg) < sizeof(*itmsg) ||
		    msgb_length(msg) < sizeof(*itmsg) + itmsg->len) {
			LOGP(DMAIN, LOGL_ERROR, "Dropping short inter-thread message\n");
		} else {
			handle_it_msg(ct, itmsg);
		}
		msgb_free(msg);
	}

	if (what & OSMO_FD_WRITE) {
		struct msgb *msg = msgb_dequeue(&ct->it_msgq);
		if (!msg) {
			/* last message: disable write events */
			ofd->when &= ~OSMO_FD_WRITE;
		} else {
			unsigned int len = msgb_length(msg);
			rc = write(ofd->fd, msgb_data(msg), len);
			msgb_free(msg);
			if (rc < len) {
				LOGP(DMAIN, LOGL_ERROR, "Short write on inter-thread fd: %d < %d\n",
				     rc, len);
			}
		}
	}


	return 0;
}

/* release all resources allocated by thread */
static void client_pthread_cleanup(void *arg)
{
	struct client_thread *ct = arg;

	LOGP(DMAIN, LOGL_INFO, "Cleaning up remsim-client thread\n");
	//FIXME remsim_client_destroy(ct->bc);
	ct->bc = NULL;
	msgb_queue_free(&ct->it_msgq);
	osmo_fd_unregister(&ct->it_ofd);
	close(ct->it_ofd.fd);
	ct->it_ofd.fd = -1;
	talloc_free(ct);
}

/* main function of remsim-client pthread */
static void *client_pthread_main(void *arg)
{
	struct client_thread_cfg *cfg = arg;
	struct client_config *ccfg;
	struct client_thread *ct;
	int rc;

	osmo_select_init();
	rc = osmo_ctx_init("client");
	OSMO_ASSERT(rc == 0);

	ct = talloc_zero(OTC_GLOBAL, struct client_thread);
	OSMO_ASSERT(ct);

	ccfg = client_config_init(ct);
	OSMO_ASSERT(ccfg);
	osmo_talloc_replace_string(ccfg, &ccfg->server_host, cfg->server_host);
	if (cfg->server_port >= 0)
		ccfg->server_port = cfg->server_port;
	ccfg->client_id = cfg->client_id;
	ccfg->client_slot = cfg->client_slot;

	if (!talloc_asn1_ctx)
	       talloc_asn1_ctx= talloc_named_const(ct, 0, "asn1");

	ct->bc = remsim_client_create(ct, cfg->name, "remsim_ifdhandler", ccfg);
	OSMO_ASSERT(ct->bc);
	ct->bc->data = ct;

	INIT_LLIST_HEAD(&ct->it_msgq);
	osmo_fd_setup(&ct->it_ofd, cfg->it_sock_fd, OSMO_FD_READ, &it_sock_fd_cb, ct, 0);
	osmo_fd_register(&ct->it_ofd);

	/* ensure we get properly cleaned up if cancelled */
	pthread_cleanup_push(client_pthread_cleanup, ct);

	osmo_fsm_inst_dispatch(ct->bc->srv_conn.fi, SRVC_E_ESTABLISH, NULL);

	while (1) {
		osmo_select_main(0);
	}

	pthread_cleanup_pop(1);
	return NULL;
}

/***********************************************************************
 * PC/SC ifd_handler API functions
 ***********************************************************************/

#include <ifdhandler.h>
#include <debuglog.h>

#include <sys/types.h>
#include <sys/socket.h>

static const struct value_string ifd_status_names[] = {
	OSMO_VALUE_STRING(IFD_SUCCESS),
	OSMO_VALUE_STRING(IFD_ERROR_TAG),
	OSMO_VALUE_STRING(IFD_ERROR_SET_FAILURE),
	OSMO_VALUE_STRING(IFD_ERROR_VALUE_READ_ONLY),
	OSMO_VALUE_STRING(IFD_ERROR_PTS_FAILURE),
	OSMO_VALUE_STRING(IFD_ERROR_NOT_SUPPORTED),
	OSMO_VALUE_STRING(IFD_PROTOCOL_NOT_SUPPORTED),
	OSMO_VALUE_STRING(IFD_ERROR_POWER_ACTION),
	OSMO_VALUE_STRING(IFD_ERROR_SWALLOW),
	OSMO_VALUE_STRING(IFD_ERROR_EJECT),
	OSMO_VALUE_STRING(IFD_ERROR_CONFISCATE),
	OSMO_VALUE_STRING(IFD_COMMUNICATION_ERROR),
	OSMO_VALUE_STRING(IFD_RESPONSE_TIMEOUT),
	OSMO_VALUE_STRING(IFD_NOT_SUPPORTED),
	OSMO_VALUE_STRING(IFD_ICC_PRESENT),
	OSMO_VALUE_STRING(IFD_ICC_NOT_PRESENT),
	OSMO_VALUE_STRING(IFD_NO_SUCH_DEVICE),
	OSMO_VALUE_STRING(IFD_ERROR_INSUFFICIENT_BUFFER),
	{ 0, NULL }
};

static const struct value_string ifd_tag_names[] = {
	OSMO_VALUE_STRING(TAG_IFD_ATR),
	OSMO_VALUE_STRING(TAG_IFD_SLOTNUM),
	OSMO_VALUE_STRING(TAG_IFD_SLOT_THREAD_SAFE),
	OSMO_VALUE_STRING(TAG_IFD_THREAD_SAFE),
	OSMO_VALUE_STRING(TAG_IFD_SLOTS_NUMBER),
	OSMO_VALUE_STRING(TAG_IFD_SIMULTANEOUS_ACCESS),
	OSMO_VALUE_STRING(TAG_IFD_POLLING_THREAD),
	OSMO_VALUE_STRING(TAG_IFD_POLLING_THREAD_KILLABLE),
	OSMO_VALUE_STRING(TAG_IFD_STOP_POLLING_THREAD),
	OSMO_VALUE_STRING(TAG_IFD_POLLING_THREAD_WITH_TIMEOUT),
	{ 0, NULL }
};

#define LOG_EXIT(Lun, r) \
	Log4(r == IFD_SUCCESS || r == IFD_ICC_NOT_PRESENT ? PCSC_LOG_DEBUG : PCSC_LOG_ERROR, \
	     "%s(0x%08lx) => %s\n", __func__, Lun, get_value_string(ifd_status_names, r))

#define LOG_EXITF(Lun, r, fmt, args...) \
	Log5(r == IFD_SUCCESS ? PCSC_LOG_DEBUG : PCSC_LOG_ERROR, \
	     "%s(0x%08lx) "fmt" => %s\n", __func__, Lun, ## args, get_value_string(ifd_status_names, r))

/* IFD side handle for a remsim-client [thread] */
struct ifd_client {
	/* the client pthread itself */
	pthread_t pthread;
	/* socket to talk to thread */
	int it_fd;
	/* configuration passed into the thread */
	struct client_thread_cfg cfg;
};

static struct msgb *ifd_xceive_client(struct ifd_client *ic, struct msgb *tx)
{
	struct msgb *rx = msgb_alloc_c(OTC_GLOBAL, 1024, "ifd_rx itmsg");
	struct itmsg *rx_it;
	int rc;

	rc = write(ic->it_fd, msgb_data(tx), msgb_length(tx));
	msgb_free(tx);
	if (rc < msgb_length(tx)) {
		Log2(PCSC_LOG_ERROR, "Short write IFD->client thread: %d\n", rc);
		msgb_free(rx);
		return NULL;
	}
	rc = read(ic->it_fd, rx->tail, msgb_tailroom(rx));
	if (rc <= 0) {
		Log2(PCSC_LOG_ERROR, "Short read IFD<-client thread: %d\n", rc);
		msgb_free(rx);
		return NULL;
	}
	msgb_put(rx, rc);
	rx_it = (struct itmsg *) msgb_data(rx);
	if (msgb_length(rx) < sizeof(*rx_it) + rx_it->len) {
		Log2(PCSC_LOG_ERROR, "Short itmsg IFD<-client thread: %d\n", msgb_length(rx));
		msgb_free(rx);
		return NULL;
	}
	return rx;
}

/* function called on IFD side to create socketpair + start remsim-client thread */
static struct ifd_client *create_ifd_client(const struct client_thread_cfg *cfg)
{
	struct ifd_client *ic = talloc_zero(OTC_GLOBAL, struct ifd_client);
	int sp[2];
	int rc;

	/* copy over configuration */
	ic->cfg = *cfg;

	/* create socket pair for communication between threads */
	rc = socketpair(AF_UNIX, SOCK_SEQPACKET, 0, sp);
	if (rc != 0) {
		talloc_free(ic);
		return NULL;
	}

	ic->it_fd = sp[0];
	ic->cfg.it_sock_fd = sp[1];

	/* start the thread */
	rc = pthread_create(&ic->pthread, NULL, client_pthread_main, &ic->cfg);
	if (rc != 0) {
		Log1(PCSC_LOG_ERROR, "Error creating remsim-client pthread\n");
		close(sp[0]);
		close(sp[1]);
		talloc_free(ic);
		return NULL;
	}

	return ic;
}

/* function called on IFD side to destroy (terminate) remsim-client thread */
static void destroy_ifd_client(struct ifd_client *ic)
{
	if (!ic)
		return;

	pthread_cancel(ic->pthread);
	pthread_join(ic->pthread, NULL);
}

#define MAX_SLOTS	256
static struct ifd_client *ifd_client[MAX_SLOTS];

#define LUN2SLOT(lun) ((lun) & 0xffff)
#define LUN2RDR(lun) ((lun) >> 16)


RESPONSECODE IFDHCreateChannel(DWORD Lun, DWORD Channel)
{
	return IFD_COMMUNICATION_ERROR;
}

RESPONSECODE IFDHCreateChannelByName(DWORD Lun, LPSTR DeviceName)
{
	struct ifd_client *ic;
	struct client_thread_cfg cfg = {
		.name = "fixme-name",
		.server_host = "127.0.0.1",
		.server_port = -1,
		.client_id = 0,
		.client_slot = 0,
	};
	char *r, *client_id, *slot_nr, *host, *port;

	if (LUN2RDR(Lun) != 0)
		return IFD_NO_SUCH_DEVICE;

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client))
		return IFD_NO_SUCH_DEVICE;

	ensure_osmo_ctx();

	client_id = strtok_r(DeviceName, ":", &r);
	if (!client_id)
		goto end_parse;
	cfg.client_id = atoi(client_id);

	slot_nr = strtok_r(NULL, ":", &r);
	if (!slot_nr)
		goto end_parse;
	cfg.client_slot = atoi(slot_nr);

	host = strtok_r(NULL, ":", &r);
	if (!host)
		goto end_parse;
	cfg.server_host = strdup(host);

	port = strtok_r(NULL, ":", &r);
	cfg.server_port = atoi(port);


end_parse:
	LOGP(DMAIN, LOGL_NOTICE, "remsim-client C%d:%d bankd=%s:%d\n",
		cfg.client_id, cfg.client_slot, cfg.server_host, cfg.server_port);

	ic = create_ifd_client(&cfg);
	if (ic) {
		ifd_client[LUN2SLOT(Lun)] = ic;
		return IFD_SUCCESS;
	} else
		return IFD_COMMUNICATION_ERROR;
}

RESPONSECODE IFDHControl(DWORD Lun, DWORD dwControlCode, PUCHAR TxBuffer, DWORD TxLength,
			 PUCHAR RxBuffer, DWORD RxLength, LPDWORD pdwBytesReturned)
{
	RESPONSECODE r = IFD_COMMUNICATION_ERROR;

	ensure_osmo_ctx();

	if (LUN2RDR(Lun) != 0) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client)) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	if (pdwBytesReturned)
		*pdwBytesReturned = 0;

	r = IFD_ERROR_NOT_SUPPORTED;
err:
	LOG_EXIT(Lun, r);
	return r;
}

RESPONSECODE IFDHCloseChannel(DWORD Lun)
{
	RESPONSECODE r = IFD_COMMUNICATION_ERROR;

	ensure_osmo_ctx();

	if (LUN2RDR(Lun) != 0) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client)) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	destroy_ifd_client(ifd_client[LUN2SLOT(Lun)]);
	ifd_client[LUN2SLOT(Lun)] = NULL;

	r = IFD_SUCCESS;
err:
	LOG_EXIT(Lun, r);
	return r;
}

RESPONSECODE IFDHGetCapabilities(DWORD Lun, DWORD Tag, PDWORD Length, PUCHAR Value)
{
	RESPONSECODE r = IFD_COMMUNICATION_ERROR;
	struct ifd_client *ic;
	struct msgb *rx, *tx;
	struct itmsg *rx_it;

	ensure_osmo_ctx();

	if (LUN2RDR(Lun) != 0) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client)) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	ic = ifd_client[LUN2SLOT(Lun)];
	if (!ic) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	if (!Length || !Value)
		goto err;

	switch (Tag) {
	case TAG_IFD_ATR:
		/* Return the ATR and its size */
		tx = itmsg_alloc(ITMSG_TYPE_ATR_REQ, 0, NULL, 0);
		OSMO_ASSERT(tx);
		rx = ifd_xceive_client(ic, tx);
		if (!rx) {
			r = IFD_NO_SUCH_DEVICE;
			goto err;
		}
		rx_it = (struct itmsg *)msgb_data(rx);
		if (*Length > rx_it->len)
			*Length = rx_it->len;
		memcpy(Value, rx_it->data, *Length);
		msgb_free(rx);
		break;
	case TAG_IFD_SIMULTANEOUS_ACCESS:
		/* Return the number of sessions (readers) the driver
		 * can handle in Value[0]. This is used for multiple
		 * readers sharing the same driver. */
		if (*Length < 1)
			goto err;
		*Value = 1;
		*Length = 1;
		break;
	case TAG_IFD_SLOTS_NUMBER:
		/* Return the number of slots in this reader in Value[0] */
		if (*Length < 1)
			goto err;
		*Value = 1;
		*Length = 1;
		break;
	case TAG_IFD_THREAD_SAFE:
		/* If the driver supports more than one reader (see
		 * TAG_IFD_SIMULTANEOUS_ACCESS above) this tag indicates
		 * if the driver supports access to multiple readers at
		 * the same time.  */
		if (*Length < 1)
			goto err;
		*Value = 0;
		*Length = 1;
		break;
	case TAG_IFD_SLOT_THREAD_SAFE:
		/* If the reader has more than one slot (see
		 * TAG_IFD_SLOTS_NUMBER above) this tag indicates if the
		 * driver supports access to multiple slots of the same
		 * reader at the same time. */
		if (*Length < 1)
			goto err;
		*Value = 0;
		*Length = 1;
		break;
	default:
		r = IFD_ERROR_TAG;
		goto err;
	}

	r = IFD_SUCCESS;

err:
	if (r != IFD_SUCCESS && Length)
		*Length = 0;

	LOG_EXITF(Lun, r, "%s", get_value_string(ifd_tag_names, Tag));
	return r;
}

RESPONSECODE IFDHSetCapabilities(DWORD Lun, DWORD Tag, DWORD Length, PUCHAR Value)
{
	ensure_osmo_ctx();

	if (LUN2RDR(Lun) != 0)
		return IFD_NO_SUCH_DEVICE;

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client))
		return IFD_NO_SUCH_DEVICE;


	LOG_EXIT(Lun, IFD_NOT_SUPPORTED);
	return IFD_NOT_SUPPORTED;
}

RESPONSECODE IFDHSetProtocolParameters(DWORD Lun, DWORD Protocol, UCHAR Flags, UCHAR PTS1,
					UCHAR PTS2, UCHAR PTS3)
{
	ensure_osmo_ctx();

	if (LUN2RDR(Lun) != 0)
		return IFD_NO_SUCH_DEVICE;

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client))
		return IFD_NO_SUCH_DEVICE;

	LOG_EXIT(Lun, IFD_SUCCESS);
	return IFD_SUCCESS;
}

RESPONSECODE IFDHPowerICC(DWORD Lun, DWORD Action, PUCHAR Atr, PDWORD AtrLength)
{
	RESPONSECODE r = IFD_COMMUNICATION_ERROR;
	struct ifd_client *ic;
	struct msgb *rx, *tx;

	ensure_osmo_ctx();

	if (LUN2RDR(Lun) != 0) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client)) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	ic = ifd_client[LUN2SLOT(Lun)];
	if (!ic) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	switch (Action) {
	case IFD_POWER_DOWN:
		tx = itmsg_alloc(ITMSG_TYPE_POWER_OFF_REQ, 0, NULL, 0);
		break;
	case IFD_POWER_UP:
		tx = itmsg_alloc(ITMSG_TYPE_POWER_ON_REQ, 0, NULL, 0);
		break;
	case IFD_RESET:
		tx = itmsg_alloc(ITMSG_TYPE_RESET_REQ, 0, NULL, 0);
		break;
	default:
		r = IFD_NOT_SUPPORTED;
		goto err;
	}

	rx = ifd_xceive_client(ic, tx);
	if (!rx) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	r = IFD_SUCCESS;
	msgb_free(rx);

err:
	if (r != IFD_SUCCESS && AtrLength)
		*AtrLength = 0;
	else
		r = IFDHGetCapabilities(Lun, TAG_IFD_ATR, AtrLength, Atr);

	LOG_EXIT(Lun, r);
	return r;
}

RESPONSECODE IFDHTransmitToICC(DWORD Lun, SCARD_IO_HEADER SendPci, PUCHAR TxBuffer,
			       DWORD TxLength, PUCHAR RxBuffer, PDWORD RxLength,
			       PSCARD_IO_HEADER RecvPci)
{
	RESPONSECODE r = IFD_COMMUNICATION_ERROR;
	struct ifd_client *ic;
	struct msgb *rx, *tx;
	struct itmsg *rx_it;

	ensure_osmo_ctx();

	if (LUN2RDR(Lun) != 0) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client)) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	ic = ifd_client[LUN2SLOT(Lun)];
	if (!ic) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	tx = itmsg_alloc(ITMSG_TYPE_C_APDU_REQ, 0, TxBuffer, TxLength);
	OSMO_ASSERT(tx);
	/* transmit C-APDU to remote reader + blocking wait for response from peer */
	rx = ifd_xceive_client(ic, tx);
	if (!rx) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}
	rx_it = (struct itmsg *) msgb_data(rx);
	if (*RxLength > rx_it->len)
		*RxLength = rx_it->len;
	memcpy(RxBuffer, rx_it->data, *RxLength);
	msgb_free(rx);

	r = IFD_SUCCESS;
err:
	if (r != IFD_SUCCESS && RxLength)
		*RxLength = 0;

	LOG_EXIT(Lun, r);
	return r;
}

RESPONSECODE IFDHICCPresence(DWORD Lun)
{
	RESPONSECODE r = IFD_COMMUNICATION_ERROR;
	struct ifd_client *ic;
	struct msgb *rx, *tx;
	struct itmsg *rx_it;

	ensure_osmo_ctx();

	if (LUN2RDR(Lun) != 0) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	if (LUN2SLOT(Lun) >= ARRAY_SIZE(ifd_client)) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	ic = ifd_client[LUN2SLOT(Lun)];
	if (!ic) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}

	tx = itmsg_alloc(ITMSG_TYPE_CARD_PRES_REQ, 0, NULL, 0);
	OSMO_ASSERT(tx);
	rx = ifd_xceive_client(ic, tx);
	if (!rx) {
		r = IFD_NO_SUCH_DEVICE;
		goto err;
	}
	rx_it = (struct itmsg *) msgb_data(rx);
	if (rx_it->status == 0)
		r = IFD_SUCCESS;
	else
		r = IFD_ICC_NOT_PRESENT;

err:
	LOG_EXIT(Lun, r);
	return r;
}

static __attribute__((constructor)) void on_dso_load_ifd(void)
{
	void *g_tall_ctx = NULL;
	ensure_osmo_ctx();
	osmo_init_logging2(g_tall_ctx, &log_info);
}
