/*! \file logging_gsmtap.c
 *  libosmocore log output encapsulated in GSMTAP.
 *
 *  Encapsulating the log output inside GSMTAP frames allows us to
 *  observer protocol traces (of Um, Abis, A or any other interface in
 *  the Osmocom world) with synchronous interspersed log messages.
 */
/*
 * (C) 2016 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.
 *
 * You should have received a copy of the GNU General Public License along
 * with this program; if not, write to the Free Software Foundation, Inc.,
 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 */

/*! \addtogroup logging
 *  @{
 * \file logging_gsmtap.c */

#include "../config.h"

#include <stdarg.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <stdbool.h>

#ifdef HAVE_STRINGS_H
#include <strings.h>
#endif

#include <osmocom/core/talloc.h>
#include <osmocom/core/utils.h>
#include <osmocom/core/gsmtap.h>
#include <osmocom/core/gsmtap_util.h>
#include <osmocom/core/logging.h>
#include <osmocom/core/timer.h>
#include <osmocom/core/byteswap.h>

#define	GSMTAP_LOG_MAX_SIZE 4096

static void _gsmtap_raw_output(struct log_target *target, int subsys,
			       unsigned int level, const char *file,
			       int line, int cont, const char *format,
			       va_list ap)
{
	struct msgb *msg;
	struct gsmtap_hdr *gh;
	struct gsmtap_osmocore_log_hdr *golh;
	const char *subsys_name = log_category_name(subsys);
	struct timeval tv;
	int rc;

	/* get timestamp ASAP */
	osmo_gettimeofday(&tv, NULL);

	msg = msgb_alloc(sizeof(*gh)+sizeof(*golh)+GSMTAP_LOG_MAX_SIZE,
			 "GSMTAP logging");

	/* GSMTAP header */
	gh = (struct gsmtap_hdr *) msgb_put(msg, sizeof(*gh));
	memset(gh, 0, sizeof(*gh));
	gh->version = GSMTAP_VERSION;
	gh->hdr_len = sizeof(*gh)/4;
	gh->type = GSMTAP_TYPE_OSMOCORE_LOG;

	/* Logging header */
	golh = (struct gsmtap_osmocore_log_hdr *) msgb_put(msg, sizeof(*golh));
	osmo_strlcpy(golh->proc_name, target->tgt_gsmtap.ident,
		     sizeof(golh->proc_name));
	if (subsys_name)
		osmo_strlcpy(golh->subsys, subsys_name+1, sizeof(golh->subsys));
	else
		golh->subsys[0] = '\0';
	osmo_strlcpy(golh->src_file.name, file, sizeof(golh->src_file.name));
	golh->src_file.line_nr = osmo_htonl(line);
	golh->level = level;
	/* we always store the timestamp in the message, irrespective
	 * of hat prrint_[ext_]timestamp say */
	golh->ts.sec = osmo_htonl(tv.tv_sec);
	golh->ts.usec = osmo_htonl(tv.tv_usec);

	rc = vsnprintf((char *) msg->tail, msgb_tailroom(msg), format, ap);
	if (rc < 0)
		return;
	msgb_put(msg, rc);

	gsmtap_sendmsg(target->tgt_gsmtap.gsmtap_inst, msg);
}

/*! Create a new logging target for GSMTAP logging
 *  \param[in] ident string identifier
 *  \returns Log target in case of success, NULL in case of error
 */
struct log_target *log_target_create_gsmtap(const char *host, uint16_t port,
					    const char *ident,
					    bool ofd_wq_mode,
					    bool add_sink)
{
	struct log_target *target;
	struct gsmtap_inst *gti;

	target = log_target_create();
	if (!target)
		return NULL;

	gti = gsmtap_source_init(host, port, ofd_wq_mode);
	if (!gti) {
		log_target_destroy(target);
		return NULL;
	}

	if (add_sink)
		gsmtap_source_add_sink(gti);

	target->tgt_gsmtap.gsmtap_inst = gti;
	target->tgt_gsmtap.ident = talloc_strdup(target, ident);
	target->tgt_gsmtap.hostname = talloc_strdup(target, host);

	target->type = LOG_TGT_TYPE_GSMTAP;
	target->raw_output = _gsmtap_raw_output;

	return target;
}

/* @} */
