aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAndres Salomon <dilinger@queued.net>2010-11-26 05:52:35 -0500
committerSamuel Ortiz <sameo@linux.intel.com>2011-01-14 06:37:38 -0500
commitf71e1afdd588ec60fd799b1e5a6f0b2e6cf9605e (patch)
treea165b8f2fda7227eaa1c9a33af5885ab9574cb6a
parente1b88eb0e08335d2f6c00b35b67b4ffc78fd46d6 (diff)
mfd: Add cs5535-mfd driver for AMD Geode's CS5535/CS5536 support
Add an MFD driver to handle the ISA device on CS5535 and CS5536 southbridges. This ISA bridge is actually multiple devices: GPIOs, MFGPTs, etc. Signed-off-by: Andres Salomon <dilinger@queued.net> Signed-off-by: Samuel Ortiz <sameo@linux.intel.com>
-rw-r--r--drivers/mfd/Kconfig8
-rw-r--r--drivers/mfd/Makefile1
-rw-r--r--drivers/mfd/cs5535-mfd.c151
3 files changed, 160 insertions, 0 deletions
diff --git a/drivers/mfd/Kconfig b/drivers/mfd/Kconfig
index da9d2971102e..b5e3e09f5637 100644
--- a/drivers/mfd/Kconfig
+++ b/drivers/mfd/Kconfig
@@ -537,6 +537,14 @@ config AB3550_CORE
537 LEDs, vibrator, system power and temperature, power management 537 LEDs, vibrator, system power and temperature, power management
538 and ALSA sound. 538 and ALSA sound.
539 539
540config MFD_CS5535
541 tristate "Support for CS5535 and CS5536 southbridge core functions"
542 select MFD_CORE
543 depends on PCI
544 ---help---
545 This is the core driver for CS5535/CS5536 MFD functions. This is
546 necessary for using the board's GPIO and MFGPT functionality.
547
540config MFD_TIMBERDALE 548config MFD_TIMBERDALE
541 tristate "Support for the Timberdale FPGA" 549 tristate "Support for the Timberdale FPGA"
542 select MFD_CORE 550 select MFD_CORE
diff --git a/drivers/mfd/Makefile b/drivers/mfd/Makefile
index 848e7eac75aa..5f35de9386e3 100644
--- a/drivers/mfd/Makefile
+++ b/drivers/mfd/Makefile
@@ -82,3 +82,4 @@ obj-$(CONFIG_MFD_JZ4740_ADC) += jz4740-adc.o
82obj-$(CONFIG_MFD_TPS6586X) += tps6586x.o 82obj-$(CONFIG_MFD_TPS6586X) += tps6586x.o
83obj-$(CONFIG_MFD_VX855) += vx855.o 83obj-$(CONFIG_MFD_VX855) += vx855.o
84obj-$(CONFIG_MFD_WL1273_CORE) += wl1273-core.o 84obj-$(CONFIG_MFD_WL1273_CORE) += wl1273-core.o
85obj-$(CONFIG_MFD_CS5535) += cs5535-mfd.o
diff --git a/drivers/mfd/cs5535-mfd.c b/drivers/mfd/cs5535-mfd.c
new file mode 100644
index 000000000000..b141ca7c777c
--- /dev/null
+++ b/drivers/mfd/cs5535-mfd.c
@@ -0,0 +1,151 @@
1/*
2 * cs5535-mfd.c - core MFD driver for CS5535/CS5536 southbridges
3 *
4 * The CS5535 and CS5536 has an ISA bridge on the PCI bus that is
5 * used for accessing GPIOs, MFGPTs, ACPI, etc. Each subdevice has
6 * an IO range that's specified in a single BAR. The BAR order is
7 * hardcoded in the CS553x specifications.
8 *
9 * Copyright (c) 2010 Andres Salomon <dilinger@queued.net>
10 *
11 * This program is free software; you can redistribute it and/or modify
12 * it under the terms of the GNU General Public License version 2 as
13 * published by the Free Software Foundation.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 */
24
25#include <linux/kernel.h>
26#include <linux/init.h>
27#include <linux/mfd/core.h>
28#include <linux/module.h>
29#include <linux/pci.h>
30
31#define DRV_NAME "cs5535-mfd"
32
33enum cs5535_mfd_bars {
34 SMB_BAR = 0,
35 GPIO_BAR = 1,
36 MFGPT_BAR = 2,
37 PMS_BAR = 4,
38 ACPI_BAR = 5,
39 NR_BARS,
40};
41
42static __devinitdata struct resource cs5535_mfd_resources[NR_BARS];
43
44static __devinitdata struct mfd_cell cs5535_mfd_cells[] = {
45 {
46 .id = SMB_BAR,
47 .name = "cs5535-smb",
48 .num_resources = 1,
49 .resources = &cs5535_mfd_resources[SMB_BAR],
50 },
51 {
52 .id = GPIO_BAR,
53 .name = "cs5535-gpio",
54 .num_resources = 1,
55 .resources = &cs5535_mfd_resources[GPIO_BAR],
56 },
57 {
58 .id = MFGPT_BAR,
59 .name = "cs5535-mfgpt",
60 .num_resources = 1,
61 .resources = &cs5535_mfd_resources[MFGPT_BAR],
62 },
63 {
64 .id = PMS_BAR,
65 .name = "cs5535-pms",
66 .num_resources = 1,
67 .resources = &cs5535_mfd_resources[PMS_BAR],
68 },
69 {
70 .id = ACPI_BAR,
71 .name = "cs5535-acpi",
72 .num_resources = 1,
73 .resources = &cs5535_mfd_resources[ACPI_BAR],
74 },
75};
76
77static int __devinit cs5535_mfd_probe(struct pci_dev *pdev,
78 const struct pci_device_id *id)
79{
80 int err, i;
81
82 err = pci_enable_device(pdev);
83 if (err)
84 return err;
85
86 /* fill in IO range for each cell; subdrivers handle the region */
87 for (i = 0; i < ARRAY_SIZE(cs5535_mfd_cells); i++) {
88 int bar = cs5535_mfd_cells[i].id;
89 struct resource *r = &cs5535_mfd_resources[bar];
90
91 r->flags = IORESOURCE_IO;
92 r->start = pci_resource_start(pdev, bar);
93 r->end = pci_resource_end(pdev, bar);
94
95 /* id is used for temporarily storing BAR; unset it now */
96 cs5535_mfd_cells[i].id = 0;
97 }
98
99 err = mfd_add_devices(&pdev->dev, -1, cs5535_mfd_cells,
100 ARRAY_SIZE(cs5535_mfd_cells), NULL, 0);
101 if (err) {
102 dev_err(&pdev->dev, "MFD add devices failed: %d\n", err);
103 goto err_disable;
104 }
105
106 dev_info(&pdev->dev, "%d devices registered.\n",
107 ARRAY_SIZE(cs5535_mfd_cells));
108
109 return 0;
110
111err_disable:
112 pci_disable_device(pdev);
113 return err;
114}
115
116static void __devexit cs5535_mfd_remove(struct pci_dev *pdev)
117{
118 mfd_remove_devices(&pdev->dev);
119 pci_disable_device(pdev);
120}
121
122static struct pci_device_id cs5535_mfd_pci_tbl[] = {
123 { PCI_DEVICE(PCI_VENDOR_ID_NS, PCI_DEVICE_ID_NS_CS5535_ISA) },
124 { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_CS5536_ISA) },
125 { 0, }
126};
127MODULE_DEVICE_TABLE(pci, cs5535_mfd_pci_tbl);
128
129static struct pci_driver cs5535_mfd_drv = {
130 .name = DRV_NAME,
131 .id_table = cs5535_mfd_pci_tbl,
132 .probe = cs5535_mfd_probe,
133 .remove = __devexit_p(cs5535_mfd_remove),
134};
135
136static int __init cs5535_mfd_init(void)
137{
138 return pci_register_driver(&cs5535_mfd_drv);
139}
140
141static void __exit cs5535_mfd_exit(void)
142{
143 pci_unregister_driver(&cs5535_mfd_drv);
144}
145
146module_init(cs5535_mfd_init);
147module_exit(cs5535_mfd_exit);
148
149MODULE_AUTHOR("Andres Salomon <dilinger@queued.net>");
150MODULE_DESCRIPTION("MFD driver for CS5535/CS5536 southbridge's ISA PCI device");
151MODULE_LICENSE("GPL");