/* Simple Osmocom System Monitor (osysmon): Support for CTRL monitoring */

/* (C) 2018 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.
 */

#include <string.h>

#include <osmocom/vty/vty.h>
#include <osmocom/vty/command.h>

#include "osysmon.h"
#include "simple_ctrl.h"
#include "value_node.h"

/***********************************************************************
 * Data Model
 ***********************************************************************/

/* a single CTRL client */
struct ctrl_client {
	/* links to osysmon.ctrl_clients */
	struct llist_head list;
	struct {
		/* name of this CTRL client */
		const char *name;
		/* remote host/IP */
		const char *remote_host;
		/* remote CTRL port */
		uint16_t remote_port;
	} cfg;
	struct simple_ctrl_handle *sch;
	/* list of ctrl_client_get_var objects */
	struct llist_head get_vars;
};

/* a variable we are GETing via a ctrl_client */
struct ctrl_client_get_var {
	/* links to ctrl_client.get_vars */
	struct llist_head list;
	/* back-link to ctrl_client */
	struct ctrl_client *cc;
	struct {
		/* CTRL variable name */
		const char *name;
		/* display name, if any */
		const char *display_name;
	} cfg;
	/* most recent value we received for this */
	char *last_value;
};

static struct ctrl_client *ctrl_client_find(struct osysmon_state *os, const char *name)
{
	struct ctrl_client *cc;
	llist_for_each_entry(cc, &os->ctrl_clients, list) {
		if (!strcmp(name, cc->cfg.name))
			return cc;
	}
	return NULL;
}

static struct ctrl_client *ctrl_client_create(struct osysmon_state *os, const char *name,
					      const char *host, uint16_t port)
{
	struct ctrl_client *cc;

	if (ctrl_client_find(os, name))
		return NULL;

	cc = talloc_zero(os, struct ctrl_client);
	if (!cc)
		return NULL;
	cc->cfg.name = talloc_strdup(cc, name);
	cc->cfg.remote_host = talloc_strdup(cc, host);
	cc->cfg.remote_port = port;
	INIT_LLIST_HEAD(&cc->get_vars);
	llist_add_tail(&cc->list, &os->ctrl_clients);
	/* FIXME */
	return cc;
}

static void ctrl_client_destroy(struct ctrl_client *cc)
{
	/* FIXME */
	llist_del(&cc->list);
	talloc_free(cc);
}

static struct ctrl_client_get_var *
ctrl_client_get_var_find_or_create(struct ctrl_client *cc, const char *name)
{
	struct ctrl_client_get_var *gv;
	llist_for_each_entry(gv, &cc->get_vars, list) {
		if (!strcmp(name, gv->cfg.name))
			return gv;
	}
	gv = talloc_zero(cc, struct ctrl_client_get_var);
	if (!gv)
		return NULL;
	gv->cc = cc;
	gv->cfg.name = talloc_strdup(gv, name);
	llist_add_tail(&gv->list, &cc->get_vars);
	return gv;
}

/***********************************************************************
 * VTY
 ***********************************************************************/

static struct cmd_node ctrl_client_node = {
	CTRL_CLIENT_NODE,
	"%s(config-ctrlclient)# ",
	1,
};

static struct cmd_node ctrl_client_getvar_node = {
	CTRL_CLIENT_GETVAR_NODE,
	"%s(config-ctrlclient-getvar)# ",
	1,
};

int osysmon_ctrl_go_parent(struct vty *vty)
{
	switch (vty->node) {
	case CTRL_CLIENT_NODE:
		vty->node = CONFIG_NODE;
		vty->index = NULL;
		break;
	case CTRL_CLIENT_GETVAR_NODE:
		vty->node = CTRL_CLIENT_NODE;
		{
			struct ctrl_client_get_var *gv = vty->index;
			vty->index = gv->cc;
		}
		break;
	default:
		break;
	}
	return vty->node;
}


DEFUN(cfg_ctrl_client, cfg_ctrl_client_cmd,
	"ctrl-client NAME A.B.C.D <1-65535>",
	"")
{
	struct ctrl_client *cc;
	cc = ctrl_client_find(g_oss, argv[0]);
	if (cc) {
		if ((strcmp(cc->cfg.remote_host, argv[1])) ||
		    (cc->cfg.remote_port != atoi(argv[2]))) {
			vty_out(vty, "Client %s has different IP/port, please remove it first%s",
				cc->cfg.name, VTY_NEWLINE);
			return CMD_WARNING;
		}
	} else
		cc = ctrl_client_create(g_oss, argv[0], argv[1], atoi(argv[2]));
	OSMO_ASSERT(cc);

	vty->node = CTRL_CLIENT_NODE;
	vty->index = cc;
	return CMD_SUCCESS;
}

DEFUN(cfg_no_ctrl_client, cfg_no_ctrl_client_cmd,
	"no ctrl-client NAME",
	NO_STR "")
{
	struct ctrl_client *cc;
	cc = ctrl_client_find(g_oss, argv[0]);
	if (!cc) {
		vty_out(vty, "Client %s doesn't exist%s", argv[0], VTY_NEWLINE);
		return CMD_WARNING;
	}
	ctrl_client_destroy(cc);
	return CMD_SUCCESS;
}

DEFUN(cfg_ctrlc_get_var, cfg_ctrlc_get_var_cmd,
	"get-variable NAME",
	"")
{
	struct ctrl_client *cc = vty->index;
	struct ctrl_client_get_var *ccgv;

	ccgv = ctrl_client_get_var_find_or_create(cc, argv[0]);
	OSMO_ASSERT(ccgv);

	vty->node = CTRL_CLIENT_GETVAR_NODE;
	vty->index = ccgv;
	return CMD_SUCCESS;
}

DEFUN(cfg_ctrlc_no_get_var, cfg_ctrlc_no_get_var_cmd,
	"no get-variable NAME",
	NO_STR "")
{
	struct ctrl_client *cc = vty->index;
	struct ctrl_client_get_var *ccgv;

	ccgv = ctrl_client_get_var_find_or_create(cc, argv[0]);
	talloc_free(ccgv);
	return CMD_SUCCESS;
}

static void write_one_ctrl_client(struct vty *vty, struct ctrl_client *cc)
{
	struct ctrl_client_get_var *ccgv;
	vty_out(vty, "ctrl-client %s %s %u%s", cc->cfg.name,
		cc->cfg.remote_host, cc->cfg.remote_port, VTY_NEWLINE);
	llist_for_each_entry(ccgv, &cc->get_vars, list) {
		vty_out(vty, " get-variable %s%s", ccgv->cfg.name, VTY_NEWLINE);
		if (ccgv->cfg.display_name)
			vty_out(vty, " display-name %s%s", ccgv->cfg.display_name, VTY_NEWLINE);
	}
}

static int config_write_ctrl_client(struct vty *vty)
{
	struct ctrl_client *cc;

	llist_for_each_entry(cc, &g_oss->ctrl_clients, list)
		write_one_ctrl_client(vty, cc);
	return CMD_SUCCESS;
}

static void osysmon_ctrl_vty_init(void)
{
	install_element(CONFIG_NODE, &cfg_ctrl_client_cmd);
	install_element(CONFIG_NODE, &cfg_no_ctrl_client_cmd);
	install_node(&ctrl_client_node, config_write_ctrl_client);
	install_element(CTRL_CLIENT_NODE, &cfg_ctrlc_get_var_cmd);
	install_element(CTRL_CLIENT_NODE, &cfg_ctrlc_no_get_var_cmd);
	install_node(&ctrl_client_getvar_node, NULL);
	//install_element(CTRL_CLIENT_GETVAR_NODE, &cfg_getvar_disp_name_cmd);
}


/***********************************************************************
 * Runtime Code
 ***********************************************************************/

/* called once on startup before config file parsing */
int osysmon_ctrl_init()
{
	osysmon_ctrl_vty_init();
	return 0;
}

static int ctrl_client_poll(struct ctrl_client *cc, struct value_node *parent)
{
	struct ctrl_client_get_var *ccgv;
	struct value_node *vn_clnt = value_node_add(parent, parent, cc->cfg.name, NULL);

	/* attempt to re-connect */
	if (!cc->sch)
		cc->sch = simple_ctrl_open(cc, cc->cfg.remote_host, cc->cfg.remote_port, 1000);
	/* abort, if that failed */
	if (!cc->sch) {
		llist_for_each_entry(ccgv, &cc->get_vars, list) {
			if (ccgv->last_value) {
				talloc_free(ccgv->last_value);
				ccgv->last_value = talloc_strdup(ccgv, "<UNKNOWN>");
			}
		}
		return -1;
	}

	llist_for_each_entry(ccgv, &cc->get_vars, list) {
		char *value = simple_ctrl_get(cc->sch, ccgv->cfg.name);
#if 0
		if (ccgv->last_value) {
			talloc_free(ccgv->last_value);
			ccgv->last_value = NULL;
		}
		ccgv->last_value = value;
#else
		value_node_add(vn_clnt, vn_clnt, ccgv->cfg.name, value);
		free(value); /* no talloc, this is from sscanf() */
#endif
	}
	return 0;
}

/* called periodically */
int osysmon_ctrl_poll(struct value_node *parent)
{
	struct ctrl_client *cc;
	llist_for_each_entry(cc, &g_oss->ctrl_clients, list)
		ctrl_client_poll(cc, parent);
	return 0;
}
