/*
 * net/tipc/bearer.c: TIPC bearer code
 * 
 * Copyright (c) 1996-2006, Ericsson AB
 * Copyright (c) 2004-2005, Wind River Systems
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 * 3. Neither the names of the copyright holders nor the names of its
 *    contributors may be used to endorse or promote products derived from
 *    this software without specific prior written permission.
 *
 * Alternatively, this software may be distributed under the terms of the
 * GNU General Public License ("GPL") version 2 as published by the Free
 * Software Foundation.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGE.
 */

#include "core.h"
#include "config.h"
#include "dbg.h"
#include "bearer.h"
#include "link.h"
#include "port.h"
#include "discover.h"
#include "bcast.h"

#define MAX_ADDR_STR 32

static struct media *media_list = 0;
static u32 media_count = 0;

struct bearer *bearers = 0;

/**
 * media_name_valid - validate media name
 * 
 * Returns 1 if media name is valid, otherwise 0.
 */

static int media_name_valid(const char *name)
{
	u32 len;

	len = strlen(name);
	if ((len + 1) > TIPC_MAX_MEDIA_NAME)
		return 0;
	return (strspn(name, tipc_alphabet) == len);
}

/**
 * media_find - locates specified media object by name
 */

static struct media *media_find(const char *name)
{
	struct media *m_ptr;
	u32 i;

	for (i = 0, m_ptr = media_list; i < media_count; i++, m_ptr++) {
		if (!strcmp(m_ptr->name, name))
			return m_ptr;
	}
	return 0;
}

/**
 * tipc_register_media - register a media type
 * 
 * Bearers for this media type must be activated separately at a later stage.
 */

int  tipc_register_media(u32 media_type,
			 char *name, 
			 int (*enable)(struct tipc_bearer *), 
			 void (*disable)(struct tipc_bearer *), 
			 int (*send_msg)(struct sk_buff *, 
					 struct tipc_bearer *,
					 struct tipc_media_addr *), 
			 char *(*addr2str)(struct tipc_media_addr *a,
					   char *str_buf, int str_size),
			 struct tipc_media_addr *bcast_addr,
			 const u32 bearer_priority,
			 const u32 link_tolerance,  /* [ms] */
			 const u32 send_window_limit)
{
	struct media *m_ptr;
	u32 media_id;
	u32 i;
	int res = -EINVAL;

	write_lock_bh(&net_lock);
	if (!media_list)
		goto exit;

	if (!media_name_valid(name)) {
		warn("Media registration error: illegal name <%s>\n", name);
		goto exit;
	}
	if (!bcast_addr) {
		warn("Media registration error: no broadcast address supplied\n");
		goto exit;
	}
	if ((bearer_priority < TIPC_MIN_LINK_PRI) &&
	    (bearer_priority > TIPC_MAX_LINK_PRI)) {
		warn("Media registration error: priority %u\n", bearer_priority);
		goto exit;
	}
	if ((link_tolerance < TIPC_MIN_LINK_TOL) || 
	    (link_tolerance > TIPC_MAX_LINK_TOL)) {
		warn("Media registration error: tolerance %u\n", link_tolerance);
		goto exit;
	}

	media_id = media_count++;
	if (media_id >= MAX_MEDIA) {
		warn("Attempt to register more than %u media\n", MAX_MEDIA);
		media_count--;
		goto exit;
	}
	for (i = 0; i < media_id; i++) {
		if (media_list[i].type_id == media_type) {
			warn("Attempt to register second media with type %u\n", 
			     media_type);
			media_count--;
			goto exit;
		}
		if (!strcmp(name, media_list[i].name)) {
			warn("Attempt to re-register media name <%s>\n", name);
			media_count--;
			goto exit;
		}
	}

	m_ptr = &media_list[media_id];
	m_ptr->type_id = media_type;
	m_ptr->send_msg = send_msg;
	m_ptr->enable_bearer = enable;
	m_ptr->disable_bearer = disable;
	m_ptr->addr2str = addr2str;
	memcpy(&m_ptr->bcast_addr, bcast_addr, sizeof(*bcast_addr));
	m_ptr->bcast = 1;
	strcpy(m_ptr->name, name);
	m_ptr->priority = bearer_priority;
	m_ptr->tolerance = link_tolerance;
	m_ptr->window = send_window_limit;
	dbg("Media <%s> registered\n", name);
	res = 0;
exit:
	write_unlock_bh(&net_lock);
	return res;
}

/**
 * media_addr_printf - record media address in print buffer
 */

void media_addr_printf(struct print_buf *pb, struct tipc_media_addr *a)
{
	struct media *m_ptr;
	u32 media_type;
	u32 i;

	media_type = ntohl(a->type);
	for (i = 0, m_ptr = media_list; i < media_count; i++, m_ptr++) {
		if (m_ptr->type_id == media_type)
			break;
	}

	if ((i < media_count) && (m_ptr->addr2str != NULL)) {
		char addr_str[MAX_ADDR_STR];

		tipc_printf(pb, "%s(%s) ", m_ptr->name, 
			    m_ptr->addr2str(a, addr_str, sizeof(addr_str)));
	} else {
		unchar *addr = (unchar *)&a->dev_addr;

		tipc_printf(pb, "UNKNOWN(%u):", media_type);
		for (i = 0; i < (sizeof(*a) - sizeof(a->type)); i++) {
			tipc_printf(pb, "%02x ", addr[i]);
		}
	}
}

/**
 * media_get_names - record names of registered media in buffer
 */

struct sk_buff *media_get_names(void)
{
	struct sk_buff *buf;
	struct media *m_ptr;
	int i;

	buf = cfg_reply_alloc(MAX_MEDIA * TLV_SPACE(TIPC_MAX_MEDIA_NAME));
	if (!buf)
		return NULL;

	read_lock_bh(&net_lock);
	for (i = 0, m_ptr = media_list; i < media_count; i++, m_ptr++) {
		cfg_append_tlv(buf, TIPC_TLV_MEDIA_NAME, m_ptr->name, 
			       strlen(m_ptr->name) + 1);
	}
	read_unlock_bh(&net_lock);
	return buf;
}

/**
 * bearer_name_validate - validate & (optionally) deconstruct bearer name
 * @name - ptr to bearer name string
 * @name_parts - ptr to area for bearer name components (or NULL if not needed)
 * 
 * Returns 1 if bearer name is valid, otherwise 0.
 */

static int bearer_name_validate(const char *name, 
				struct bearer_name *name_parts)
{
	char name_copy[TIPC_MAX_BEARER_NAME];
	char *media_name;
	char *if_name;
	u32 media_len;
	u32 if_len;

	/* copy bearer name & ensure length is OK */

	name_copy[TIPC_MAX_BEARER_NAME - 1] = 0;
	/* need above in case non-Posix strncpy() doesn't pad with nulls */
	strncpy(name_copy, name, TIPC_MAX_BEARER_NAME);
	if (name_copy[TIPC_MAX_BEARER_NAME - 1] != 0)
		return 0;

	/* ensure all component parts of bearer name are present */

	media_name = name_copy;
	if ((if_name = strchr(media_name, ':')) == NULL)
		return 0;
	*(if_name++) = 0;
	media_len = if_name - media_name;
	if_len = strlen(if_name) + 1;

	/* validate component parts of bearer name */

	if ((media_len <= 1) || (media_len > TIPC_MAX_MEDIA_NAME) || 
	    (if_len <= 1) || (if_len > TIPC_MAX_IF_NAME) || 
	    (strspn(media_name, tipc_alphabet) != (media_len - 1)) ||
	    (strspn(if_name, tipc_alphabet) != (if_len - 1)))
		return 0;

	/* return bearer name components, if necessary */

	if (name_parts) {
		strcpy(name_parts->media_name, media_name);
		strcpy(name_parts->if_name, if_name);
	}
	return 1;
}

/**
 * bearer_find - locates bearer object with matching bearer name
 */

static struct bearer *bearer_find(const char *name)
{
	struct bearer *b_ptr;
	u32 i;

	for (i = 0, b_ptr = bearers; i < MAX_BEARERS; i++, b_ptr++) {
		if (b_ptr->active && (!strcmp(b_ptr->publ.name, name)))
			return b_ptr;
	}
	return 0;
}

/**
 * bearer_find - locates bearer object with matching interface name
 */

struct bearer *bearer_find_interface(const char *if_name)
{
	struct bearer *b_ptr;
	char *b_if_name;
	u32 i;

	for (i = 0, b_ptr = bearers; i < MAX_BEARERS; i++, b_ptr++) {
		if (!b_ptr->active)
			continue;
		b_if_name = strchr(b_ptr->publ.name, ':') + 1;
		if (!strcmp(b_if_name, if_name))
			return b_ptr;
	}
	return 0;
}

/**
 * bearer_get_names - record names of bearers in buffer
 */

struct sk_buff *bearer_get_names(void)
{
	struct sk_buff *buf;
	struct media *m_ptr;
	struct bearer *b_ptr;
	int i, j;

	buf = cfg_reply_alloc(MAX_BEARERS * TLV_SPACE(TIPC_MAX_BEARER_NAME));
	if (!buf)
		return NULL;

	read_lock_bh(&net_lock);
	for (i = 0, m_ptr = media_list; i < media_count; i++, m_ptr++) {
		for (j = 0; j < MAX_BEARERS; j++) {
			b_ptr = &bearers[j];
			if (b_ptr->active && (b_ptr->media == m_ptr)) {
				cfg_append_tlv(buf, TIPC_TLV_BEARER_NAME, 
					       b_ptr->publ.name, 
					       strlen(b_ptr->publ.name) + 1);
			}
		}
	}
	read_unlock_bh(&net_lock);
	return buf;
}

void bearer_add_dest(struct bearer *b_ptr, u32 dest)
{
	nmap_add(&b_ptr->nodes, dest);
	disc_update_link_req(b_ptr->link_req);
	bcbearer_sort();
}

void bearer_remove_dest(struct bearer *b_ptr, u32 dest)
{
	nmap_remove(&b_ptr->nodes, dest);
	disc_update_link_req(b_ptr->link_req);
	bcbearer_sort();
}

/*
 * bearer_push(): Resolve bearer congestion. Force the waiting
 * links to push out their unsent packets, one packet per link
 * per iteration, until all packets are gone or congestion reoccurs.
 * 'net_lock' is read_locked when this function is called
 * bearer.lock must be taken before calling
 * Returns binary true(1) ore false(0)
 */
static int bearer_push(struct bearer *b_ptr)
{
	u32 res = TIPC_OK;
	struct link *ln, *tln;

	if (b_ptr->publ.blocked)
		return 0;

	while (!list_empty(&b_ptr->cong_links) && (res != PUSH_FAILED)) {
		list_for_each_entry_safe(ln, tln, &b_ptr->cong_links, link_list) {
			res = link_push_packet(ln);
			if (res == PUSH_FAILED)
				break;
			if (res == PUSH_FINISHED)
				list_move_tail(&ln->link_list, &b_ptr->links);
		}
	}
	return list_empty(&b_ptr->cong_links);
}

void bearer_lock_push(struct bearer *b_ptr)
{
	int res;

	spin_lock_bh(&b_ptr->publ.lock);
	res = bearer_push(b_ptr);
	spin_unlock_bh(&b_ptr->publ.lock);
	if (res)
		bcbearer_push();
}


/*
 * Interrupt enabling new requests after bearer congestion or blocking:    
 * See bearer_send().   
 */
void tipc_continue(struct tipc_bearer *tb_ptr)
{
	struct bearer *b_ptr = (struct bearer *)tb_ptr;

	spin_lock_bh(&b_ptr->publ.lock);
	b_ptr->continue_count++;
	if (!list_empty(&b_ptr->cong_links))
		k_signal((Handler)bearer_lock_push, (unsigned long)b_ptr);
	b_ptr->publ.blocked = 0;
	spin_unlock_bh(&b_ptr->publ.lock);
}

/*
 * Schedule link for sending of messages after the bearer 
 * has been deblocked by 'continue()'. This method is called 
 * when somebody tries to send a message via this link while 
 * the bearer is congested. 'net_lock' is in read_lock here
 * bearer.lock is busy
 */

static void bearer_schedule_unlocked(struct bearer *b_ptr, struct link *l_ptr)
{
	list_move_tail(&l_ptr->link_list, &b_ptr->cong_links);
}

/*
 * Schedule link for sending of messages after the bearer 
 * has been deblocked by 'continue()'. This method is called 
 * when somebody tries to send a message via this link while 
 * the bearer is congested. 'net_lock' is in read_lock here,
 * bearer.lock is free
 */

void bearer_schedule(struct bearer *b_ptr, struct link *l_ptr)
{
	spin_lock_bh(&b_ptr->publ.lock);
	bearer_schedule_unlocked(b_ptr, l_ptr);
	spin_unlock_bh(&b_ptr->publ.lock);
}


/*
 * bearer_resolve_congestion(): Check if there is bearer congestion,
 * and if there is, try to resolve it before returning.
 * 'net_lock' is read_locked when this function is called
 */
int bearer_resolve_congestion(struct bearer *b_ptr, struct link *l_ptr)
{
	int res = 1;

	if (list_empty(&b_ptr->cong_links))
		return 1;
	spin_lock_bh(&b_ptr->publ.lock);
	if (!bearer_push(b_ptr)) {
		bearer_schedule_unlocked(b_ptr, l_ptr);
		res = 0;
	}
	spin_unlock_bh(&b_ptr->publ.lock);
	return res;
}


/**
 * tipc_enable_bearer - enable bearer with the given name
 */              

int tipc_enable_bearer(const char *name, u32 bcast_scope, u32 priority)
{
	struct bearer *b_ptr;
	struct media *m_ptr;
	struct bearer_name b_name;
	char addr_string[16];
	u32 bearer_id;
	u32 with_this_prio;
	u32 i;
	int res = -EINVAL;

	if (tipc_mode != TIPC_NET_MODE)
		return -ENOPROTOOPT;

	if (!bearer_name_validate(name, &b_name) ||
	    !addr_domain_valid(bcast_scope) ||
	    !in_scope(bcast_scope, tipc_own_addr))
		return -EINVAL;

	if ((priority < TIPC_MIN_LINK_PRI ||
	     priority > TIPC_MAX_LINK_PRI) &&
	    (priority != TIPC_MEDIA_LINK_PRI))
		return -EINVAL;

	write_lock_bh(&net_lock);
	if (!bearers)
		goto failed;

	m_ptr = media_find(b_name.media_name);
	if (!m_ptr) {
		warn("No media <%s>\n", b_name.media_name);
		goto failed;
	}

	if (priority == TIPC_MEDIA_LINK_PRI)
		priority = m_ptr->priority;

restart:
	bearer_id = MAX_BEARERS;
	with_this_prio = 1;
	for (i = MAX_BEARERS; i-- != 0; ) {
		if (!bearers[i].active) {
			bearer_id = i;
			continue;
		}
		if (!strcmp(name, bearers[i].publ.name)) {
			warn("Bearer <%s> already enabled\n", name);
			goto failed;
		}
		if ((bearers[i].priority == priority) &&
		    (++with_this_prio > 2)) {
			if (priority-- == 0) {
				warn("Third bearer <%s> with priority %u, unable to lower to %u\n",
				     name, priority + 1, priority);
				goto failed;
			}
			warn("Third bearer <%s> with priority %u, lowering to %u\n",
			     name, priority + 1, priority);
			goto restart;
		}
	}
	if (bearer_id >= MAX_BEARERS) {
		warn("Attempt to enable more than %d bearers\n", MAX_BEARERS);
		goto failed;
	}

	b_ptr = &bearers[bearer_id];
	memset(b_ptr, 0, sizeof(struct bearer));

	strcpy(b_ptr->publ.name, name);
	res = m_ptr->enable_bearer(&b_ptr->publ);
	if (res) {
		warn("Failed to enable bearer <%s>\n", name);
		goto failed;
	}

	b_ptr->identity = bearer_id;
	b_ptr->media = m_ptr;
	b_ptr->net_plane = bearer_id + 'A';
	b_ptr->active = 1;
	b_ptr->detect_scope = bcast_scope;
	b_ptr->priority = priority;
	INIT_LIST_HEAD(&b_ptr->cong_links);
	INIT_LIST_HEAD(&b_ptr->links);
	if (m_ptr->bcast) {
		b_ptr->link_req = disc_init_link_req(b_ptr, &m_ptr->bcast_addr,
						     bcast_scope, 2);
	}
	b_ptr->publ.lock = SPIN_LOCK_UNLOCKED;
	write_unlock_bh(&net_lock);
	info("Enabled bearer <%s>, discovery domain %s, priority %u\n",
	     name, addr_string_fill(addr_string, bcast_scope), priority);
	return 0;
failed:
	write_unlock_bh(&net_lock);
	return res;
}

/**
 * tipc_block_bearer(): Block the bearer with the given name,
 *                      and reset all its links
 */

int tipc_block_bearer(const char *name)
{
	struct bearer *b_ptr = 0;
	struct link *l_ptr;
	struct link *temp_l_ptr;

	if (tipc_mode != TIPC_NET_MODE)
		return -ENOPROTOOPT;

	read_lock_bh(&net_lock);
	b_ptr = bearer_find(name);
	if (!b_ptr) {
		warn("Attempt to block unknown bearer <%s>\n", name);
		read_unlock_bh(&net_lock);
		return -EINVAL;
	}

	spin_lock_bh(&b_ptr->publ.lock);
	b_ptr->publ.blocked = 1;
	list_for_each_entry_safe(l_ptr, temp_l_ptr, &b_ptr->links, link_list) {
		struct node *n_ptr = l_ptr->owner;

		spin_lock_bh(&n_ptr->lock);
		link_reset(l_ptr);
		spin_unlock_bh(&n_ptr->lock);
	}
	spin_unlock_bh(&b_ptr->publ.lock);
	read_unlock_bh(&net_lock);
	info("Blocked bearer <%s>\n", name);
	return TIPC_OK;
}

/**
 * bearer_disable -
 * 
 * Note: This routine assumes caller holds net_lock.
 */

static int bearer_disable(const char *name)
{
	struct bearer *b_ptr;
	struct link *l_ptr;
	struct link *temp_l_ptr;

	if (tipc_mode != TIPC_NET_MODE)
		return -ENOPROTOOPT;

	b_ptr = bearer_find(name);
	if (!b_ptr) {
		warn("Attempt to disable unknown bearer <%s>\n", name);
		return -EINVAL;
	}

	disc_stop_link_req(b_ptr->link_req);
	spin_lock_bh(&b_ptr->publ.lock);
	b_ptr->link_req = NULL;
	b_ptr->publ.blocked = 1;
	if (b_ptr->media->disable_bearer) {
		spin_unlock_bh(&b_ptr->publ.lock);
		write_unlock_bh(&net_lock);
		b_ptr->media->disable_bearer(&b_ptr->publ);
		write_lock_bh(&net_lock);
		spin_lock_bh(&b_ptr->publ.lock);
	}
	list_for_each_entry_safe(l_ptr, temp_l_ptr, &b_ptr->links, link_list) {
		link_delete(l_ptr);
	}
	spin_unlock_bh(&b_ptr->publ.lock);
	info("Disabled bearer <%s>\n", name);
	memset(b_ptr, 0, sizeof(struct bearer));
	return TIPC_OK;
}

int tipc_disable_bearer(const char *name)
{
	int res;

	write_lock_bh(&net_lock);
	res = bearer_disable(name);
	write_unlock_bh(&net_lock);
	return res;
}



int bearer_init(void)
{
	int res;

	write_lock_bh(&net_lock);
	bearers = kmalloc(MAX_BEARERS * sizeof(struct bearer), GFP_ATOMIC);
	media_list = kmalloc(MAX_MEDIA * sizeof(struct media), GFP_ATOMIC);
	if (bearers && media_list) {
		memset(bearers, 0, MAX_BEARERS * sizeof(struct bearer));
		memset(media_list, 0, MAX_MEDIA * sizeof(struct media));
		res = TIPC_OK;
	} else {
		kfree(bearers);
		kfree(media_list);
		bearers = 0;
		media_list = 0;
		res = -ENOMEM;
	}
	write_unlock_bh(&net_lock);
	return res;
}

void bearer_stop(void)
{
	u32 i;

	if (!bearers)
		return;

	for (i = 0; i < MAX_BEARERS; i++) {
		if (bearers[i].active)
			bearers[i].publ.blocked = 1;
	}
	for (i = 0; i < MAX_BEARERS; i++) {
		if (bearers[i].active)
			bearer_disable(bearers[i].publ.name);
	}
	kfree(bearers);
	kfree(media_list);
	bearers = 0;
	media_list = 0;
	media_count = 0;
}


