/*
 * arch/sh/kernel/cpu/bus.c
 *
 * Virtual bus for SuperH.
 *
 * Copyright (C) 2004 Paul Mundt
 *
 * Shamelessly cloned from arch/arm/mach-omap/bus.c, which was written
 * by:
 *
 *  	Copyright (C) 2003 - 2004 Nokia Corporation
 *  	Written by Tony Lindgren <tony@atomide.com>
 *  	Portions of code based on sa1111.c.
 *
 * 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.
 */
#include <linux/kernel.h>
#include <linux/device.h>
#include <linux/init.h>
#include <linux/module.h>
#include <asm/bus-sh.h>

static int sh_bus_match(struct device *dev, struct device_driver *drv)
{
	struct sh_driver *shdrv = to_sh_driver(drv);
	struct sh_dev *shdev = to_sh_dev(dev);

	return shdev->dev_id == shdrv->dev_id;
}

static int sh_bus_suspend(struct device *dev, pm_message_t state)
{
	struct sh_dev *shdev = to_sh_dev(dev);
	struct sh_driver *shdrv = to_sh_driver(dev->driver);

	if (shdrv && shdrv->suspend)
		return shdrv->suspend(shdev, state);

	return 0;
}

static int sh_bus_resume(struct device *dev)
{
	struct sh_dev *shdev = to_sh_dev(dev);
	struct sh_driver *shdrv = to_sh_driver(dev->driver);

	if (shdrv && shdrv->resume)
		return shdrv->resume(shdev);

	return 0;
}

static struct device sh_bus_devices[SH_NR_BUSES] = {
	{
		.bus_id		= SH_BUS_NAME_VIRT,
	},
};

struct bus_type sh_bus_types[SH_NR_BUSES] = {
	{
		.name		= SH_BUS_NAME_VIRT,
		.match		= sh_bus_match,
		.suspend	= sh_bus_suspend,
		.resume		= sh_bus_resume,
	},
};

static int sh_device_probe(struct device *dev)
{
	struct sh_dev *shdev = to_sh_dev(dev);
	struct sh_driver *shdrv = to_sh_driver(dev->driver);

	if (shdrv && shdrv->probe)
		return shdrv->probe(shdev);

	return -ENODEV;
}

static int sh_device_remove(struct device *dev)
{
	struct sh_dev *shdev = to_sh_dev(dev);
	struct sh_driver *shdrv = to_sh_driver(dev->driver);

	if (shdrv && shdrv->remove)
		return shdrv->remove(shdev);

	return 0;
}

int sh_device_register(struct sh_dev *dev)
{
	if (!dev)
		return -EINVAL;

	if (dev->bus_id < 0 || dev->bus_id >= SH_NR_BUSES) {
		printk(KERN_ERR "%s: bus_id invalid: %s bus: %d\n",
		       __FUNCTION__, dev->name, dev->bus_id);
		return -EINVAL;
	}

	dev->dev.parent = &sh_bus_devices[dev->bus_id];
	dev->dev.bus    = &sh_bus_types[dev->bus_id];

	/* This is needed for USB OHCI to work */
	if (dev->dma_mask)
		dev->dev.dma_mask = dev->dma_mask;

	snprintf(dev->dev.bus_id, BUS_ID_SIZE, "%s%u",
		 dev->name, dev->dev_id);

	printk(KERN_INFO "Registering SH device '%s'. Parent at %s\n",
	       dev->dev.bus_id, dev->dev.parent->bus_id);

	return device_register(&dev->dev);
}

void sh_device_unregister(struct sh_dev *dev)
{
	device_unregister(&dev->dev);
}

int sh_driver_register(struct sh_driver *drv)
{
	if (!drv)
		return -EINVAL;

	if (drv->bus_id < 0 || drv->bus_id >= SH_NR_BUSES) {
		printk(KERN_ERR "%s: bus_id invalid: bus: %d device %d\n",
		       __FUNCTION__, drv->bus_id, drv->dev_id);
		return -EINVAL;
	}

	drv->drv.probe  = sh_device_probe;
	drv->drv.remove = sh_device_remove;
	drv->drv.bus    = &sh_bus_types[drv->bus_id];

	return driver_register(&drv->drv);
}

void sh_driver_unregister(struct sh_driver *drv)
{
	driver_unregister(&drv->drv);
}

static int __init sh_bus_init(void)
{
	int i, ret = 0;

	for (i = 0; i < SH_NR_BUSES; i++) {
		ret = device_register(&sh_bus_devices[i]);
		if (ret != 0) {
			printk(KERN_ERR "Unable to register bus device %s\n",
			       sh_bus_devices[i].bus_id);
			continue;
		}

		ret = bus_register(&sh_bus_types[i]);
		if (ret != 0) {
			printk(KERN_ERR "Unable to register bus %s\n",
			       sh_bus_types[i].name);
			device_unregister(&sh_bus_devices[i]);
		}
	}

	printk(KERN_INFO "SH Virtual Bus initialized\n");

	return ret;
}

static void __exit sh_bus_exit(void)
{
	int i;

	for (i = 0; i < SH_NR_BUSES; i++) {
		bus_unregister(&sh_bus_types[i]);
		device_unregister(&sh_bus_devices[i]);
	}
}

module_init(sh_bus_init);
module_exit(sh_bus_exit);

MODULE_AUTHOR("Paul Mundt <lethal@linux-sh.org>");
MODULE_DESCRIPTION("SH Virtual Bus");
MODULE_LICENSE("GPL");

EXPORT_SYMBOL(sh_bus_types);
EXPORT_SYMBOL(sh_device_register);
EXPORT_SYMBOL(sh_device_unregister);
EXPORT_SYMBOL(sh_driver_register);
EXPORT_SYMBOL(sh_driver_unregister);

