/* OpenBSC Abis interface to E1 */

/* (C) 2008-2009 by Harald Welte <laforge@gnumonks.org>
 *
 * All Rights Reserved
 *
 * SPDX-License-Identifier: AGPL-3.0+
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License as published by
 * the Free Software Foundation; either version 3 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 Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 */

#include "internal.h"
#include "../config.h"

#include <stdio.h>
#include <unistd.h>
#include <inttypes.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <time.h>
#include <fcntl.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <arpa/inet.h>

#include <osmocom/abis/lapd.h>

#include <osmocom/core/linuxlist.h>
#include <osmocom/core/talloc.h>
#include <osmocom/core/rate_ctr.h>
#include <osmocom/core/logging.h>
#include <osmocom/core/signal.h>
#include <osmocom/core/endian.h>
#include <osmocom/gsm/i460_mux.h>
#include <osmocom/abis/e1_input.h>

#define NUM_E1_TS	32

static void *tall_e1inp_ctx;

/* list of all E1 drivers */
LLIST_HEAD(e1inp_driver_list);

/* list of all E1 lines */
LLIST_HEAD(e1inp_line_list);

static void *tall_sigl_ctx;

static const struct rate_ctr_desc e1inp_ctr_d[] = {
	[E1I_CTR_HDLC_ABORT]  = {
		"hdlc:abort", 	"HDLC abort"
	},
	[E1I_CTR_HDLC_BADFCS] = {
		"hdlc:bad_fcs",	"HLDC Bad FCS"
	},
	[E1I_CTR_HDLC_OVERR]  = {
		"hdlc:overrun",	"HDLC Overrun"
	},
	[E1I_CTR_ALARM] = {
		"alarm", 	"Alarm"
	},
	[E1I_CTR_REMOVED] = {
		"removed", 	"Line removed"
	},
};

static const struct rate_ctr_group_desc e1inp_ctr_g_d = {
	.group_name_prefix = "e1inp",
	.group_description = "E1 Input subsystem",
	.num_ctr = ARRAY_SIZE(e1inp_ctr_d),
	.ctr_desc = e1inp_ctr_d,
};

/*
 * pcap writing of the misdn load
 * pcap format is from http://wiki.wireshark.org/Development/LibpcapFileFormat
 */
#define DLT_LINUX_LAPD		177
#define PCAP_INPUT		0
#define PCAP_OUTPUT		1

struct pcap_hdr {
	uint32_t magic_number;
	uint16_t version_major;
	uint16_t version_minor;
	int32_t  thiszone;
	uint32_t sigfigs;
	uint32_t snaplen;
	uint32_t network;
} __attribute__((packed));

struct pcaprec_hdr {
	uint32_t ts_sec;
	uint32_t ts_usec;
	uint32_t incl_len;
	uint32_t orig_len;
} __attribute__((packed));

struct fake_linux_lapd_header {
        uint16_t pkttype;
	uint16_t hatype;
	uint16_t halen;
	uint64_t addr;
	int16_t protocol;
} __attribute__((packed));

struct lapd_header {
#if OSMO_IS_LITTLE_ENDIAN
	uint8_t ea1 : 1;
	uint8_t cr : 1;
	uint8_t sapi : 6;
	uint8_t ea2 : 1;
	uint8_t tei : 7;
	uint8_t control_foo; /* fake UM's ... */
#elif OSMO_IS_BIG_ENDIAN
/* auto-generated from the little endian part above (libosmocore/contrib/struct_endianess.py) */
	uint8_t sapi:6, cr:1, ea1:1;
	uint8_t tei:7, ea2:1;
	uint8_t control_foo;
#endif
} __attribute__((packed));

osmo_static_assert(offsetof(struct fake_linux_lapd_header, hatype) == 2,    hatype_offset);
osmo_static_assert(offsetof(struct fake_linux_lapd_header, halen) == 4,     halen_offset);
osmo_static_assert(offsetof(struct fake_linux_lapd_header, addr) == 6,      addr_offset);
osmo_static_assert(offsetof(struct fake_linux_lapd_header, protocol) == 14, proto_offset);
osmo_static_assert(sizeof(struct fake_linux_lapd_header) == 16,	       lapd_header_size);

int e1_set_pcap_fd2(struct e1inp_line *line, int fd)
{
	static const struct pcap_hdr header = {
		.magic_number	= 0xa1b2c3d4,
		.version_major	= 2,
		.version_minor	= 4,
		.thiszone	= 0,
		.sigfigs	= 0,
		.snaplen	= 65535,
		.network	= DLT_LINUX_LAPD,
	};
	int i;

	/* write header */
	if (fd >= 0) {
		int rc = write(fd, &header, sizeof(header));
		if (rc < 0)
			return rc;
	}

	/* Set the PCAP file descriptor for all timeslots that have
	 * software LAPD instances, to ensure the osmo_lapd_pcap code is
	 * used to write PCAP files (if requested) */
	for (i = 0; i < ARRAY_SIZE(line->ts); i++) {
		struct e1inp_ts *e1i_ts = &line->ts[i];
		if (e1i_ts->lapd)
			e1i_ts->lapd->pcap_fd = fd;
	}
	/* close previous and update */
	if (line->pcap_fd >= 0)
		close(line->pcap_fd);
	line->pcap_fd = fd;
	return 0;
}

static int pcap_fd = -1;

int e1_set_pcap_fd(int fd)
{
	const struct pcap_hdr header = {
		.magic_number	= 0xa1b2c3d4,
		.version_major	= 2,
		.version_minor	= 4,
		.thiszone	= 0,
		.sigfigs	= 0,
		.snaplen	= 65535,
		.network	= DLT_LINUX_LAPD,
	};
	struct e1inp_line *line;
	int i;

	/* write header */
	if (fd >= 0) {
		int rc = write(fd, &header, sizeof(header));
		if (rc < 0)
			return rc;
	}

	/* update fd in all lines in our global list of e1 lines */
	llist_for_each_entry(line, &e1inp_line_list, list) {
		/* Set the PCAP file descriptor for all timeslots that have
		 * software LAPD instances, to ensure the osmo_lapd_pcap code is
		 * used to write PCAP files (if requested) */
		for (i = 0; i < ARRAY_SIZE(line->ts); i++) {
			struct e1inp_ts *e1i_ts = &line->ts[i];
			if (e1i_ts->lapd)
				e1i_ts->lapd->pcap_fd = fd;
		}
	}

	/* close previous and update global */
	if (pcap_fd >= 0)
		close(pcap_fd);
	pcap_fd = fd;

	return 0;
}

/* This currently only works for the D-Channel */
static void write_pcap_packet(int direction, int sapi, int tei,
			      struct msgb *msg, int pcap_fd) {
	if (pcap_fd < 0)
		return;

	time_t cur_time;
	struct tm *tm;

	struct fake_linux_lapd_header header = {
		.pkttype	= 4,
		.hatype		= 0,
		.halen		= 0,
		.addr		= direction == PCAP_OUTPUT ? 0x0 : 0x1,
		.protocol	= ntohs(48),
	};

	struct lapd_header lapd_header = {
		.ea1		= 0,
		.cr		= direction == PCAP_OUTPUT ? 1 : 0,
		.sapi		= sapi & 0x3F,
		.ea2		= 1,
		.tei		= tei & 0x7F,
		.control_foo	= 0x03 /* UI */,
	};

	struct pcaprec_hdr payload_header = {
		.ts_sec	    = 0,
		.ts_usec    = 0,
		.incl_len   = msgb_l2len(msg) + sizeof(struct fake_linux_lapd_header)
				+ sizeof(struct lapd_header),
		.orig_len   = msgb_l2len(msg) + sizeof(struct fake_linux_lapd_header)
				+ sizeof(struct lapd_header),
	};


	cur_time = time(NULL);
	tm = localtime(&cur_time);
	payload_header.ts_sec = mktime(tm);

	write(pcap_fd, &payload_header, sizeof(payload_header));
	write(pcap_fd, &header, sizeof(header));
	write(pcap_fd, &lapd_header, sizeof(lapd_header));
	write(pcap_fd, msg->l2h, msgb_l2len(msg));
}

const struct value_string e1inp_sign_type_names[5] = {
	{ E1INP_SIGN_NONE,	"None" },
	{ E1INP_SIGN_OML,	"OML" },
	{ E1INP_SIGN_RSL,	"RSL" },
	{ E1INP_SIGN_OSMO,	"OSMO" },
	{ 0, NULL }
};

const char *e1inp_signtype_name(enum e1inp_sign_type tp)
{
	return get_value_string(e1inp_sign_type_names, tp);
}

const struct value_string e1inp_ts_type_names[] = {
	{ E1INP_TS_TYPE_NONE,	"None" },
	{ E1INP_TS_TYPE_SIGN,	"Signalling" },
	{ E1INP_TS_TYPE_TRAU,	"TRAU" },
	{ E1INP_TS_TYPE_RAW,	"RAW" },
	{ E1INP_TS_TYPE_HDLC,	"HDLC" },
	{ E1INP_TS_TYPE_I460,	"I460" },
	{ 0, NULL }
};

const char *e1inp_tstype_name(enum e1inp_ts_type tp)
{
	return get_value_string(e1inp_ts_type_names, tp);
}

int abis_sendmsg(struct msgb *msg)
{
	struct e1inp_sign_link *sign_link = msg->dst;
	struct e1inp_driver *e1inp_driver;
	struct e1inp_ts *e1i_ts;

	msg->l2h = msg->data;

	/* don't know how to route this message. */
	if (sign_link == NULL) {
		LOGP(DLINP, LOGL_ERROR, "abis_sendmsg: msg->dst == NULL: %s\n",
			osmo_hexdump(msg->data, msg->len));
		talloc_free(msg);
		return -EINVAL;
	}
	e1i_ts = sign_link->ts;
	if (!osmo_timer_pending(&e1i_ts->sign.tx_timer)) {
		/* notify the driver we have something to write */
		e1inp_driver = sign_link->ts->line->driver;
		e1inp_driver->want_write(e1i_ts);
	}
	msgb_enqueue(&sign_link->tx_list, msg);

	/* we only need to write a 'Fake LAPD' packet here, if the
	 * underlying driver hides LAPD from us.  If we use the
	 * libosmocore LAPD implementation, it will take care of writing
	 * the _actual_ LAPD packet */
	if (!e1i_ts->lapd) {
		write_pcap_packet(PCAP_OUTPUT, sign_link->sapi,
				  sign_link->tei, msg, e1i_ts->line->pcap_fd);
	}

	return 0;
}

int abis_rsl_sendmsg(struct msgb *msg)
{
	return abis_sendmsg(msg);
}

/* Timeslot */
int e1inp_ts_config_trau(struct e1inp_ts *ts, struct e1inp_line *line,
			 int (*trau_rcv_cb)(struct subch_demux *dmx, int ch,
					const ubit_t *data, int len, void *_priv))
{
	if (ts->type == E1INP_TS_TYPE_TRAU && ts->line && line)
		return 0;

	ts->type = E1INP_TS_TYPE_TRAU;
	ts->line = line;

	subchan_mux_init(&ts->trau.mux);
	ts->trau.demux.out_cb = trau_rcv_cb;
	ts->trau.demux.data = ts;
	subch_demux_init(&ts->trau.demux);
	return 0;
}

int e1inp_ts_config_i460(struct e1inp_ts *ts, struct e1inp_line *line)
{
	if (ts->type == E1INP_TS_TYPE_I460 && ts->line && line)
		return 0;

	ts->type = E1INP_TS_TYPE_I460;
	ts->line = line;
	osmo_i460_ts_init(&ts->i460.i460_ts);
	return 0;
}

void e1inp_ts_name(char *out, size_t out_len, const struct e1inp_ts *ts)
{
	if (ts->line->name)
		snprintf(out, out_len, "%s:%u", ts->line->name, ts->num);
	else
		snprintf(out, out_len, "%u:%u", ts->line->num, ts->num);
}

int e1inp_ts_config_sign(struct e1inp_ts *ts, struct e1inp_line *line)
{
	if (ts->type == E1INP_TS_TYPE_SIGN && ts->line && line)
		return 0;

	ts->type = E1INP_TS_TYPE_SIGN;
	ts->line = line;

	if (line && line->driver)
		ts->sign.delay = line->driver->default_delay;
	else
		ts->sign.delay = 100000;
	INIT_LLIST_HEAD(&ts->sign.sign_links);
	return 0;
}

int e1inp_ts_config_raw(struct e1inp_ts *ts, struct e1inp_line *line,
			void (*raw_recv_cb)(struct e1inp_ts *ts,
					    struct msgb *msg))
{
	if (ts->type == E1INP_TS_TYPE_RAW && ts->line && line)
		return 0;

	ts->type = E1INP_TS_TYPE_RAW;
	ts->line = line;
	ts->raw.recv_cb = raw_recv_cb;
	INIT_LLIST_HEAD(&ts->raw.tx_queue);

	return 0;
}

int e1inp_ts_config_hdlc(struct e1inp_ts *ts, struct e1inp_line *line,
			 void (*hdlc_recv_cb)(struct e1inp_ts *ts,
					      struct msgb *msg))
{
	if (ts->type == E1INP_TS_TYPE_HDLC && ts->line && line)
		return 0;

	ts->type = E1INP_TS_TYPE_HDLC;
	ts->line = line;
	ts->hdlc.recv_cb = hdlc_recv_cb;
	INIT_LLIST_HEAD(&ts->hdlc.tx_queue);

	return 0;
}

static int e1inp_line_use_cb(struct osmo_use_count_entry *use_count_entry, int32_t old_use_count,
			     const char *file, int file_line)
{
	char buf[512];
	struct osmo_use_count *uc = use_count_entry->use_count;
	struct e1inp_line *line = uc->talloc_object;

	LOGPSRC(DLINP, LOGL_INFO, file, file_line,
		"E1L(%u) Line (%p) reference count %s changed %" PRId32 " -> %" PRId32 " [%s]\n",
		(line)->num, line, use_count_entry->use,
		old_use_count, use_count_entry->count,
		osmo_use_count_name_buf(buf, sizeof(buf), uc));

	if (!use_count_entry->count)
		osmo_use_count_free(use_count_entry);

	if (osmo_use_count_total(uc) > 0)
		return 0;

	/* Remove our counter group from libosmocore's global counter
	 * list if we are freeing the last remaining talloc context.
	 * Otherwise we get a use-after-free when libosmocore's timer
	 * ticks again and attempts to update these counters (OS#3011).
	 *
	 * Note that talloc internally counts "secondary" references
	 * _in addition to_ the initial allocation context, so yes,
	 * we must check for *zero* remaining secondary contexts here. */
	if (talloc_reference_count(line->rate_ctr) == 0) {
		rate_ctr_group_free(line->rate_ctr);
	} else {
		/* We are not freeing the last talloc context.
		 * Instead of calling talloc_free(), unlink this 'line' pointer
		 * which serves as one of several talloc contexts for the rate
		 * counters and driver private state. */
		talloc_unlink(line, line->rate_ctr);
		if (line->driver_data)
			talloc_unlink(line, line->driver_data);
	}

	llist_del(&line->list);
	talloc_free(line);
	return 0;
}

struct e1inp_line *e1inp_line_find(uint8_t e1_nr)
{
	struct e1inp_line *e1i_line;

	/* iterate over global list of e1 lines */
	llist_for_each_entry(e1i_line, &e1inp_line_list, list) {
		if (e1i_line->num == e1_nr)
			return e1i_line;
	}
	return NULL;
}

/*! Create a new e1inp line object.
 * \param[in] e1_nr The line number of the new line to be created.
 * \param[in] driver_name String identifying the driver (see e1inp_driver_register() for more info).
 * \returns pointer to the new object created.
 *
 * The allocated object is returned with a count reference with name "ctor",
 * which must be dropped in order to free the object [e1inp_line_put2(line, "ctor")].
 */
struct e1inp_line *
e1inp_line_create(uint8_t e1_nr, const char *driver_name)
{
	struct e1inp_driver *driver;
	struct e1inp_line *line;
	int i;

	line = e1inp_line_find(e1_nr);
	if (line) {
		LOGPIL(line, DLINP, LOGL_ERROR, "E1 Line %u already exists\n", e1_nr);
		return NULL;
	}

	driver = e1inp_driver_find(driver_name);
	if (!driver) {
		LOGP(DLINP, LOGL_ERROR, "No such E1 driver '%s'\n",
		     driver_name);
		return NULL;
	}

	line = talloc_zero(tall_e1inp_ctx, struct e1inp_line);
	if (!line)
		return NULL;

	line->driver = driver;
	line->num = e1_nr;
	line->pcap_fd = -1;

	line->rate_ctr = rate_ctr_group_alloc(line, &e1inp_ctr_g_d, line->num);
	if (!line->rate_ctr) {
		LOGPIL(line, DLINP, LOGL_ERROR, "Cannot allocate counter group\n");
		talloc_free(line);
		return NULL;
	}

	line->num_ts = NUM_E1_TS;
	for (i = 0; i < line->num_ts; i++) {
		line->ts[i].num = i+1;
		line->ts[i].line = line;
	}

	line->use_count.talloc_object = line;
	line->use_count.use_cb = e1inp_line_use_cb;
	e1inp_line_get2(line, "ctor");

	llist_add_tail(&line->list, &e1inp_line_list);

	return line;
}

struct e1inp_line *
e1inp_line_clone(void *ctx, struct e1inp_line *line, const char *use)
{
	struct e1inp_line *clone;

	/* clone virtual E1 line for this new OML link. */
	clone = talloc_zero(ctx, struct e1inp_line);
	if (clone == NULL)
	        return NULL;

	memcpy(clone, line, sizeof(struct e1inp_line));

	if (line->name) {
		clone->name = talloc_strdup(clone, line->name);
		OSMO_ASSERT(clone->name);
	}
	if (line->sock_path) {
		clone->sock_path = talloc_strdup(clone, line->sock_path);
		OSMO_ASSERT(clone->sock_path);
	}

	/*
	 * Rate counters and driver data are shared between clones. These are pointers
	 * to dynamic memory so we use reference counting to avoid a double-free (see OS#3137).
	 */
	OSMO_ASSERT(line->rate_ctr);
	clone->rate_ctr = talloc_reference(clone, line->rate_ctr);
	if (line->driver_data)
		clone->driver_data = talloc_reference(clone, line->driver_data);

	clone->use_count = (struct osmo_use_count) {
		.talloc_object = clone,
		.use_cb = e1inp_line_use_cb,
		.use_counts = {0},
	};
	/* initialize list so it can be safely deleted without affecting original line */
	INIT_LLIST_HEAD(&clone->list);
	e1inp_line_get2(clone, use); /* Clone is used internally for bfd */
	return clone;
}

void e1inp_line_get(struct e1inp_line *line)
{
	e1inp_line_get2(line, "unknown");
}

void e1inp_line_put(struct e1inp_line *line)
{
	e1inp_line_put2(line, "unknown");
}

void
e1inp_line_bind_ops(struct e1inp_line *line, const struct e1inp_line_ops *ops)
{
	line->ops = ops;
}

#if 0
struct e1inp_line *e1inp_line_find_create(uint8_t e1_nr)
{
	struct e1inp_line *line;
	int i;

	line = e1inp_line_find(e1_nr);
	if (line)
		return line;

	line = talloc_zero(tall_e1inp_ctx, struct e1inp_line);
	if (!line)
		return NULL;

	line->num = e1_nr;
	for (i = 0; i < NUM_E1_TS; i++) {
		line->ts[i].num = i+1;
		line->ts[i].line = line;
	}
	llist_add_tail(&line->list, &e1inp_line_list);

	return line;
}
#endif

static struct e1inp_ts *e1inp_ts_get(uint8_t e1_nr, uint8_t ts_nr)
{
	struct e1inp_line *e1i_line;

	e1i_line = e1inp_line_find(e1_nr);
	if (!e1i_line)
		return NULL;

	return &e1i_line->ts[ts_nr-1];
}

struct subch_mux *e1inp_get_mux(uint8_t e1_nr, uint8_t ts_nr)
{
	struct e1inp_ts *e1i_ts = e1inp_ts_get(e1_nr, ts_nr);

	if (!e1i_ts)
		return NULL;

	return &e1i_ts->trau.mux;
}

/* Signalling Link */

struct e1inp_sign_link *e1inp_lookup_sign_link(struct e1inp_ts *e1i,
						uint8_t tei, uint8_t sapi)
{
	struct e1inp_sign_link *link;

	llist_for_each_entry(link, &e1i->sign.sign_links, list) {
		if (link->sapi == sapi && link->tei == tei)
			return link;
	}

	return NULL;
}

/* create a new signalling link in a E1 timeslot */

struct e1inp_sign_link *
e1inp_sign_link_create(struct e1inp_ts *ts, enum e1inp_sign_type type,
			struct gsm_bts_trx *trx, uint8_t tei,
			uint8_t sapi)
{
	struct e1inp_sign_link *link;

	if (ts->type != E1INP_TS_TYPE_SIGN)
		return NULL;

	link = talloc_zero(tall_sigl_ctx, struct e1inp_sign_link);
	if (!link)
		return NULL;

	link->ts = ts;
	link->type = type;
	INIT_LLIST_HEAD(&link->tx_list);
	link->trx = trx;
	link->tei = tei;
	link->sapi = sapi;

	e1inp_line_get2(link->ts->line, "e1inp_sign_link");

	llist_add_tail(&link->list, &ts->sign.sign_links);

	return link;
}

void e1inp_sign_link_destroy(struct e1inp_sign_link *link)
{
	struct msgb *msg;

	llist_del(&link->list);
	while (!llist_empty(&link->tx_list)) {
		msg = msgb_dequeue(&link->tx_list);
		msgb_free(msg);
	}

	if (link->ts->type == E1INP_TS_TYPE_SIGN)
		osmo_timer_del(&link->ts->sign.tx_timer);

	if (link->ts->line->driver->close)
		link->ts->line->driver->close(link);

	e1inp_line_put2(link->ts->line, "e1inp_sign_link");
	talloc_free(link);
}

/* XXX */
/* the E1 driver tells us he has received something on a TS */
int e1inp_rx_ts(struct e1inp_ts *ts, struct msgb *msg,
		uint8_t tei, uint8_t sapi)
{
	struct e1inp_sign_link *link;
	int ret = 0;

	switch (ts->type) {
	case E1INP_TS_TYPE_SIGN:
		/* we only need to write a 'Fake LAPD' packet here, if
		 * the underlying driver hides LAPD from us.  If we use
		 * the libosmocore LAPD implementation, it will take
		 * care of writing the _actual_ LAPD packet */
		if (!ts->lapd)
			write_pcap_packet(PCAP_INPUT, sapi, tei, msg, ts->line->pcap_fd);
		/* consult the list of signalling links */
		link = e1inp_lookup_sign_link(ts, tei, sapi);
		if (!link) {
			LOGPITS(ts, DLMI, LOGL_ERROR, "didn't find signalling link for "
				"tei %d, sapi %d\n", tei, sapi);
			msgb_free(msg);
			return -EINVAL;
		}
		if (!ts->line->ops->sign_link) {
	                LOGPITS(ts, DLINP, LOGL_ERROR, "Fix your application, "
				"no action set for signalling messages.\n");
			msgb_free(msg);
			return -ENOENT;
		}
		msg->dst = link;
		ts->line->ops->sign_link(msg);
		break;
	case E1INP_TS_TYPE_TRAU:
		ret = subch_demux_in(&ts->trau.demux, msg->l2h, msgb_l2len(msg));
		msgb_free(msg);
		break;
	case E1INP_TS_TYPE_RAW:
		ts->raw.recv_cb(ts, msg);
		break;
	case E1INP_TS_TYPE_HDLC:
		ts->hdlc.recv_cb(ts, msg);
		break;
	case E1INP_TS_TYPE_I460:
		osmo_i460_demux_in(&ts->i460.i460_ts, msg->l2h, msgb_l2len(msg));
		msgb_free(msg);
		break;
	default:
		ret = -EINVAL;
		LOGPITS(ts, DLMI, LOGL_ERROR, "unknown TS type %u\n", ts->type);
		msgb_free(msg);
		break;
	}

	return ret;
}

/*! \brief Receive some data from the L1/HDLC into LAPD of a timeslot
 *  \param[in] e1i_ts E1 Timeslot data structure
 *  \param[in] msg Message buffer containing full LAPD message
 *
 * This is a wrapper around e1inp_rx_ts(), but feeding the incoming
 * message first into our LAPD code.  This allows a driver to read raw
 * (HDLC decoded) data from the timeslot, instead of a LAPD stack
 * present in any underlying driver.
 */
int e1inp_rx_ts_lapd(struct e1inp_ts *e1i_ts, struct msgb *msg)
{
	unsigned int sapi, tei;
	int ret = 0, error = 0;

	sapi = msg->data[0] >> 2;
	if ((msg->data[0] & 0x1))
		tei = 0;
	else
		tei = msg->data[1] >> 1;

	LOGPITS(e1i_ts, DLMI, LOGL_DEBUG, "<= len = %d, sapi(%d) tei(%d)\n", msg->len, sapi, tei);

	ret = lapd_receive(e1i_ts->lapd, msg, &error);
	if (ret < 0) {
		switch(error) {
		case LAPD_ERR_UNKNOWN_TEI:
			/* We don't know about this TEI, probably the BSC
			 * lost local states (it crashed or it was stopped),
			 * notify the driver to see if it can do anything to
			 * recover the existing signalling links with the BTS.
			 */
			e1inp_event(e1i_ts, S_L_INP_TEI_UNKNOWN, tei, sapi);
			return -EIO;
		}
	}

	return 0;
}

void e1inp_dlsap_up(struct osmo_dlsap_prim *dp, uint8_t tei, uint8_t sapi,
        void *rx_cbdata)
{
	struct e1inp_ts *e1i_ts = rx_cbdata;
	struct msgb *msg = dp->oph.msg;

	switch (dp->oph.primitive) {
	case PRIM_DL_EST:
		LOGPITS(e1i_ts, DLMI, LOGL_DEBUG, "DL_EST: sapi(%d) tei(%d)\n", sapi, tei);
		e1inp_event(e1i_ts, S_L_INP_TEI_UP, tei, sapi);
		break;
	case PRIM_DL_REL:
		LOGPITS(e1i_ts, DLMI, LOGL_DEBUG, "DL_REL: sapi(%d) tei(%d)\n", sapi, tei);
		e1inp_event(e1i_ts, S_L_INP_TEI_DN, tei, sapi);
		break;
	case PRIM_DL_DATA:
	case PRIM_DL_UNIT_DATA:
		if (dp->oph.operation == PRIM_OP_INDICATION) {
			msg->l2h = msg->l3h;
			LOGPITS(e1i_ts, DLMI, LOGL_DEBUG, "RX: %s sapi=%d tei=%d\n",
				osmo_hexdump(msgb_l2(msg), msgb_l2len(msg)),
				sapi, tei);
			e1inp_rx_ts(e1i_ts, msg, tei, sapi);
			return;
		}
		break;
	case PRIM_MDL_ERROR:
		LOGPITS(e1i_ts, DLMI, LOGL_DEBUG, "MDL_EERROR: cause(%d)\n", dp->u.error_ind.cause);
		break;
	default:
		printf("ERROR: unknown prim\n");
		break;
	}

	msgb_free(msg);

	return;
}

#define TSX_ALLOC_SIZE 4096

/* called by driver if it wants to transmit on a given TS */
struct msgb *e1inp_tx_ts(struct e1inp_ts *e1i_ts,
			 struct e1inp_sign_link **sign_link)
{
	struct e1inp_sign_link *link;
	struct msgb *msg = NULL;
	int len;

	switch (e1i_ts->type) {
	case E1INP_TS_TYPE_SIGN:
		/* FIXME: implement this round robin */
		llist_for_each_entry(link, &e1i_ts->sign.sign_links, list) {
			msg = msgb_dequeue(&link->tx_list);
			if (msg) {
				if (sign_link)
					*sign_link = link;
				break;
			}
		}
		break;
	case E1INP_TS_TYPE_TRAU:
		msg = msgb_alloc(TSX_ALLOC_SIZE, "TRAU_TX");
		if (!msg)
			return NULL;
		len = subchan_mux_out(&e1i_ts->trau.mux, msg->data, 40);
		if (len != 40) {
			LOGPITS(e1i_ts, DLMI, LOGL_ERROR, "cannot transmit, failed to mux\n");
			msgb_free(msg);
			return NULL;
		}
		msgb_put(msg, 40);
		break;
	case E1INP_TS_TYPE_RAW:
		/* Get msgb from tx_queue */
		msg = msgb_dequeue(&e1i_ts->raw.tx_queue);
		break;
	case E1INP_TS_TYPE_HDLC:
		/* Get msgb from tx_queue */
		msg = msgb_dequeue(&e1i_ts->hdlc.tx_queue);
		break;
	case E1INP_TS_TYPE_I460:
		msg = msgb_alloc(TSX_ALLOC_SIZE, "I460_TX");
		if (!msg)
			return NULL;
		len = osmo_i460_mux_out(&e1i_ts->i460.i460_ts, msg->data, 160);
		msgb_put(msg, len);
		break;
	default:
		LOGPITS(e1i_ts, DLMI, LOGL_ERROR, "unsupported E1 TS type %u\n", e1i_ts->type);
		return NULL;
	}
	return msg;
}

int e1inp_int_snd_event(struct e1inp_ts *ts, struct e1inp_sign_link *link, int evt)
{
	struct input_signal_data isd;
	isd.line = ts->line;
	isd.ts_nr = ts->num;
	isd.link_type = link->type;
	isd.trx = link->trx;
	isd.tei = link->tei;
	isd.sapi = link->sapi;

	/* report further upwards */
	osmo_signal_dispatch(SS_L_INPUT, evt, &isd);
	return 0;
}


/* called by driver in case some kind of link state event */
int e1inp_event(struct e1inp_ts *ts, int evt, uint8_t tei, uint8_t sapi)
{
	struct e1inp_sign_link *link;

	link = e1inp_lookup_sign_link(ts, tei, sapi);
	if (!link)
		return -EINVAL;
	return e1inp_int_snd_event(ts, link, evt);
}

/* register a driver with the E1 core */
int e1inp_driver_register(struct e1inp_driver *drv)
{
	llist_add_tail(&drv->list, &e1inp_driver_list);
	return 0;
}

struct e1inp_driver *e1inp_driver_find(const char *name)
{
	struct e1inp_driver *drv;

	llist_for_each_entry(drv, &e1inp_driver_list, list) {
		if (!strcasecmp(name, drv->name))
			return drv;
	}
	return NULL;
}

int e1inp_line_update(struct e1inp_line *line)
{
	struct input_signal_data isd;
	int i, rc;

	if (line->driver && line->ops && line->driver->line_update) {
		rc = line->driver->line_update(line);
	} else
		rc = 0;

	/* Set the PCAP file descriptor for all timeslots that have
	 * software LAPD instances, to ensure the osmo_lapd_pcap code is
	 * used to write PCAP files (if requested) */
	for (i = 0; i < ARRAY_SIZE(line->ts); i++) {
		struct e1inp_ts *e1i_ts = &line->ts[i];
		if (e1i_ts->lapd)
			e1i_ts->lapd->pcap_fd = line->pcap_fd;
	}

	/* Send a signal to anyone who is interested in new lines being
	 * configured */
	memset(&isd, 0, sizeof(isd));
	isd.line = line;
	osmo_signal_dispatch(SS_L_INPUT, S_L_INP_LINE_INIT, &isd);

	return rc;
}

static int e1i_sig_cb(unsigned int subsys, unsigned int signal,
		      void *handler_data, void *signal_data)
{
	struct e1inp_line *line;

	if (subsys != SS_L_GLOBAL ||
	    signal != S_L_GLOBAL_SHUTDOWN)
		return 0;

	llist_for_each_entry(line, &e1inp_line_list, list) {
		if (line->pcap_fd >=0)
			close(line->pcap_fd);
		line->pcap_fd = -1;
	}

	return 0;
}

const struct value_string e1inp_signal_names[] = {
	{ S_L_INP_NONE,		"NONE" },
	{ S_L_INP_TEI_UP,	"TEI-UP" },
	{ S_L_INP_TEI_DN,	"TEI-DOWN" },
	{ S_L_INP_TEI_UNKNOWN,	"TEI-UNKNOWN" },
	{ S_L_INP_LINE_INIT,	"LINE-INIT" },
	{ S_L_INP_LINE_ALARM,	"LINE-ALARM" },
	{ S_L_INP_LINE_NOALARM,	"LINE-NOALARM" },
	{ 0, NULL }
};

void e1inp_misdn_init(void);
void e1inp_dahdi_init(void);
void e1inp_e1d_init(void);
void e1inp_ipaccess_init(void);
void e1inp_rs232_init(void);
void e1inp_unixsocket_init(void);

void e1inp_init(void)
{
	tall_e1inp_ctx = talloc_named_const(libosmo_abis_ctx, 1, "e1inp");
	tall_sigl_ctx = talloc_named_const(tall_e1inp_ctx, 1,
					   "e1inp_sign_link");
	osmo_signal_register_handler(SS_L_GLOBAL, e1i_sig_cb, NULL);

	e1inp_misdn_init();
#ifdef HAVE_DAHDI_USER_H
	e1inp_dahdi_init();
#endif
#ifdef HAVE_E1D
	e1inp_e1d_init();
#endif
	e1inp_ipaccess_init();
	e1inp_rs232_init();
	e1inp_unixsocket_init();
}
