/* mgcp_utils - common functions to setup an MGCP connection
 */
/* (C) 2016 by sysmocom s.f.m.c. GmbH <info@sysmocom.de>
 * All Rights Reserved
 *
 * 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, see <http://www.gnu.org/licenses/>.
 *
 */

#include <osmocom/core/linuxlist.h>
#include <osmocom/core/select.h>
#include <osmocom/core/write_queue.h>
#include <osmocom/core/msgb.h>
#include <osmocom/core/logging.h>
#include <osmocom/core/byteswap.h>
#include <osmocom/core/socket.h>
#include <osmocom/core/sockaddr_str.h>

#include <osmocom/mgcp_client/mgcp_client.h>
#include <osmocom/mgcp_client/mgcp_client_internal.h>

#include <osmocom/abis/e1_input.h>

#include <netinet/in.h>
#include <arpa/inet.h>

#include <errno.h>
#include <unistd.h>
#include <string.h>
#include <ctype.h>
#include <stdlib.h>
#include <limits.h>

#ifndef OSMUX_CID_MAX
#define OSMUX_CID_MAX 255 /* FIXME: use OSMUX_CID_MAX from libosmo-netif? */
#endif

#define LOGPMGW(mgcp, level, fmt, args...) \
LOGP(DLMGCP, level, "MGW(%s) " fmt, mgcp_client_name(mgcp), ## args)

/* Codec descripton for dynamic payload types (SDP) */
const struct value_string osmo_mgcpc_codec_names[] = {
	{ CODEC_PCMU_8000_1, "PCMU/8000/1" },
	{ CODEC_GSM_8000_1, "GSM/8000/1" },
	{ CODEC_PCMA_8000_1, "PCMA/8000/1" },
	{ CODEC_G729_8000_1, "G729/8000/1" },
	{ CODEC_GSMEFR_8000_1, "GSM-EFR/8000/1" },
	{ CODEC_GSMHR_8000_1, "GSM-HR-08/8000/1" },
	{ CODEC_AMR_8000_1, "AMR/8000/1" },
	{ CODEC_AMRWB_16000_1, "AMR-WB/16000/1" },
	{ CODEC_IUFP, "VND.3GPP.IUFP/16000" },
	{ CODEC_CLEARMODE, "CLEARMODE/8000" },
	{ 0, NULL },
};

/* Get encoding name from a full codec string e,g.
 * ("CODEC/8000/2" => returns "CODEC") */
static char *extract_codec_name(const char *str)
{
	static char buf[64];
	char *pos;

	if (!str)
		return NULL;

	osmo_strlcpy(buf, str, sizeof(buf));

	pos = strchr(buf, '/');
	if (pos)
		*pos = '\0';

	return buf;
}

/*! Map a string to a codec.
 *  \ptmap[in] str input string (e.g "GSM/8000/1", "GSM/8000" or "GSM")
 *  \returns codec that corresponds to the given string representation. */
enum mgcp_codecs map_str_to_codec(const char *str)
{
	unsigned int i;
	char *codec_name;
	char str_buf[64];

	osmo_strlcpy(str_buf, extract_codec_name(str), sizeof(str_buf));

	for (i = 0; i < ARRAY_SIZE(osmo_mgcpc_codec_names); i++) {
		codec_name = extract_codec_name(osmo_mgcpc_codec_names[i].str);
		if (!codec_name)
			continue;
		if (strcmp(codec_name, str_buf) == 0)
			return osmo_mgcpc_codec_names[i].value;
	}

	return -1;
}

/* Check the ptmap for illegal mappings */
static int check_ptmap(const struct ptmap *ptmap)
{
	/* Check if there are mappings that leave the IANA assigned dynamic
	 * payload type range. Under normal conditions such mappings should
	 * not occur */

	/* Its ok to have a 1:1 mapping in the statically defined
	 * range, this won't hurt */
	if (ptmap->codec == ptmap->pt)
		return 0;

	if (ptmap->codec < 96 || ptmap->codec > 127)
		goto error;
	if (ptmap->pt < 96 || ptmap->pt > 127)
		goto error;

	return 0;
error:
	LOGP(DLMGCP, LOGL_ERROR,
	     "ptmap contains illegal mapping: codec=%u maps to pt=%u\n",
	     ptmap->codec, ptmap->pt);
	return -1;
}

/*! Map a codec to a payload type.
 *  \ptmap[in] payload pointer to payload type map with specified payload types.
 *  \ptmap[in] ptmap_len length of the payload type map.
 *  \ptmap[in] codec the codec for which the payload type should be looked up.
 *  \returns assigned payload type */
unsigned int map_codec_to_pt(const struct ptmap *ptmap, unsigned int ptmap_len,
			     enum mgcp_codecs codec)
{
	unsigned int i;

	/*! Note: If the payload type map is empty or the codec is not found
	 *  in the map, then a 1:1 mapping is performed. If the codec falls
	 *  into the statically defined range or if the mapping table isself
	 *  tries to map to the statically defined range, then the mapping
	 *  is also ignored and a 1:1 mapping is performed instead. */

	/* we may return the codec directly since enum mgcp_codecs directly
	 * corresponds to the statically assigned payload types */
	if (codec < 96 || codec > 127)
		return codec;

	for (i = 0; i < ptmap_len; i++) {
		/* Skip illegal map entries */
		if (check_ptmap(ptmap) == 0 && ptmap->codec == codec)
			return ptmap->pt;
		ptmap++;
	}

	/* If nothing is found, do not perform any mapping */
	return codec;
}

/*! Map a payload type to a codec.
 *  \ptmap[in] payload pointer to payload type map with specified payload types.
 *  \ptmap[in] ptmap_len length of the payload type map.
 *  \ptmap[in] payload type for which the codec should be looked up.
 *  \returns codec that corresponds to the specified payload type */
enum mgcp_codecs map_pt_to_codec(struct ptmap *ptmap, unsigned int ptmap_len,
				 unsigned int pt)
{
	unsigned int i;

	/*! Note: If the payload type map is empty or the payload type is not
	 *  found in the map, then a 1:1 mapping is performed. If the payload
	 *  type falls into the statically defined range or if the mapping
	 *  table isself tries to map to the statically defined range, then
	 *  the mapping is also ignored and a 1:1 mapping is performed
	 *  instead. */

	/* See also note in map_codec_to_pt() */
	if (pt < 96 || pt > 127)
		return pt;

	for (i = 0; i < ptmap_len; i++) {
		if (check_ptmap(ptmap) == 0 && ptmap->pt == pt)
			return ptmap->codec;
		ptmap++;
	}

	/* If nothing is found, do not perform any mapping */
	return pt;
}

static void _mgcp_client_conf_init(struct mgcp_client_conf *conf)
{
	/* NULL and -1 default to MGCP_CLIENT_*_DEFAULT values */
	*conf = (struct mgcp_client_conf){
		.local_addr = NULL,
		.local_port = -1,
		.remote_addr = NULL,
		.remote_port = -1,
		.keepalive = {
			.timeout_sec = 0, /* disabled */
			.req_interval_sec = 0, /* disabled */
			.req_endpoint_name = MGCP_CLIENT_KEEPALIVE_DEFAULT_ENDP,
		},
	};

	INIT_LLIST_HEAD(&conf->reset_epnames);
}

/*! Allocate and initialize MGCP client configuration struct with default values.
 *  \param[in] ctx talloc context to use as a parent during allocation.
 *
 * The returned struct can be freed using talloc_free().
 */
struct mgcp_client_conf *mgcp_client_conf_alloc(void *ctx)
{
	struct mgcp_client_conf *conf = talloc(ctx, struct mgcp_client_conf);
	_mgcp_client_conf_init(conf);
	return conf;
}

/*! Initialize MGCP client configuration struct with default values.
 *  \param[out] conf Client configuration.
 *
 * This function is deprecated and should not be used, as it may break if size
 * of struct mgcp_client_conf changes in the future!
 */
void mgcp_client_conf_init(struct mgcp_client_conf *conf)
{
	_mgcp_client_conf_init(conf);
}

static void mgcp_client_handle_response(struct mgcp_client *mgcp,
					struct mgcp_response_pending *pending,
					struct mgcp_response *response)
{
	if (!pending) {
		LOGPMGW(mgcp, LOGL_ERROR, "Cannot handle NULL response\n");
		return;
	}
	if (pending->response_cb)
		pending->response_cb(response, pending->priv);
	else
		LOGPMGW(mgcp, LOGL_DEBUG, "MGCP response ignored (NULL cb)\n");
	talloc_free(pending);
}

static int mgcp_response_parse_head(struct mgcp_response *r, struct msgb *msg)
{
	int comment_pos;
	char *end;

	if (mgcp_msg_terminate_nul(msg))
		goto response_parse_failure;

	r->body = (char *)msg->data;

	if (sscanf(r->body, "%3d %u %n",
		   &r->head.response_code, &r->head.trans_id,
		   &comment_pos) != 2)
		goto response_parse_failure;

	osmo_strlcpy(r->head.comment, r->body + comment_pos, sizeof(r->head.comment));
	end = strchr(r->head.comment, '\r');
	if (!end)
		goto response_parse_failure;
	/* Mark the end of the comment */
	*end = '\0';
	return 0;

response_parse_failure:
	LOGP(DLMGCP, LOGL_ERROR,
	     "Failed to parse MGCP response header\n");
	return -EINVAL;
}

/* TODO undup against mgcp_protocol.c:mgcp_check_param() */
static bool mgcp_line_is_valid(const char *line)
{
	const size_t line_len = strlen(line);
	if (line[0] == '\0')
		return true;

	if (line_len < 2
	    || line[1] != '=') {
		LOGP(DLMGCP, LOGL_ERROR,
		     "Wrong MGCP option format: '%s'\n",
		     line);
		return false;
	}

	return true;
}

/* Parse a line like "m=audio 16002 RTP/AVP 98", extract port and payload types */
static int mgcp_parse_audio_port_pt(struct mgcp_response *r, char *line)
{
	char *pt_str;
	char *pt_end;
	unsigned long int pt;
	unsigned int ptmap_len;
	unsigned int i;

	/* Extract port information */
	if (sscanf(line, "m=audio %hu", &r->audio_port) != 1)
		goto response_parse_failure_port;
	if (r->audio_port == 0)
		goto response_parse_failure_port;

	/* Extract payload types */
	line = strstr(line, "RTP/AVP ");
	if (!line)
		goto exit;

	/* Clear any previous entries before writing over r->ptmap */
	r->ptmap_len = 0;
	/* Keep a local ptmap_len to show only the full list after parsing succeeded in whole. */
	ptmap_len = 0;

	pt_str = strtok(line, " ");
	while (1) {
		pt_str = strtok(NULL, " ");
		if (!pt_str)
			break;
		errno = 0;
		pt = strtoul(pt_str, &pt_end, 0);
		if ((errno == ERANGE && pt == ULONG_MAX) || (errno && !pt) ||
		    pt_str == pt_end) {
			LOGP(DLMGCP, LOGL_ERROR, "SDP: cannot parse payload type number from '%s'\n", pt_str);
			goto response_parse_failure_pt;
		}

		/* PT is 7 bit field, higher values not allowed */
		if (pt >> 7) {
			LOGP(DLMGCP, LOGL_ERROR, "SDP: payload type number out of range: %lu > 127\n", pt);
			goto response_parse_failure_pt;
		}

		/* Do not allow duplicate payload types */
		for (i = 0; i < ptmap_len; i++) {
			if (r->ptmap[i].pt == pt) {
				LOGP(DLMGCP, LOGL_ERROR, "SDP: payload type number %lu listed twice\n", pt);
				goto response_parse_failure_pt;
			}
		}

		/* Do not allow excessive payload types */
		if (ptmap_len >= ARRAY_SIZE(r->ptmap)) {
			LOGP(DLMGCP, LOGL_ERROR,
			     "SDP: can parse only up to %zu payload type numbers\n", ARRAY_SIZE(r->ptmap));
			goto response_parse_failure_pt;
		}

		/* Some payload type numbers imply a specific codec. For those, using the PT number as enum mgcp_codecs
		 * yields the correct result. If no more specific information on the codec follows in "a=rtpmap:N"
		 * lines, then this default number takes over. This only applies for PT below the dynamic range (<96). */
		if (pt < 96)
			r->ptmap[ptmap_len].codec = pt;
		else
			r->ptmap[ptmap_len].codec = -1;
		r->ptmap[ptmap_len].pt = pt;
		ptmap_len++;
	}

	/* Parsing succeeded, publish all entries. */
	r->ptmap_len = ptmap_len;

exit:
	return 0;

response_parse_failure_port:
	LOGP(DLMGCP, LOGL_ERROR,
	     "Failed to parse SDP parameter port (%s)\n", line);
	return -EINVAL;

response_parse_failure_pt:
	LOGP(DLMGCP, LOGL_ERROR,
	     "Failed to parse SDP parameter payload types (%s)\n", line);
	return -EINVAL;
}

/* Parse an 'a=...' parameter */
static int mgcp_parse_audio_ptime_rtpmap(struct mgcp_response *r, const char *line)
{
	unsigned int pt;
	unsigned int i;
	char codec_resp[64];
	int rc;

#define A_PTIME "a=ptime:"
#define A_RTPMAP "a=rtpmap:"

	if (osmo_str_startswith(line, A_PTIME)) {
		if (sscanf(line, A_PTIME "%u", &r->ptime) != 1) {
			LOGP(DLMGCP, LOGL_ERROR,
			     "Failed to parse SDP parameter, invalid ptime (%s)\n", line);
			return -EINVAL;
		}
	} else if (osmo_str_startswith(line, A_RTPMAP)) {
		if (sscanf(line, A_RTPMAP "%d %63s", &pt, codec_resp) != 2) {
			LOGP(DLMGCP, LOGL_ERROR,
			     "Failed to parse SDP parameter, invalid rtpmap: %s\n", osmo_quote_str(line, -1));
			return -EINVAL;
		}
		rc = map_str_to_codec(codec_resp);
		if (rc < 0) {
			LOGP(DLMGCP, LOGL_ERROR,
			     "Failed to parse SDP parameter, can't parse codec in rtpmap: %s\n", osmo_quote_str(line, -1));
			return -EINVAL;
		}

		/* Earlier, a line like "m=audio 16002 RTP/AVP 98 112 3" established the desired order of payloads, now
		 * enrich it with actual codec information provided by "a=rtpmap:..." entries.
		 * For each, find the entry with the right pt number and add the info there. */

		for (i = 0; i < r->ptmap_len; i++) {
			if (r->ptmap[i].pt != pt)
				continue;
			r->ptmap[i].codec = rc;
			return 0;
		}

		/* No entry was found. This is an error in the MGCP protocol, but let's just add another entry
		 * anyway, to not make it look like it was never there. */
		LOGP(DLMGCP, LOGL_ERROR,
		     "error in MGCP message: 'a=rtpmap:%u' has no matching entry in 'm=audio ... %u'\n",
		     pt, pt);
		if (r->ptmap_len >= ARRAY_SIZE(r->ptmap)) {
			LOGP(DLMGCP, LOGL_ERROR,
			     "cannot parse all codecs: can only store up to %zu rtpmap entries.\n",
			     ARRAY_SIZE(r->ptmap));
			return -ENOSPC;
		}
		r->ptmap[r->ptmap_len] = (struct ptmap){
			.pt = pt,
			.codec = rc,
		};
		r->ptmap_len++;
	}

	return 0;
}

/* Parse a line like "c=IN IP4 10.11.12.13" */
static int mgcp_parse_audio_ip(struct mgcp_response *r, const char *line)
{
	struct in6_addr ip_test;
	bool is_ipv6;

	if (strncmp("c=IN IP", line, 7) != 0)
		goto response_parse_failure;
	line += 7;
	if (*line == '6')
		is_ipv6 = true;
	else if (*line == '4')
		is_ipv6 = false;
	else
		goto response_parse_failure;
	line++;
	if (*line != ' ')
		goto response_parse_failure;
	line++;

	/* Extract and check IP-Address */
	if (is_ipv6) {
		/* 45 = INET6_ADDRSTRLEN -1 */
		if (sscanf(line, "%45s", r->audio_ip) != 1)
			goto response_parse_failure;
		if (inet_pton(AF_INET6, r->audio_ip, &ip_test) != 1)
			goto response_parse_failure;
	} else {
		/* 15 = INET_ADDRSTRLEN -1 */
		if (sscanf(line, "%15s", r->audio_ip) != 1)
			goto response_parse_failure;
		if (inet_pton(AF_INET, r->audio_ip, &ip_test) != 1)
			goto response_parse_failure;
	}
	return 0;

response_parse_failure:
	LOGP(DLMGCP, LOGL_ERROR,
	     "Failed to parse MGCP response header (audio ip)\n");
	return -EINVAL;
}

/*! Extract OSMUX CID from an MGCP parameter line (string).
 *  \param[in] line single parameter line from the MGCP message
 *  \returns OSMUX CID, -1 wildcard, -2 on error
 * FIXME: This is a copy of function in mgcp_msg.c. Have some common.c file between both libs?
 */
static int mgcp_parse_osmux_cid(const char *line)
{
	int osmux_cid;


	if (strcasecmp(line + 2, "Osmux: *") == 0) {
		LOGP(DLMGCP, LOGL_DEBUG, "Parsed wilcard Osmux CID\n");
		return -1;
	}

	if (sscanf(line + 2 + 7, "%u", &osmux_cid) != 1) {
		LOGP(DLMGCP, LOGL_ERROR, "Failed parsing Osmux in MGCP msg line: %s\n",
		     line);
		return -2;
	}

	if (osmux_cid > OSMUX_CID_MAX) { /* OSMUX_CID_MAX from libosmo-netif */
		LOGP(DLMGCP, LOGL_ERROR, "Osmux ID too large: %u > %u\n",
		     osmux_cid, OSMUX_CID_MAX);
		return -2;
	}
	LOGP(DLMGCP, LOGL_DEBUG, "MGW offered Osmux CID %u\n", osmux_cid);

	return osmux_cid;
}

/* A new section is marked by a double line break, check a few more
 * patterns as there may be variants */
static char *mgcp_find_section_end(char *string)
{
	char *rc;

	rc = strstr(string, "\n\n");
	if (rc)
		return rc + 2;

	rc = strstr(string, "\n\r\n\r");
	if (rc)
		return rc + 4;

	rc = strstr(string, "\r\n\r\n");
	if (rc)
		return rc + 4;

	return NULL;
}

/*! Parse body (SDP) parameters of the MGCP response
 *  \param[in,out] r Response data
 *  \returns 0 on success, -EINVAL on error. */
int mgcp_response_parse_params(struct mgcp_response *r)
{
	char *line;
	int rc;
	char *data;
	char *data_ptr;

	/* Since this functions performs a destructive parsing, we create a
	 * local copy of the body data */
	OSMO_ASSERT(r->body);
	data = talloc_strdup(r, r->body);
	OSMO_ASSERT(data);

	/* Find beginning of the parameter (SDP) section */
	data_ptr = mgcp_find_section_end(data);
	if (!data_ptr) {
		LOGP(DLMGCP, LOGL_DEBUG, "MGCP response contains no SDP parameters\n");
		rc = 0;
		goto exit;
	}

	/* data_ptr now points to the beginning of the section-end-marker; for_each_non_empty_line()
	 * skips any \r and \n characters for free, so we don't need to skip the marker. */

	for_each_non_empty_line(line, data_ptr) {
		if (!mgcp_line_is_valid(line))
			return -EINVAL;

		switch (line[0]) {
		case 'a':
			rc = mgcp_parse_audio_ptime_rtpmap(r, line);
			if (rc)
				goto exit;
			break;
		case 'm':
			rc = mgcp_parse_audio_port_pt(r, line);
			if (rc)
				goto exit;
			break;
		case 'c':
			rc = mgcp_parse_audio_ip(r, line);
			if (rc)
				goto exit;
			break;
		default:
			/* skip unhandled parameters */
			break;
		}
	}

	rc = 0;
exit:
	talloc_free(data);
	return rc;
}

/* Parse a line like "X: something" */
static int mgcp_parse_head_param(char *result, unsigned int result_len,
				 char label, const char *line)
{
	char label_string[4];
	size_t rc;

	/* Detect empty parameters */
	if (strlen(line) < 4)
		goto response_parse_failure;

	/* Check if the label matches */
	snprintf(label_string, sizeof(label_string), "%c: ", label);
	if (memcmp(label_string, line, 3) != 0)
		goto response_parse_failure;

	/* Copy payload part of the string to destinations (the label string
	 * is always 3 chars long) */
	rc = osmo_strlcpy(result, line + 3, result_len);
	if (rc >= result_len) {
		LOGP(DLMGCP, LOGL_ERROR,
		     "Failed to parse MGCP response (parameter label: %c):"
		     " the received conn ID is too long: %zu, maximum is %u characters\n",
		     label, rc, result_len - 1);
		return -ENOSPC;
	}
	return 0;

response_parse_failure:
	LOGP(DLMGCP, LOGL_ERROR,
	     "Failed to parse MGCP response (parameter label: %c)\n", label);
	return -EINVAL;
}

/* Parse MGCP parameters of the response */
static int parse_head_params(struct mgcp_response *r)
{
	char *line;
	int rc = 0;
	OSMO_ASSERT(r->body);
	char *data;
	char *data_ptr;
	char *data_end;

	/* Since this functions performs a destructive parsing, we create a
	 * local copy of the body data */
	data = talloc_zero_size(r, strlen(r->body)+1);
	OSMO_ASSERT(data);
	data_ptr = data;
	osmo_strlcpy(data, r->body, strlen(r->body));

	/* If there is an SDP body attached, prevent for_each_non_empty_line()
	 * into running in there, we are not yet interested in the parameters
	 * stored there. */
	data_end = mgcp_find_section_end(data);
	if (data_end)
		*data_end = '\0';

	for_each_non_empty_line(line, data_ptr) {
		switch (toupper(line[0])) {
		case 'Z':
			rc = mgcp_parse_head_param(r->head.endpoint,
						   sizeof(r->head.endpoint),
						   'Z', line);
			if (rc)
				goto exit;

			/* A specific endpoint identifier returned by the MGW
			 * must not contain any wildcard characters */
			if (strstr(r->head.endpoint, "*") != NULL) {
				rc = -EINVAL;
				goto exit;
			}

			/* A specific endpoint identifier returned by the MGW
			 * must contain an @ character */
			if (strstr(r->head.endpoint, "@") == NULL) {
				rc = -EINVAL;
				goto exit;
			}
			break;
		case 'I':
			rc = mgcp_parse_head_param(r->head.conn_id,
						   sizeof(r->head.conn_id),
						   'I', line);
			if (rc)
				goto exit;
			break;
		case 'X':
			if (strncasecmp("Osmux: ", line + 2, strlen("Osmux: ")) == 0) {
				rc = mgcp_parse_osmux_cid(line);
				if (rc < 0) {
					/* -1: we don't want wildcards in response. -2: error */
					rc = -EINVAL;
					goto exit;
				}
				r->head.x_osmo_osmux_use = true;
				r->head.x_osmo_osmux_cid = (uint8_t) rc;
				rc = 0;
				break;
			}
			/* Ignore unknown X-headers */
			break;
		default:
			/* skip unhandled parameters */
			break;
		}
	}
exit:
	talloc_free(data);
	return rc;
}

static struct mgcp_response_pending *mgcp_client_response_pending_get(
					 struct mgcp_client *mgcp,
					 mgcp_trans_id_t trans_id)
{
	struct mgcp_response_pending *pending;
	llist_for_each_entry(pending, &mgcp->responses_pending, entry) {
		if (pending->trans_id == trans_id) {
			llist_del(&pending->entry);
			return pending;
		}
	}
	return NULL;
}

/* Feed an MGCP message into the receive processing.
 * Parse the head and call any callback registered for the transaction id found
 * in the MGCP message. This is normally called directly from the internal
 * mgcp_read_cb that reads from the socket connected to the MGCP gateway. This
 * function is published mainly to be able to feed data from the test suite.
 */
int mgcp_client_rx(struct mgcp_client *mgcp, struct msgb *msg)
{
	struct mgcp_response *r;
	struct mgcp_response_pending *pending;
	int rc;

	r = talloc_zero(mgcp, struct mgcp_response);
	OSMO_ASSERT(r);

	/* Re-arm keepalive timer if enabled */
	if (OSMO_UNLIKELY(mgcp->conn_up == false)) {
		LOGPMGW(mgcp, LOGL_NOTICE, "MGCP link to MGW now considered UP\n");
		mgcp->conn_up = true;
	}
	if (mgcp->actual.keepalive.timeout_sec > 0)
		osmo_timer_schedule(&mgcp->keepalive_rx_timer, mgcp->actual.keepalive.timeout_sec, 0);

	rc = mgcp_response_parse_head(r, msg);
	if (rc) {
		LOGPMGW(mgcp, LOGL_ERROR, "Cannot parse MGCP response (head)\n");
		rc = 1;
		goto error;
	}

	LOGPMGW(mgcp, LOGL_DEBUG, "MGCP client: Rx %d %u %s\n",
	     r->head.response_code, r->head.trans_id, r->head.comment);

	rc = parse_head_params(r);
	if (rc) {
		LOGPMGW(mgcp, LOGL_ERROR, "Cannot parse MGCP response (head parameters)\n");
		rc = 1;
		goto error;
	}

	pending = mgcp_client_response_pending_get(mgcp, r->head.trans_id);
	if (!pending) {
		LOGPMGW(mgcp, LOGL_ERROR, "Cannot find matching MGCP transaction for trans_id %d\n",
			r->head.trans_id);
		rc = -ENOENT;
		goto error;
	}

	mgcp_client_handle_response(mgcp, pending, r);
	rc = 0;

error:
	talloc_free(r);
	return rc;
}

static void mgcp_read_cb(struct osmo_io_fd *iofd, int res, struct msgb *msg)
{
	struct mgcp_client *mgcp = osmo_iofd_get_data(iofd);

	if (res <= 0) {
		LOGPMGW(mgcp, LOGL_ERROR, "Failed to read: %s: %d='%s'\n",
			osmo_iofd_get_name(iofd), res, strerror(res));

		msgb_free(msg);
		return;
	}

	msg->l2h = msg->head;
	mgcp_client_rx(mgcp, msg);
	talloc_free(msg);
}

static int mgcp_do_write(struct mgcp_client *mgcp, struct msgb *msg)
{
	int ret;

	LOGPMGW(mgcp, LOGL_DEBUG, "Tx MGCP: %s: len=%u '%s'...\n",
		osmo_iofd_get_name(mgcp->iofd), msg->len,
		osmo_escape_str((const char *)msg->data, OSMO_MIN(42, msg->len)));

	ret = osmo_iofd_write_msgb(mgcp->iofd, msg);
	if (ret < 0)
		msgb_free(msg);

	/* Re-arm the keepalive Tx timer: */
	if (mgcp->actual.keepalive.req_interval_sec > 0)
		osmo_timer_schedule(&mgcp->keepalive_tx_timer, mgcp->actual.keepalive.req_interval_sec, 0);

	return ret;
}

static void mgcp_write_cb(struct osmo_io_fd *iofd, int res, struct msgb *msg)
{
	struct mgcp_client *mgcp = osmo_iofd_get_data(iofd);

	if (OSMO_UNLIKELY(res != msg->len)) {
		LOGPMGW(mgcp, LOGL_ERROR, "Failed to Tx MGCP: %s: %d='%s'; msg: len=%u '%s'...\n",
			osmo_iofd_get_name(mgcp->iofd), res, strerror(res),
			msg->len, osmo_escape_str((const char *)msg->data, OSMO_MIN(42, msg->len)));
	}
}


static const char *_mgcp_client_name_append_domain(const struct mgcp_client *mgcp, const char *name)
{
	static char endpoint[MGCP_ENDPOINT_MAXLEN];
	int rc;

	rc = snprintf(endpoint, sizeof(endpoint), "%s@%s", name, mgcp_client_endpoint_domain(mgcp));
	if (rc > sizeof(endpoint) - 1) {
		LOGPMGW(mgcp, LOGL_ERROR, "MGCP endpoint exceeds maximum length of %zu: '%s@%s'\n",
			sizeof(endpoint) - 1, name, mgcp_client_endpoint_domain(mgcp));
		return NULL;
	}
	if (rc < 1) {
		LOGPMGW(mgcp, LOGL_ERROR, "Cannot compose MGCP endpoint name\n");
		return NULL;
	}
	return endpoint;
}

/* Safely ignore the MGCP response to the DLCX sent via _mgcp_client_send_dlcx() */
static void _ignore_mgcp_response(struct mgcp_response *response, void *priv) { }

/* Format DLCX message (fire and forget) and send it off to the MGW */
static void _mgcp_client_send_dlcx(struct mgcp_client *mgcp, const char *epname)
{
	struct msgb *msgb_dlcx;
	struct mgcp_msg mgcp_msg_dlcx = {
		.verb = MGCP_VERB_DLCX,
		.presence = MGCP_MSG_PRESENCE_ENDPOINT,
	};
	osmo_strlcpy(mgcp_msg_dlcx.endpoint, epname, sizeof(mgcp_msg_dlcx.endpoint));
	msgb_dlcx = mgcp_msg_gen(mgcp, &mgcp_msg_dlcx);
	mgcp_client_tx(mgcp, msgb_dlcx, &_ignore_mgcp_response, NULL);
}

/* Format AuditEndpoint message (fire and forget) and send it off to the MGW */
static void _mgcp_client_send_auep(struct mgcp_client *mgcp, const char *epname)
{
	struct msgb *msgb_auep;
	struct mgcp_msg mgcp_msg_auep = {
		.verb = MGCP_VERB_AUEP,
		.presence = MGCP_MSG_PRESENCE_ENDPOINT,
	};
	OSMO_STRLCPY_ARRAY(mgcp_msg_auep.endpoint, epname);
	msgb_auep = mgcp_msg_gen(mgcp, &mgcp_msg_auep);
	mgcp_client_tx(mgcp, msgb_auep, &_ignore_mgcp_response, NULL);
}

static void mgcp_client_keepalive_tx_timer_cb(void *data)
{
	struct mgcp_client *mgcp = (struct mgcp_client *)data;
	LOGPMGW(mgcp, LOGL_INFO, "Triggering keepalive MGCP request\n");
	const char *epname = _mgcp_client_name_append_domain(mgcp, mgcp->actual.keepalive.req_endpoint_name);
	_mgcp_client_send_auep(mgcp, epname);

	/* Re-arm the timer: */
	osmo_timer_schedule(&mgcp->keepalive_tx_timer, mgcp->actual.keepalive.req_interval_sec, 0);
}

static void mgcp_client_keepalive_rx_timer_cb(void *data)
{
	struct mgcp_client *mgcp = (struct mgcp_client *)data;
	LOGPMGW(mgcp, LOGL_ERROR, "MGCP link to MGW now considered DOWN (keepalive timeout, more than %u seconds with no answer from MGW)\n",
		mgcp->actual.keepalive.timeout_sec);
	mgcp->conn_up = false;
	/* TODO: Potentially time out all ongoing transactions for that MGW. Maybe based on VTY cfg? */
}

struct mgcp_client *mgcp_client_init(void *ctx,
				     struct mgcp_client_conf *conf)
{
	struct mgcp_client *mgcp;
	struct reset_ep *reset_ep;
	struct reset_ep *actual_reset_ep;

	mgcp = talloc_zero(ctx, struct mgcp_client);
	if (!mgcp)
		return NULL;

	INIT_LLIST_HEAD(&mgcp->responses_pending);

	mgcp->next_trans_id = 1;

	mgcp->actual.local_addr = conf->local_addr ? conf->local_addr :
		MGCP_CLIENT_LOCAL_ADDR_DEFAULT;
	mgcp->actual.local_port = conf->local_port > 0 ? (uint16_t)conf->local_port :
		MGCP_CLIENT_LOCAL_PORT_DEFAULT;

	mgcp->actual.remote_addr = conf->remote_addr ? conf->remote_addr :
		MGCP_CLIENT_REMOTE_ADDR_DEFAULT;
	mgcp->actual.remote_port = conf->remote_port >= 0 ? (uint16_t)conf->remote_port :
		MGCP_CLIENT_REMOTE_PORT_DEFAULT;

	if (osmo_strlcpy(mgcp->actual.endpoint_domain_name, conf->endpoint_domain_name,
			 sizeof(mgcp->actual.endpoint_domain_name))
	    >= sizeof(mgcp->actual.endpoint_domain_name)) {
		LOGPMGW(mgcp, LOGL_ERROR, "MGCP client: endpoint domain name is too long, max length is %zu: '%s'\n",
			sizeof(mgcp->actual.endpoint_domain_name) - 1, conf->endpoint_domain_name);
		talloc_free(mgcp);
		return NULL;
	}
	LOGPMGW(mgcp, LOGL_NOTICE, "MGCP client: using endpoint domain '@%s'\n", mgcp_client_endpoint_domain(mgcp));

	INIT_LLIST_HEAD(&mgcp->actual.reset_epnames);
	llist_for_each_entry(reset_ep, &conf->reset_epnames, list) {
		actual_reset_ep = talloc_memdup(mgcp, reset_ep, sizeof(*reset_ep));
		llist_add_tail(&actual_reset_ep->list, &mgcp->actual.reset_epnames);
	}

	if (conf->description)
		mgcp->actual.description = talloc_strdup(mgcp, conf->description);

	memcpy(&mgcp->actual.keepalive, &conf->keepalive, sizeof(conf->keepalive));
	osmo_timer_setup(&mgcp->keepalive_tx_timer, mgcp_client_keepalive_tx_timer_cb, mgcp);
	osmo_timer_setup(&mgcp->keepalive_rx_timer, mgcp_client_keepalive_rx_timer_cb, mgcp);

	return mgcp;
}

static const struct osmo_io_ops mgcp_clnt_ioops = {
	.read_cb = mgcp_read_cb,
	.write_cb = mgcp_write_cb,
};

/*! Initialize client connection (opens socket)
 *  \param[in,out] mgcp MGCP client descriptor.
 *  \returns 0 on success, -EINVAL on error. */
int mgcp_client_connect(struct mgcp_client *mgcp)
{
	int rc;
	struct reset_ep *reset_ep;
	const char *epname;
	bool some_dlcx_sent = false;

	if (!mgcp) {
		LOGPMGW(mgcp, LOGL_FATAL, "Client not initialized properly\n");
		return -EINVAL;
	}

	rc = osmo_sock_init2(AF_UNSPEC, SOCK_DGRAM, IPPROTO_UDP, mgcp->actual.local_addr,
			     mgcp->actual.local_port, mgcp->actual.remote_addr, mgcp->actual.remote_port,
			     OSMO_SOCK_F_BIND | OSMO_SOCK_F_CONNECT);
	if (rc < 0) {
		LOGPMGW(mgcp, LOGL_FATAL,
		     "Failed to initialize socket %s:%u -> %s:%u for MGW: %s\n",
		     mgcp->actual.local_addr ? mgcp->actual.local_addr : "(any)", mgcp->actual.local_port,
		     mgcp->actual.remote_addr ? mgcp->actual.local_addr : "(any)", mgcp->actual.remote_port,
		     strerror(errno));
		goto error_free;
	}

	mgcp->iofd = osmo_iofd_setup(mgcp, rc, osmo_sock_get_name2(rc), OSMO_IO_FD_MODE_READ_WRITE,
				     &mgcp_clnt_ioops, mgcp);
	if (!mgcp->iofd)
		goto error_close_fd;

	LOGPMGW(mgcp, LOGL_INFO, "MGW connection: %s\n", osmo_iofd_get_name(mgcp->iofd));

	osmo_iofd_register(mgcp->iofd, -1);
	osmo_iofd_set_alloc_info(mgcp->iofd, 4096, 128);
	osmo_iofd_set_txqueue_max_length(mgcp->iofd, 1024);

	/* If configured, send a DLCX message to the endpoints that are configured to
	 * be reset on startup. Usually this is a wildcarded endpoint. */
	llist_for_each_entry(reset_ep, &mgcp->actual.reset_epnames, list) {
		epname = _mgcp_client_name_append_domain(mgcp, reset_ep->name);
		LOGPMGW(mgcp, LOGL_INFO, "Sending DLCX to: %s\n", epname);
		_mgcp_client_send_dlcx(mgcp, epname);
		some_dlcx_sent = true;
	}

	if (mgcp->actual.keepalive.req_interval_sec > 0) {
		if (!some_dlcx_sent) {
			/* Attempt an immediate probe to find out if link is UP or DOWN: */
			osmo_timer_schedule(&mgcp->keepalive_tx_timer, 0, 0);
		}
		/* else: keepalive_tx_timer was already scheduled (if needed) down in the stack during Tx DLCX above */
	} else {
		/* Assume link is UP by default, so that this MGW can be selected: */
		mgcp->conn_up = true;
	}

	if (mgcp->actual.keepalive.timeout_sec > 0)
		osmo_timer_schedule(&mgcp->keepalive_rx_timer, mgcp->actual.keepalive.timeout_sec, 0);

	return 0;

error_close_fd:
	close(rc);
error_free:
	return rc;
}

/*! DEPRECATED: Initialize client connection (opens socket)
 *  \param[in,out] mgcp MGCP client descriptor.
 *  \returns 0 on success, -EINVAL on error. */
int mgcp_client_connect2(struct mgcp_client *mgcp, unsigned int retry_n_ports)
{
	return mgcp_client_connect(mgcp);
}

/*! Terminate client connection
 *  \param[in,out] mgcp MGCP client descriptor.
 *  \returns 0 on success, -EINVAL on error. */
void mgcp_client_disconnect(struct mgcp_client *mgcp)
{
	if (!mgcp) {
		LOGP(DLMGCP, LOGL_FATAL, "MGCP client not initialized properly\n");
		return;
	}

	/* Disarm keepalive Tx/Rx timer until next connect() */
	osmo_timer_del(&mgcp->keepalive_rx_timer);
	osmo_timer_del(&mgcp->keepalive_tx_timer);
	mgcp->conn_up = false;

	osmo_iofd_txqueue_clear(mgcp->iofd);
	LOGPMGW(mgcp, LOGL_INFO, "MGCP association: %s -- closed!\n", osmo_iofd_get_name(mgcp->iofd));
	osmo_iofd_free(mgcp->iofd);
}

/*! Get the IP-Aaddress of the associated MGW as string.
 *  \param[in] mgcp MGCP client descriptor.
 *  \returns a pointer to the address string. */
const char *mgcp_client_remote_addr_str(struct mgcp_client *mgcp)
{
	return mgcp->actual.remote_addr;
}

/*! Get the IP-Port of the associated MGW.
 *  \param[in] mgcp MGCP client descriptor.
 *  \returns port number. */
uint16_t mgcp_client_remote_port(struct mgcp_client *mgcp)
{
	return mgcp->actual.remote_port;
}

/*! Get the IP-Address of the associated MGW as its numeric representation.
 *  DEPRECATED, DON'T USE.
 *  \param[in] mgcp MGCP client descriptor.
 *  \returns IP-Address as 32 bit integer (network byte order) */
uint32_t mgcp_client_remote_addr_n(struct mgcp_client *mgcp)
{
	return 0;
}

/* To compose endpoint names, usually for CRCX, use this as domain name.
 * For example, snprintf("rtpbridge\*@%s", mgcp_client_endpoint_domain(mgcp)). */
const char *mgcp_client_endpoint_domain(const struct mgcp_client *mgcp)
{
	return mgcp->actual.endpoint_domain_name[0] ? mgcp->actual.endpoint_domain_name : "mgw";
}

/*! Compose endpoint name for a wildcarded request to the virtual trunk
 *  \param[in] mgcp MGCP client descriptor.
 *  \returns string containing the endpoint name (e.g. rtpbridge\*@mgw) */
const char *mgcp_client_rtpbridge_wildcard(const struct mgcp_client *mgcp)
{
	return _mgcp_client_name_append_domain(mgcp, "rtpbridge/*");
}

/*! Compose endpoint name for an E1 endpoint.
 *  \param[in] ctx talloc context.
 *  \param[in] mgcp MGCP client descriptor.
 *  \param[in] trunk_id id number of the E1 trunk (1-64).
 *  \param[in] ts timeslot on the E1 trunk (1-31).
 *  \param[in] rate bitrate used on the E1 trunk (e.g 16 for 16kbit).
 *  \param[in] offset bit offset of the E1 subslot (e.g. 4 for the third 16k subslot).
 *  \returns string containing the endpoint name (e.g. ds/e1-1/s-1/su16-4). */
const char *mgcp_client_e1_epname(void *ctx, const struct mgcp_client *mgcp, uint8_t trunk_id, uint8_t ts,
				  uint8_t rate, uint8_t offset)
{
	/* See also comment in libosmo-mgcp, mgcp_client.c, gen_e1_epname() */
	const uint8_t valid_rates[] = { 64, 32, 32, 16, 16, 16, 16, 8, 8, 8, 8, 8, 8, 8, 8 };
	const uint8_t valid_offsets[] = { 0, 0, 4, 0, 2, 4, 6, 0, 1, 2, 3, 4, 5, 6, 7 };

	uint8_t i;
	bool rate_offs_valid = false;
	char *epname;

	epname =
	    talloc_asprintf(ctx, "ds/e1-%u/s-%u/su%u-%u@%s", trunk_id, ts, rate, offset,
			    mgcp_client_endpoint_domain(mgcp));
	if (!epname) {
		LOGPMGW(mgcp, LOGL_ERROR, "Cannot compose MGCP e1-endpoint name!\n");
		return NULL;
	}

	/* Check if the supplied rate/offset pair resembles a valid combination */
	for (i = 0; i < sizeof(valid_rates); i++) {
		if (valid_rates[i] == rate && valid_offsets[i] == offset)
			rate_offs_valid = true;
	}
	if (!rate_offs_valid) {
		LOGPMGW(mgcp, LOGL_ERROR,
			"Cannot compose MGCP e1-endpoint name (%s), rate(%u)/offset(%u) combination is invalid!\n",
			epname, rate, offset);
		talloc_free(epname);
		return NULL;
	}

	/* An E1 line has a maximum of 32 timeslots, while the first (ts=0) is
	 * reserverd for framing and alignment, so we can not use it here. */
	if (ts == 0 || ts > NUM_E1_TS-1) {
		LOGPMGW(mgcp, LOGL_ERROR,
			"Cannot compose MGCP e1-endpoint name (%s), E1-timeslot number (%u) is invalid!\n",
			epname, ts);
		talloc_free(epname);
		return NULL;
	}

	return epname;
}

struct mgcp_response_pending *mgcp_client_pending_add(struct mgcp_client *mgcp, mgcp_trans_id_t trans_id,
						      mgcp_response_cb_t response_cb, void *priv)
{
	struct mgcp_response_pending *pending;

	pending = talloc_zero(mgcp, struct mgcp_response_pending);
	if (!pending)
		return NULL;

	pending->trans_id = trans_id;
	pending->response_cb = response_cb;
	pending->priv = priv;
	llist_add_tail(&pending->entry, &mgcp->responses_pending);

	return pending;
}

/* Send the MGCP message in msg to the MGW and handle a response with
 * response_cb. NOTE: the response_cb still needs to call
 * mgcp_response_parse_params(response) to get the parsed parameters -- to
 * potentially save some CPU cycles, only the head line has been parsed when
 * the response_cb is invoked.
 * Before the priv pointer becomes invalid, e.g. due to transaction timeout,
 * mgcp_client_cancel() needs to be called for this transaction.
 */
int mgcp_client_tx(struct mgcp_client *mgcp, struct msgb *msg,
		   mgcp_response_cb_t response_cb, void *priv)
{
	struct mgcp_response_pending *pending = NULL;
	mgcp_trans_id_t trans_id;
	int rc;

	trans_id = msg->cb[MSGB_CB_MGCP_TRANS_ID];
	if (!trans_id) {
		LOGPMGW(mgcp, LOGL_ERROR,
			"Unset transaction id in mgcp send request\n");
		talloc_free(msg);
		return -EINVAL;
	}

	/* Do not allocate a dummy 'mgcp_response_pending' entry */
	if (response_cb != NULL) {
		pending = mgcp_client_pending_add(mgcp, trans_id, response_cb, priv);
		if (!pending) {
			talloc_free(msg);
			return -ENOMEM;
		}
	}

	if (msgb_l2len(msg) > 4096) {
		LOGPMGW(mgcp, LOGL_ERROR,
			"Cannot send, MGCP message too large: %u\n",
			msgb_l2len(msg));
		msgb_free(msg);
		rc = -EINVAL;
		goto mgcp_tx_error;
	}

	rc = mgcp_do_write(mgcp, msg);
	if (rc) {
		LOGPMGW(mgcp, LOGL_FATAL, "Could not queue message to MGW\n");
		goto mgcp_tx_error;
	} else
		LOGPMGW(mgcp, LOGL_DEBUG, "Queued %u bytes for MGW\n",
			msgb_l2len(msg));
	return 0;

mgcp_tx_error:
	if (!pending)
		return rc;
	/* Dequeue pending response, it's going to be free()d */
	llist_del(&pending->entry);
	/* Pass NULL to response cb to indicate an error */
	mgcp_client_handle_response(mgcp, pending, NULL);
	return rc;
}

/*! Cancel a pending transaction.
 *  \param[in] mgcp MGCP client descriptor.
 *  \param[in,out] trans_id Transaction id.
 *  \returns 0 on success, -ENOENT on error.
 *
 * Should a priv pointer passed to mgcp_client_tx() become invalid, this function must be called. In
 * practical terms, if the caller of mgcp_client_tx() wishes to tear down a transaction without having
 * received a response this function must be called. The trans_id can be obtained by calling
 * mgcp_msg_trans_id() on the msgb produced by mgcp_msg_gen(). */
int mgcp_client_cancel(struct mgcp_client *mgcp, mgcp_trans_id_t trans_id)
{
	struct mgcp_response_pending *pending = mgcp_client_response_pending_get(mgcp, trans_id);
	if (!pending) {
		/*! Note: it is not harmful to cancel a transaction twice. */
		LOGPMGW(mgcp, LOGL_ERROR, "Cannot cancel, no such transaction: %u\n", trans_id);
		return -ENOENT;
	}
	LOGPMGW(mgcp, LOGL_DEBUG, "Canceled transaction %u\n", trans_id);
	talloc_free(pending);
	return 0;
	/*! We don't really need to clean up the wqueue: In all sane cases, the msgb has already been sent
	 *  out and is no longer in the wqueue. If it still is in the wqueue, then sending MGCP messages
	 *  per se is broken and the program should notice so by a full wqueue. Even if this was called
	 *  before we had a chance to send out the message and it is still going to be sent, we will just
	 *  ignore the reply to it later. Removing a msgb from the wqueue here would just introduce more
	 *  bug surface in terms of failing to update wqueue API's counters or some such.
	 */
}

static mgcp_trans_id_t mgcp_client_next_trans_id(struct mgcp_client *mgcp)
{
	/* avoid zero trans_id to distinguish from unset trans_id */
	if (!mgcp->next_trans_id)
		mgcp->next_trans_id ++;
	return mgcp->next_trans_id ++;
}

#define MGCP_CRCX_MANDATORY (MGCP_MSG_PRESENCE_ENDPOINT | \
			     MGCP_MSG_PRESENCE_CALL_ID | \
			     MGCP_MSG_PRESENCE_CONN_MODE)
#define MGCP_MDCX_MANDATORY (MGCP_MSG_PRESENCE_ENDPOINT | \
			     MGCP_MSG_PRESENCE_CALL_ID |  \
			     MGCP_MSG_PRESENCE_CONN_ID)
#define MGCP_DLCX_MANDATORY (MGCP_MSG_PRESENCE_ENDPOINT)
#define MGCP_AUEP_MANDATORY (MGCP_MSG_PRESENCE_ENDPOINT)
#define MGCP_RSIP_MANDATORY 0	/* none */

/* Helper function for mgcp_msg_gen(): Add LCO information to MGCP message */
static int add_lco(struct msgb *msg, struct mgcp_msg *mgcp_msg)
{
	unsigned int i;
	const char *codec;

#define MSGB_PRINTF_OR_RET(FMT, ARGS...) do { \
		if (msgb_printf(msg, FMT, ##ARGS) != 0) { \
			LOGP(DLMGCP, LOGL_ERROR, "Message buffer too small, can not generate MGCP/SDP message\n"); \
			return -ENOBUFS; \
		} \
	} while (0)

	MSGB_PRINTF_OR_RET("L:");

	if (mgcp_msg->ptime)
		MSGB_PRINTF_OR_RET(" p:%u,", mgcp_msg->ptime);

	if (mgcp_msg->ptmap_len) {
		MSGB_PRINTF_OR_RET(" a:");
		for (i = 0; i < mgcp_msg->ptmap_len; i++) {
			codec = get_value_string_or_null(osmo_mgcpc_codec_names, mgcp_msg->ptmap[i].codec);

			/* Note: Use codec descriptors from enum mgcp_codecs
			 * in mgcp_client only! */
			if (!codec)
				return -EINVAL;

			MSGB_PRINTF_OR_RET("%s", extract_codec_name(codec));
			if (i < mgcp_msg->ptmap_len - 1)
				MSGB_PRINTF_OR_RET(";");
		}
		MSGB_PRINTF_OR_RET(",");
	}

	MSGB_PRINTF_OR_RET(" nt:IN\r\n");
	return 0;

#undef MSGB_PRINTF_OR_RET
}

/* Helper function for mgcp_msg_gen(): Add SDP information to MGCP message */
static int add_sdp(struct msgb *msg, struct mgcp_msg *mgcp_msg, struct mgcp_client *mgcp)
{
	unsigned int i;
	char local_ip[INET6_ADDRSTRLEN];
	int local_ip_family, audio_ip_family;
	const char *codec;
	unsigned int pt;
	uint16_t audio_port;

#define MSGB_PRINTF_OR_RET(FMT, ARGS...) do { \
		if (msgb_printf(msg, FMT, ##ARGS) != 0) { \
			LOGPMGW(mgcp, LOGL_ERROR, "Message buffer too small, can not generate MGCP message (SDP)\n"); \
			return -ENOBUFS; \
		} \
	} while (0)

	/* Add separator to mark the beginning of the SDP block */
	MSGB_PRINTF_OR_RET("\r\n");

	/* Add SDP protocol version */
	MSGB_PRINTF_OR_RET("v=0\r\n");

	/* Determine local IP-Address */
	if (osmo_sock_local_ip(local_ip, mgcp->actual.remote_addr) < 0) {
		LOGPMGW(mgcp, LOGL_ERROR,
			"Could not determine local IP-Address!\n");
		return -EINVAL;
	}
	local_ip_family = osmo_ip_str_type(local_ip);
	if (local_ip_family == AF_UNSPEC)
		return -EINVAL;

	/* Add owner/creator (SDP) */
	MSGB_PRINTF_OR_RET("o=- %x 23 IN IP%c %s\r\n", mgcp_msg->call_id,
			  local_ip_family == AF_INET6 ? '6' : '4',
			  local_ip);

	/* Add session name (none) */
	MSGB_PRINTF_OR_RET("s=-\r\n");

	/* Add RTP address */
	if (mgcp_msg->presence & MGCP_MSG_PRESENCE_AUDIO_IP) {
		audio_ip_family = osmo_ip_str_type(mgcp_msg->audio_ip);
		if (audio_ip_family == AF_UNSPEC)
			return -EINVAL;
		if (strlen(mgcp_msg->audio_ip) <= 0) {
			LOGPMGW(mgcp, LOGL_ERROR,
				"Empty ip address, can not generate MGCP message\n");
			return -EINVAL;
		}
		MSGB_PRINTF_OR_RET("c=IN IP%c %s\r\n",
				   audio_ip_family == AF_INET6 ? '6' : '4',
				   mgcp_msg->audio_ip);
	}

	/* Add time description, active time (SDP) */
	MSGB_PRINTF_OR_RET("t=0 0\r\n");

	/* Add RTP address port and codecs */
	audio_port = 0;
	if ((mgcp_msg->presence & MGCP_MSG_PRESENCE_AUDIO_PORT)) {
		audio_port = mgcp_msg->audio_port;
		if (!audio_port) {
			LOGPMGW(mgcp, LOGL_ERROR,
				"Invalid port number, can not generate MGCP message\n");
			return -EINVAL;
		}
	}
	MSGB_PRINTF_OR_RET("m=audio %u RTP/AVP", audio_port);
	for (i = 0; i < mgcp_msg->ptmap_len; i++)
		MSGB_PRINTF_OR_RET(" %u", mgcp_msg->ptmap[i].pt);
	MSGB_PRINTF_OR_RET("\r\n");

	/* Add optional codec parameters (fmtp) */
	if (mgcp_msg->param_present) {
		for (i = 0; i < mgcp_msg->ptmap_len; i++) {
			/* The following is only applicable for AMR */
			if (mgcp_msg->ptmap[i].codec != CODEC_AMR_8000_1
			    && mgcp_msg->ptmap[i].codec != CODEC_AMRWB_16000_1)
				continue;
			pt = mgcp_msg->ptmap[i].pt;
			if (mgcp_msg->param.amr_octet_aligned_present && mgcp_msg->param.amr_octet_aligned)
				MSGB_PRINTF_OR_RET("a=fmtp:%u octet-align=1\r\n", pt);
			else if (mgcp_msg->param.amr_octet_aligned_present && !mgcp_msg->param.amr_octet_aligned)
				MSGB_PRINTF_OR_RET("a=fmtp:%u octet-align=0\r\n", pt);
		}
	}

	for (i = 0; i < mgcp_msg->ptmap_len; i++) {
		pt = mgcp_msg->ptmap[i].pt;

		/* Note: Only dynamic payload type from the range 96-127
		 * require to be explained further via rtpmap. All others
		 * are implcitly definedby the number in m=audio */
		if (pt >= 96 && pt <= 127) {
			codec = get_value_string_or_null(osmo_mgcpc_codec_names, mgcp_msg->ptmap[i].codec);

			/* Note: Use codec descriptors from enum mgcp_codecs
			 * in mgcp_client only! */
			if (!codec)
				return -EINVAL;

			MSGB_PRINTF_OR_RET("a=rtpmap:%u %s\r\n", pt, codec);
		}
	}

	if (mgcp_msg->ptime)
		MSGB_PRINTF_OR_RET("a=ptime:%u\r\n", mgcp_msg->ptime);

	return 0;
#undef MSGB_PRINTF_OR_RET
}

/*! Generate an MGCP message
 *  \param[in] mgcp MGCP client descriptor.
 *  \param[in] mgcp_msg Message description
 *  \returns message buffer on success, NULL on error. */
struct msgb *mgcp_msg_gen(struct mgcp_client *mgcp, struct mgcp_msg *mgcp_msg)
{
	mgcp_trans_id_t trans_id = mgcp_client_next_trans_id(mgcp);
	uint32_t mandatory_mask;
	struct msgb *msg = msgb_alloc_headroom(4096, 128, "MGCP tx");
	bool use_sdp = false;
	char buf[32];

#define MSGB_PRINTF_OR_RET(FMT, ARGS...) do { \
		if (msgb_printf(msg, FMT, ##ARGS) != 0) { \
			LOGPMGW(mgcp, LOGL_ERROR, "Message buffer too small, can not generate MGCP/SDP message\n"); \
			goto exit_error; \
		} \
	} while (0)

	msg->l2h = msg->data;
	msg->cb[MSGB_CB_MGCP_TRANS_ID] = trans_id;

	/* Add command verb */
	switch (mgcp_msg->verb) {
	case MGCP_VERB_CRCX:
		mandatory_mask = MGCP_CRCX_MANDATORY;
		MSGB_PRINTF_OR_RET("CRCX %u", trans_id);
		break;
	case MGCP_VERB_MDCX:
		mandatory_mask = MGCP_MDCX_MANDATORY;
		MSGB_PRINTF_OR_RET("MDCX %u", trans_id);
		break;
	case MGCP_VERB_DLCX:
		mandatory_mask = MGCP_DLCX_MANDATORY;
		MSGB_PRINTF_OR_RET("DLCX %u", trans_id);
		break;
	case MGCP_VERB_AUEP:
		mandatory_mask = MGCP_AUEP_MANDATORY;
		MSGB_PRINTF_OR_RET("AUEP %u", trans_id);
		break;
	case MGCP_VERB_RSIP:
		mandatory_mask = MGCP_RSIP_MANDATORY;
		MSGB_PRINTF_OR_RET("RSIP %u", trans_id);
		break;
	default:
		LOGPMGW(mgcp, LOGL_ERROR, "Invalid command verb, can not generate MGCP message\n");
		goto exit_error;
	}

	/* Check if mandatory fields are missing */
	if (!((mgcp_msg->presence & mandatory_mask) == mandatory_mask)) {
		LOGPMGW(mgcp, LOGL_ERROR,
			"One or more missing mandatory fields, can not generate MGCP message\n");
		goto exit_error;
	}

	/* Add endpoint name */
	if (mgcp_msg->presence & MGCP_MSG_PRESENCE_ENDPOINT) {
		if (strlen(mgcp_msg->endpoint) <= 0) {
			LOGPMGW(mgcp, LOGL_ERROR, "Empty endpoint name, can not generate MGCP message\n");
			goto exit_error;
		}

		if (strstr(mgcp_msg->endpoint, "@") == NULL) {
			LOGPMGW(mgcp, LOGL_ERROR,
				"Endpoint name (%s) lacks separator (@), can not generate MGCP message\n",
				mgcp_msg->endpoint);
			goto exit_error;
		}

		MSGB_PRINTF_OR_RET(" %s", mgcp_msg->endpoint);
	}

	/* Add protocol version */
	MSGB_PRINTF_OR_RET(" MGCP 1.0\r\n");

	/* Add call id */
	if (mgcp_msg->presence & MGCP_MSG_PRESENCE_CALL_ID)
		MSGB_PRINTF_OR_RET("C: %x\r\n", mgcp_msg->call_id);

	/* Add connection id */
	if (mgcp_msg->presence & MGCP_MSG_PRESENCE_CONN_ID) {
		if (strlen(mgcp_msg->conn_id) <= 0) {
			LOGPMGW(mgcp, LOGL_ERROR, "Empty connection id, can not generate MGCP message\n");
			goto exit_error;
		}
		MSGB_PRINTF_OR_RET("I: %s\r\n", mgcp_msg->conn_id);
	}

	/* Using SDP makes sense when a valid IP or Port is specified,
	 * if we do not know this information yet, we fall back to LCO */
	if (mgcp_msg->presence & MGCP_MSG_PRESENCE_AUDIO_IP
	    || mgcp_msg->presence & MGCP_MSG_PRESENCE_AUDIO_PORT)
		use_sdp = true;

	/* Add local connection options (LCO) */
	if (!use_sdp
	    && (mgcp_msg->verb == MGCP_VERB_CRCX
		|| mgcp_msg->verb == MGCP_VERB_MDCX)) {
		if (add_lco(msg, mgcp_msg) < 0) {
			LOGPMGW(mgcp, LOGL_ERROR, "Failed to add LCO, can not generate MGCP message\n");
			goto exit_error;
		}
	}

	/* Add mode */
	if (mgcp_msg->presence & MGCP_MSG_PRESENCE_CONN_MODE)
		MSGB_PRINTF_OR_RET("M: %s\r\n", mgcp_client_cmode_name(mgcp_msg->conn_mode));

	/* Add X-Osmo-IGN */
	if ((mgcp_msg->presence & MGCP_MSG_PRESENCE_X_OSMO_IGN)
	    && (mgcp_msg->x_osmo_ign != 0))
		MSGB_PRINTF_OR_RET(MGCP_X_OSMO_IGN_HEADER "%s\r\n",
				   mgcp_msg->x_osmo_ign & MGCP_X_OSMO_IGN_CALLID ? " C" : "");

	/* Add X-Osmo-Osmux */
	if ((mgcp_msg->presence & MGCP_MSG_PRESENCE_X_OSMO_OSMUX_CID)) {
		if (mgcp_msg->x_osmo_osmux_cid < -1 || mgcp_msg->x_osmo_osmux_cid > OSMUX_CID_MAX) {
			LOGPMGW(mgcp, LOGL_ERROR, "Wrong Osmux CID %d, can not generate MGCP message\n",
				mgcp_msg->x_osmo_osmux_cid);
			goto exit_error;
		}
		snprintf(buf, sizeof(buf), " %d", mgcp_msg->x_osmo_osmux_cid);
		MSGB_PRINTF_OR_RET(MGCP_X_OSMO_OSMUX_HEADER "%s\r\n",
				   mgcp_msg->x_osmo_osmux_cid == -1 ? " *" : buf);
	}


	/* Add session description protocol (SDP) */
	if (use_sdp
	    && (mgcp_msg->verb == MGCP_VERB_CRCX
		|| mgcp_msg->verb == MGCP_VERB_MDCX)) {
		if (add_sdp(msg, mgcp_msg, mgcp) < 0) {
			LOGPMGW(mgcp, LOGL_ERROR, "Failed to add SDP, can not generate MGCP message\n");
			goto exit_error;
		}
	}

	return msg;

exit_error:
	msgb_free(msg);
	return NULL;
#undef MSGB_PRINTF_OR_RET
}

/*! Retrieve the MGCP transaction ID from a msgb generated by mgcp_msg_gen()
 *  \param[in] msg message buffer
 *  \returns Transaction id. */
mgcp_trans_id_t mgcp_msg_trans_id(struct msgb *msg)
{
	return (mgcp_trans_id_t)msg->cb[MSGB_CB_MGCP_TRANS_ID];
}

/*! Get the configuration parameters for a given MGCP client instance
 *  \param[in] mgcp MGCP client descriptor.
 *  \returns configuration */
struct mgcp_client_conf *mgcp_client_conf_actual(struct mgcp_client *mgcp)
{
	return &mgcp->actual;
}

const struct value_string mgcp_client_connection_mode_strs[] = {
	{ MGCP_CONN_NONE, "none" },
	{ MGCP_CONN_RECV_SEND, "sendrecv" },
	{ MGCP_CONN_SEND_ONLY, "sendonly" },
	{ MGCP_CONN_RECV_ONLY, "recvonly" },
	{ MGCP_CONN_CONFECHO, "confecho" },
	{ MGCP_CONN_LOOPBACK, "loopback" },
	{ 0, NULL }
};

/*! Get MGCP client instance name (VTY).
 *  \param[in] mgcp MGCP client descriptor.
 *  \returns MGCP client name.
 *
 *  The user can only modify the name of an MGCP client instance when it is
 *  part of a pool. For single MGCP client instances and MGCP client instance
 *  where no description is set via the VTY, the MGW domain name will be used
 *  as name. */
const char *mgcp_client_name(const struct mgcp_client *mgcp)
{
	if (!mgcp)
		return "(null)";

	if (mgcp->actual.description)
		return mgcp->actual.description;
	else
		return mgcp_client_endpoint_domain(mgcp);
}

/*! Return typical cmp result, comparing a to b.
 * Return 0 if a == b, -1 if a < b, 1 if a > b; comparing all members of ptmap in turn. */
int ptmap_cmp(const struct ptmap *a, const struct ptmap *b)
{
	int rc;
	if (a == b)
		return 0;
	if (!a)
		return -1;
	if (!b)
		return 1;
	rc = OSMO_CMP(a->codec, b->codec);
	if (rc)
		return rc;
	return OSMO_CMP(a->pt, b->pt);
}
