diff options
Diffstat (limited to 'arch/mips/txx9/generic')
-rw-r--r-- | arch/mips/txx9/generic/setup.c | 84 | ||||
-rw-r--r-- | arch/mips/txx9/generic/setup_tx4938.c | 6 | ||||
-rw-r--r-- | arch/mips/txx9/generic/setup_tx4939.c | 6 |
3 files changed, 96 insertions, 0 deletions
diff --git a/arch/mips/txx9/generic/setup.c b/arch/mips/txx9/generic/setup.c index 7f910125761..3b7d77d61ce 100644 --- a/arch/mips/txx9/generic/setup.c +++ b/arch/mips/txx9/generic/setup.c @@ -24,6 +24,7 @@ #include <linux/serial_core.h> #include <linux/mtd/physmap.h> #include <linux/leds.h> +#include <linux/sysdev.h> #include <asm/bootinfo.h> #include <asm/time.h> #include <asm/reboot.h> @@ -912,3 +913,86 @@ void __init txx9_aclc_init(unsigned long baseaddr, int irq, platform_device_put(pdev); #endif } + +static struct sysdev_class txx9_sramc_sysdev_class; + +struct txx9_sramc_sysdev { + struct sys_device dev; + struct bin_attribute bindata_attr; + void __iomem *base; +}; + +static ssize_t txx9_sram_read(struct kobject *kobj, + struct bin_attribute *bin_attr, + char *buf, loff_t pos, size_t size) +{ + struct txx9_sramc_sysdev *dev = bin_attr->private; + size_t ramsize = bin_attr->size; + + if (pos >= ramsize) + return 0; + if (pos + size > ramsize) + size = ramsize - pos; + memcpy_fromio(buf, dev->base + pos, size); + return size; +} + +static ssize_t txx9_sram_write(struct kobject *kobj, + struct bin_attribute *bin_attr, + char *buf, loff_t pos, size_t size) +{ + struct txx9_sramc_sysdev *dev = bin_attr->private; + size_t ramsize = bin_attr->size; + + if (pos >= ramsize) + return 0; + if (pos + size > ramsize) + size = ramsize - pos; + memcpy_toio(dev->base + pos, buf, size); + return size; +} + +void __init txx9_sramc_init(struct resource *r) +{ + struct txx9_sramc_sysdev *dev; + size_t size; + int err; + + if (!txx9_sramc_sysdev_class.name) { + txx9_sramc_sysdev_class.name = "txx9_sram"; + err = sysdev_class_register(&txx9_sramc_sysdev_class); + if (err) { + txx9_sramc_sysdev_class.name = NULL; + return; + } + } + dev = kzalloc(sizeof(*dev), GFP_KERNEL); + if (!dev) + return; + size = resource_size(r); + dev->base = ioremap(r->start, size); + if (!dev->base) + goto exit; + dev->dev.cls = &txx9_sramc_sysdev_class; + dev->bindata_attr.attr.name = "bindata"; + dev->bindata_attr.attr.mode = S_IRUSR | S_IWUSR; + dev->bindata_attr.read = txx9_sram_read; + dev->bindata_attr.write = txx9_sram_write; + dev->bindata_attr.size = size; + dev->bindata_attr.private = dev; + err = sysdev_register(&dev->dev); + if (err) + goto exit; + err = sysfs_create_bin_file(&dev->dev.kobj, &dev->bindata_attr); + if (err) { + sysdev_unregister(&dev->dev); + goto exit; + } + return; +exit: + if (dev) { + if (dev->base) + iounmap(dev->base); + kfree(dev); + } +} diff --git a/arch/mips/txx9/generic/setup_tx4938.c b/arch/mips/txx9/generic/setup_tx4938.c index 4dfdb52e866..eb208011023 100644 --- a/arch/mips/txx9/generic/setup_tx4938.c +++ b/arch/mips/txx9/generic/setup_tx4938.c @@ -425,6 +425,12 @@ void __init tx4938_aclc_init(void) 1, 0, 1); } +void __init tx4938_sramc_init(void) +{ + if (tx4938_sram_resource.start) + txx9_sramc_init(&tx4938_sram_resource); +} + static void __init tx4938_stop_unused_modules(void) { __u64 pcfg, rst = 0, ckd = 0; diff --git a/arch/mips/txx9/generic/setup_tx4939.c b/arch/mips/txx9/generic/setup_tx4939.c index 71396863f54..df13a891fb4 100644 --- a/arch/mips/txx9/generic/setup_tx4939.c +++ b/arch/mips/txx9/generic/setup_tx4939.c @@ -494,6 +494,12 @@ void __init tx4939_aclc_init(void) TXX9_IRQ_BASE + TX4939_IR_ACLC, 1, 0, 1); } +void __init tx4939_sramc_init(void) +{ + if (tx4939_sram_resource.start) + txx9_sramc_init(&tx4939_sram_resource); +} + static void __init tx4939_stop_unused_modules(void) { __u64 pcfg, rst = 0, ckd = 0; |