/*						-*- c-basic-offset: 8 -*-
 *
 * fw-card.c - card level functions
 *
 * Copyright (C) 2005-2006  Kristian Hoegsberg <krh@bitplanet.net>
 *
 * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 */

#include <linux/module.h>
#include <linux/errno.h>
#include <linux/device.h>
#include "fw-transaction.h"
#include "fw-topology.h"
#include "fw-device.h"

/* The lib/crc16.c implementation uses the standard (0x8005)
 * polynomial, but we need the ITU-T (or CCITT) polynomial (0x1021).
 * The implementation below works on an array of host-endian u32
 * words, assuming they'll be transmited msb first. */
u16
crc16_itu_t(const u32 *buffer, size_t length)
{
	int shift, i;
	u32 data;
	u16 sum, crc = 0;

	for (i = 0; i < length; i++) {
		data = *buffer++;
		for (shift = 28; shift >= 0; shift -= 4 ) {
			sum = ((crc >> 12) ^ (data >> shift)) & 0xf;
			crc = (crc << 4) ^ (sum << 12) ^ (sum << 5) ^ (sum);
		}
		crc &= 0xffff;
	}

	return crc;
}

static LIST_HEAD(card_list);

static LIST_HEAD(descriptor_list);
static int descriptor_count;

#define bib_crc(v)		((v) <<  0)
#define bib_crc_length(v)	((v) << 16)
#define bib_info_length(v)	((v) << 24)

#define bib_link_speed(v)	((v) <<  0)
#define bib_generation(v)	((v) <<  4)
#define bib_max_rom(v)		((v) <<  8)
#define bib_max_receive(v)	((v) << 12)
#define bib_cyc_clk_acc(v)	((v) << 16)
#define bib_pmc			((1) << 27)
#define bib_bmc			((1) << 28)
#define bib_isc			((1) << 29)
#define bib_cmc			((1) << 30)
#define bib_imc			((1) << 31)

static u32 *
generate_config_rom (struct fw_card *card, size_t *config_rom_length)
{
	struct fw_descriptor *desc;
	static u32 config_rom[256];
	int i, j, length;

	/* Initialize contents of config rom buffer.  On the OHCI
	 * controller, block reads to the config rom accesses the host
	 * memory, but quadlet read access the hardware bus info block
	 * registers.  That's just crack, but it means we should make
	 * sure the contents of bus info block in host memory mathces
	 * the version stored in the OHCI registers. */

	memset(config_rom, 0, sizeof config_rom);
	config_rom[0] = bib_crc_length(4) | bib_info_length(4) | bib_crc(0);
	config_rom[1] = 0x31333934;

	config_rom[2] =
		bib_link_speed(card->link_speed) |
		bib_generation(card->config_rom_generation++ % 14 + 2) |
		bib_max_rom(2) |
		bib_max_receive(card->max_receive) |
		bib_bmc | bib_isc | bib_cmc | bib_imc;
	config_rom[3] = card->guid >> 32;
	config_rom[4] = card->guid;

	/* Generate root directory. */
	i = 5;
	config_rom[i++] = 0;
	config_rom[i++] = 0x0c0083c0; /* node capabilities */
	j = i + descriptor_count;

	/* Generate root directory entries for descriptors. */
	list_for_each_entry (desc, &descriptor_list, link) {
		if (desc->immediate > 0)
			config_rom[i++] = desc->immediate;
		config_rom[i] = desc->key | (j - i);
		i++;
		j += desc->length;
	}

	/* Update root directory length. */
	config_rom[5] = (i - 5 - 1) << 16;

	/* End of root directory, now copy in descriptors. */
	list_for_each_entry (desc, &descriptor_list, link) {
		memcpy(&config_rom[i], desc->data, desc->length * 4);
		i += desc->length;
	}

	/* Calculate CRCs for all blocks in the config rom.  This
	 * assumes that CRC length and info length are identical for
	 * the bus info block, which is always the case for this
	 * implementation. */
	for (i = 0; i < j; i += length + 1) {
		length = (config_rom[i] >> 16) & 0xff;
		config_rom[i] |= crc16_itu_t(&config_rom[i + 1], length);
	}

	*config_rom_length = j;

	return config_rom;
}

static void
update_config_roms (void)
{
	struct fw_card *card;
	u32 *config_rom;
	size_t length;

	list_for_each_entry (card, &card_list, link) {
		config_rom = generate_config_rom(card, &length);
		card->driver->set_config_rom(card, config_rom, length);
	}
}

int
fw_core_add_descriptor (struct fw_descriptor *desc)
{
	size_t i;

	/* Check descriptor is valid; the length of all blocks in the
	 * descriptor has to add up to exactly the length of the
	 * block. */
	i = 0;
	while (i < desc->length)
		i += (desc->data[i] >> 16) + 1;

	if (i != desc->length)
		return -1;

	down_write(&fw_bus_type.subsys.rwsem);

	list_add_tail (&desc->link, &descriptor_list);
	descriptor_count++;
	if (desc->immediate > 0)
		descriptor_count++;
	update_config_roms();

	up_write(&fw_bus_type.subsys.rwsem);

	return 0;
}
EXPORT_SYMBOL(fw_core_add_descriptor);

void
fw_core_remove_descriptor (struct fw_descriptor *desc)
{
	down_write(&fw_bus_type.subsys.rwsem);

	list_del(&desc->link);
	descriptor_count--;
	if (desc->immediate > 0)
		descriptor_count--;
	update_config_roms();

	up_write(&fw_bus_type.subsys.rwsem);
}
EXPORT_SYMBOL(fw_core_remove_descriptor);

static const char gap_count_table[] = {
	63, 5, 7, 8, 10, 13, 16, 18, 21, 24, 26, 29, 32, 35, 37, 40
};

struct bm_data {
	struct fw_transaction t;
	struct {
		__be32 arg;
		__be32 data;
	} lock;
	u32 old;
	int rcode;
	struct completion done;
};

static void
complete_bm_lock(struct fw_card *card, int rcode,
		 void *payload, size_t length, void *data)
{
	struct bm_data *bmd = data;

	if (rcode == RCODE_COMPLETE)
		bmd->old = be32_to_cpu(*(__be32 *) payload);
	bmd->rcode = rcode;
	complete(&bmd->done);
}

static void
fw_card_bm_work(struct work_struct *work)
{
	struct fw_card *card = container_of(work, struct fw_card, work.work);
	struct fw_device *root;
	struct bm_data bmd;
	unsigned long flags;
	int root_id, new_root_id, irm_id, gap_count, generation, grace;
	int do_reset = 0;

	spin_lock_irqsave(&card->lock, flags);

	generation = card->generation;
	root = card->root_node->data;
	root_id = card->root_node->node_id;
	grace = time_after(jiffies, card->reset_jiffies + DIV_ROUND_UP(HZ, 10));

	if (card->bm_generation + 1 == generation ||
	    (card->bm_generation != generation && grace)) {
		/* This first step is to figure out who is IRM and
		 * then try to become bus manager.  If the IRM is not
		 * well defined (e.g. does not have an active link
		 * layer or does not responds to our lock request, we
		 * will have to do a little vigilante bus management.
		 * In that case, we do a goto into the gap count logic
		 * so that when we do the reset, we still optimize the
		 * gap count.  That could well save a reset in the
		 * next generation. */

		irm_id = card->irm_node->node_id;
		if (!card->irm_node->link_on) {
			new_root_id = card->local_node->node_id;
			fw_notify("IRM has link off, making local node (%02x) root.\n",
				  new_root_id);
			goto pick_me;
		}

		bmd.lock.arg = cpu_to_be32(0x3f);
		bmd.lock.data = cpu_to_be32(card->local_node->node_id);

		spin_unlock_irqrestore(&card->lock, flags);

		init_completion(&bmd.done);
		fw_send_request(card, &bmd.t, TCODE_LOCK_COMPARE_SWAP,
				irm_id, generation,
				SCODE_100, CSR_REGISTER_BASE + CSR_BUS_MANAGER_ID,
				&bmd.lock, sizeof bmd.lock,
				complete_bm_lock, &bmd);
		wait_for_completion(&bmd.done);

		if (bmd.rcode == RCODE_GENERATION) {
			/* Another bus reset happened. Just return,
			 * the BM work has been rescheduled. */
			return;
		}

		if (bmd.rcode == RCODE_COMPLETE && bmd.old != 0x3f)
			/* Somebody else is BM, let them do the work. */
			return;

		spin_lock_irqsave(&card->lock, flags);
		if (bmd.rcode != RCODE_COMPLETE) {
			/* The lock request failed, maybe the IRM
			 * isn't really IRM capable after all. Let's
			 * do a bus reset and pick the local node as
			 * root, and thus, IRM. */
			new_root_id = card->local_node->node_id;
			fw_notify("BM lock failed, making local node (%02x) root.\n",
				  new_root_id);
			goto pick_me;
		}
	} else if (card->bm_generation != generation) {
		/* OK, we weren't BM in the last generation, and it's
		 * less than 100ms since last bus reset. Reschedule
		 * this task 100ms from now. */
		spin_unlock_irqrestore(&card->lock, flags);
		schedule_delayed_work(&card->work, DIV_ROUND_UP(HZ, 10));
		return;
	}

	/* We're bus manager for this generation, so next step is to
	 * make sure we have an active cycle master and do gap count
	 * optimization. */
	card->bm_generation = generation;

	if (root == NULL) {
		/* Either link_on is false, or we failed to read the
		 * config rom.  In either case, pick another root. */
		new_root_id = card->local_node->node_id;
	} else if (atomic_read(&root->state) != FW_DEVICE_RUNNING) {
		/* If we haven't probed this device yet, bail out now
		 * and let's try again once that's done. */
		spin_unlock_irqrestore(&card->lock, flags);
		return;
	} else if (root->config_rom[2] & bib_cmc) {
		/* FIXME: I suppose we should set the cmstr bit in the
		 * STATE_CLEAR register of this node, as described in
		 * 1394-1995, 8.4.2.6.  Also, send out a force root
		 * packet for this node. */
		new_root_id = root_id;
	} else {
		/* Current root has an active link layer and we
		 * successfully read the config rom, but it's not
		 * cycle master capable. */
		new_root_id = card->local_node->node_id;
	}

 pick_me:
	/* Now figure out what gap count to set. */
	if (card->topology_type == FW_TOPOLOGY_A &&
	    card->root_node->max_hops < ARRAY_SIZE(gap_count_table))
		gap_count = gap_count_table[card->root_node->max_hops];
	else
		gap_count = 63;

	/* Finally, figure out if we should do a reset or not.  If we've
	 * done less that 5 resets with the same physical topology and we
	 * have either a new root or a new gap count setting, let's do it. */

	if (card->bm_retries++ < 5 &&
	    (card->gap_count != gap_count || new_root_id != root_id))
		do_reset = 1;

	spin_unlock_irqrestore(&card->lock, flags);

	if (do_reset) {
		fw_notify("phy config: card %d, new root=%x, gap_count=%d\n",
			  card->index, new_root_id, gap_count);
		fw_send_phy_config(card, new_root_id, generation, gap_count);
		fw_core_initiate_bus_reset(card, 1);
	}
}

static void
flush_timer_callback(unsigned long data)
{
	struct fw_card *card = (struct fw_card *)data;

	fw_flush_transactions(card);
}

void
fw_card_initialize(struct fw_card *card, const struct fw_card_driver *driver,
		   struct device *device)
{
	static atomic_t index = ATOMIC_INIT(-1);

	kref_init(&card->kref);
	card->index = atomic_inc_return(&index);
	card->driver = driver;
	card->device = device;
	card->current_tlabel = 0;
	card->tlabel_mask = 0;
	card->color = 0;

	INIT_LIST_HEAD(&card->transaction_list);
	spin_lock_init(&card->lock);
	setup_timer(&card->flush_timer,
		    flush_timer_callback, (unsigned long)card);

	card->local_node = NULL;

	INIT_DELAYED_WORK(&card->work, fw_card_bm_work);
}
EXPORT_SYMBOL(fw_card_initialize);

int
fw_card_add(struct fw_card *card,
	    u32 max_receive, u32 link_speed, u64 guid)
{
	u32 *config_rom;
	size_t length;

	card->max_receive = max_receive;
	card->link_speed = link_speed;
	card->guid = guid;

	/* FIXME: add #define's for phy registers. */
	/* Activate link_on bit and contender bit in our self ID packets.*/
	if (card->driver->update_phy_reg(card, 4, 0, 0x80 | 0x40) < 0)
		return -EIO;

	/* The subsystem grabs a reference when the card is added and
	 * drops it when the driver calls fw_core_remove_card. */
	fw_card_get(card);

	down_write(&fw_bus_type.subsys.rwsem);
	config_rom = generate_config_rom (card, &length);
	list_add_tail(&card->link, &card_list);
	up_write(&fw_bus_type.subsys.rwsem);

	return card->driver->enable(card, config_rom, length);
}
EXPORT_SYMBOL(fw_card_add);


/* The next few functions implements a dummy driver that use once a
 * card driver shuts down an fw_card.  This allows the driver to
 * cleanly unload, as all IO to the card will be handled by the dummy
 * driver instead of calling into the (possibly) unloaded module.  The
 * dummy driver just fails all IO. */

static int
dummy_enable(struct fw_card *card, u32 *config_rom, size_t length)
{
	BUG();
	return -1;
}

static int
dummy_update_phy_reg(struct fw_card *card, int address,
		     int clear_bits, int set_bits)
{
	return -ENODEV;
}

static int
dummy_set_config_rom(struct fw_card *card,
		     u32 *config_rom, size_t length)
{
	/* We take the card out of card_list before setting the dummy
	 * driver, so this should never get called. */
	BUG();
	return -1;
}

static void
dummy_send_request(struct fw_card *card, struct fw_packet *packet)
{
	packet->callback(packet, card, -ENODEV);
}

static void
dummy_send_response(struct fw_card *card, struct fw_packet *packet)
{
	packet->callback(packet, card, -ENODEV);
}

static int
dummy_cancel_packet(struct fw_card *card, struct fw_packet *packet)
{
	return -ENOENT;
}

static int
dummy_enable_phys_dma(struct fw_card *card,
		      int node_id, int generation)
{
	return -ENODEV;
}

static struct fw_card_driver dummy_driver = {
	.name            = "dummy",
	.enable          = dummy_enable,
	.update_phy_reg  = dummy_update_phy_reg,
	.set_config_rom  = dummy_set_config_rom,
	.send_request    = dummy_send_request,
	.cancel_packet   = dummy_cancel_packet,
	.send_response   = dummy_send_response,
	.enable_phys_dma = dummy_enable_phys_dma,
};

void
fw_core_remove_card(struct fw_card *card)
{
	card->driver->update_phy_reg(card, 4, 0x80 | 0x40, 0);
	fw_core_initiate_bus_reset(card, 1);

	down_write(&fw_bus_type.subsys.rwsem);
	list_del(&card->link);
	up_write(&fw_bus_type.subsys.rwsem);

	/* Set up the dummy driver. */
	card->driver = &dummy_driver;

	fw_flush_transactions(card);

	fw_destroy_nodes(card);

	fw_card_put(card);
}
EXPORT_SYMBOL(fw_core_remove_card);

struct fw_card *
fw_card_get(struct fw_card *card)
{
	kref_get(&card->kref);

	return card;
}
EXPORT_SYMBOL(fw_card_get);

static void
release_card(struct kref *kref)
{
	struct fw_card *card = container_of(kref, struct fw_card, kref);

	kfree(card);
}

/* An assumption for fw_card_put() is that the card driver allocates
 * the fw_card struct with kalloc and that it has been shut down
 * before the last ref is dropped. */
void
fw_card_put(struct fw_card *card)
{
	kref_put(&card->kref, release_card);
}
EXPORT_SYMBOL(fw_card_put);

int
fw_core_initiate_bus_reset(struct fw_card *card, int short_reset)
{
	return card->driver->update_phy_reg(card, short_reset ? 5 : 1, 0, 0x40);
}
EXPORT_SYMBOL(fw_core_initiate_bus_reset);
