diff options
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/gpio/Kconfig | 1 | ||||
-rw-r--r-- | drivers/gpio/gpio-ml-ioh.c | 8 | ||||
-rw-r--r-- | drivers/gpio/gpio-pch.c | 4 | ||||
-rw-r--r-- | drivers/gpio/gpio-tps65910.c | 2 | ||||
-rw-r--r-- | drivers/mfd/mcp-core.c | 61 | ||||
-rw-r--r-- | drivers/mfd/mcp-sa11x0.c | 169 | ||||
-rw-r--r-- | drivers/mfd/ucb1x00-core.c | 67 | ||||
-rw-r--r-- | drivers/mfd/ucb1x00-ts.c | 34 |
8 files changed, 105 insertions, 241 deletions
diff --git a/drivers/gpio/Kconfig b/drivers/gpio/Kconfig index 37c4bd1cacd5..d0c41188d4e5 100644 --- a/drivers/gpio/Kconfig +++ b/drivers/gpio/Kconfig | |||
@@ -87,6 +87,7 @@ config GPIO_GENERIC_PLATFORM | |||
87 | 87 | ||
88 | config GPIO_IT8761E | 88 | config GPIO_IT8761E |
89 | tristate "IT8761E GPIO support" | 89 | tristate "IT8761E GPIO support" |
90 | depends on X86 # unconditional access to IO space. | ||
90 | help | 91 | help |
91 | Say yes here to support GPIO functionality of IT8761E super I/O chip. | 92 | Say yes here to support GPIO functionality of IT8761E super I/O chip. |
92 | 93 | ||
diff --git a/drivers/gpio/gpio-ml-ioh.c b/drivers/gpio/gpio-ml-ioh.c index 461958fc2264..03d6dd5dcb77 100644 --- a/drivers/gpio/gpio-ml-ioh.c +++ b/drivers/gpio/gpio-ml-ioh.c | |||
@@ -248,7 +248,7 @@ static void ioh_gpio_setup(struct ioh_gpio *chip, int num_port) | |||
248 | static int ioh_irq_type(struct irq_data *d, unsigned int type) | 248 | static int ioh_irq_type(struct irq_data *d, unsigned int type) |
249 | { | 249 | { |
250 | u32 im; | 250 | u32 im; |
251 | u32 *im_reg; | 251 | void __iomem *im_reg; |
252 | u32 ien; | 252 | u32 ien; |
253 | u32 im_pos; | 253 | u32 im_pos; |
254 | int ch; | 254 | int ch; |
@@ -412,7 +412,7 @@ static int __devinit ioh_gpio_probe(struct pci_dev *pdev, | |||
412 | int i, j; | 412 | int i, j; |
413 | struct ioh_gpio *chip; | 413 | struct ioh_gpio *chip; |
414 | void __iomem *base; | 414 | void __iomem *base; |
415 | void __iomem *chip_save; | 415 | void *chip_save; |
416 | int irq_base; | 416 | int irq_base; |
417 | 417 | ||
418 | ret = pci_enable_device(pdev); | 418 | ret = pci_enable_device(pdev); |
@@ -428,7 +428,7 @@ static int __devinit ioh_gpio_probe(struct pci_dev *pdev, | |||
428 | } | 428 | } |
429 | 429 | ||
430 | base = pci_iomap(pdev, 1, 0); | 430 | base = pci_iomap(pdev, 1, 0); |
431 | if (base == 0) { | 431 | if (!base) { |
432 | dev_err(&pdev->dev, "%s : pci_iomap failed", __func__); | 432 | dev_err(&pdev->dev, "%s : pci_iomap failed", __func__); |
433 | ret = -ENOMEM; | 433 | ret = -ENOMEM; |
434 | goto err_iomap; | 434 | goto err_iomap; |
@@ -521,7 +521,7 @@ static void __devexit ioh_gpio_remove(struct pci_dev *pdev) | |||
521 | int err; | 521 | int err; |
522 | int i; | 522 | int i; |
523 | struct ioh_gpio *chip = pci_get_drvdata(pdev); | 523 | struct ioh_gpio *chip = pci_get_drvdata(pdev); |
524 | void __iomem *chip_save; | 524 | void *chip_save; |
525 | 525 | ||
526 | chip_save = chip; | 526 | chip_save = chip; |
527 | 527 | ||
diff --git a/drivers/gpio/gpio-pch.c b/drivers/gpio/gpio-pch.c index f0603297f829..68fa55e86eb1 100644 --- a/drivers/gpio/gpio-pch.c +++ b/drivers/gpio/gpio-pch.c | |||
@@ -231,7 +231,7 @@ static void pch_gpio_setup(struct pch_gpio *chip) | |||
231 | static int pch_irq_type(struct irq_data *d, unsigned int type) | 231 | static int pch_irq_type(struct irq_data *d, unsigned int type) |
232 | { | 232 | { |
233 | u32 im; | 233 | u32 im; |
234 | u32 *im_reg; | 234 | u32 __iomem *im_reg; |
235 | u32 ien; | 235 | u32 ien; |
236 | u32 im_pos; | 236 | u32 im_pos; |
237 | int ch; | 237 | int ch; |
@@ -376,7 +376,7 @@ static int __devinit pch_gpio_probe(struct pci_dev *pdev, | |||
376 | } | 376 | } |
377 | 377 | ||
378 | chip->base = pci_iomap(pdev, 1, 0); | 378 | chip->base = pci_iomap(pdev, 1, 0); |
379 | if (chip->base == 0) { | 379 | if (!chip->base) { |
380 | dev_err(&pdev->dev, "%s : pci_iomap FAILED", __func__); | 380 | dev_err(&pdev->dev, "%s : pci_iomap FAILED", __func__); |
381 | ret = -ENOMEM; | 381 | ret = -ENOMEM; |
382 | goto err_iomap; | 382 | goto err_iomap; |
diff --git a/drivers/gpio/gpio-tps65910.c b/drivers/gpio/gpio-tps65910.c index b9c1c297669e..91f45b965d1e 100644 --- a/drivers/gpio/gpio-tps65910.c +++ b/drivers/gpio/gpio-tps65910.c | |||
@@ -52,7 +52,7 @@ static int tps65910_gpio_output(struct gpio_chip *gc, unsigned offset, | |||
52 | struct tps65910 *tps65910 = container_of(gc, struct tps65910, gpio); | 52 | struct tps65910 *tps65910 = container_of(gc, struct tps65910, gpio); |
53 | 53 | ||
54 | /* Set the initial value */ | 54 | /* Set the initial value */ |
55 | tps65910_gpio_set(gc, 0, value); | 55 | tps65910_gpio_set(gc, offset, value); |
56 | 56 | ||
57 | return tps65910_set_bits(tps65910, TPS65910_GPIO0 + offset, | 57 | return tps65910_set_bits(tps65910, TPS65910_GPIO0 + offset, |
58 | GPIO_CFG_MASK); | 58 | GPIO_CFG_MASK); |
diff --git a/drivers/mfd/mcp-core.c b/drivers/mfd/mcp-core.c index 63be60bc3455..86cc3f7841cd 100644 --- a/drivers/mfd/mcp-core.c +++ b/drivers/mfd/mcp-core.c | |||
@@ -26,35 +26,9 @@ | |||
26 | #define to_mcp(d) container_of(d, struct mcp, attached_device) | 26 | #define to_mcp(d) container_of(d, struct mcp, attached_device) |
27 | #define to_mcp_driver(d) container_of(d, struct mcp_driver, drv) | 27 | #define to_mcp_driver(d) container_of(d, struct mcp_driver, drv) |
28 | 28 | ||
29 | static const struct mcp_device_id *mcp_match_id(const struct mcp_device_id *id, | ||
30 | const char *codec) | ||
31 | { | ||
32 | while (id->name[0]) { | ||
33 | if (strcmp(codec, id->name) == 0) | ||
34 | return id; | ||
35 | id++; | ||
36 | } | ||
37 | return NULL; | ||
38 | } | ||
39 | |||
40 | const struct mcp_device_id *mcp_get_device_id(const struct mcp *mcp) | ||
41 | { | ||
42 | const struct mcp_driver *driver = | ||
43 | to_mcp_driver(mcp->attached_device.driver); | ||
44 | |||
45 | return mcp_match_id(driver->id_table, mcp->codec); | ||
46 | } | ||
47 | EXPORT_SYMBOL(mcp_get_device_id); | ||
48 | |||
49 | static int mcp_bus_match(struct device *dev, struct device_driver *drv) | 29 | static int mcp_bus_match(struct device *dev, struct device_driver *drv) |
50 | { | 30 | { |
51 | const struct mcp *mcp = to_mcp(dev); | 31 | return 1; |
52 | const struct mcp_driver *driver = to_mcp_driver(drv); | ||
53 | |||
54 | if (driver->id_table) | ||
55 | return !!mcp_match_id(driver->id_table, mcp->codec); | ||
56 | |||
57 | return 0; | ||
58 | } | 32 | } |
59 | 33 | ||
60 | static int mcp_bus_probe(struct device *dev) | 34 | static int mcp_bus_probe(struct device *dev) |
@@ -100,18 +74,9 @@ static int mcp_bus_resume(struct device *dev) | |||
100 | return ret; | 74 | return ret; |
101 | } | 75 | } |
102 | 76 | ||
103 | static int mcp_bus_uevent(struct device *dev, struct kobj_uevent_env *env) | ||
104 | { | ||
105 | struct mcp *mcp = to_mcp(dev); | ||
106 | |||
107 | add_uevent_var(env, "MODALIAS=%s%s", MCP_MODULE_PREFIX, mcp->codec); | ||
108 | return 0; | ||
109 | } | ||
110 | |||
111 | static struct bus_type mcp_bus_type = { | 77 | static struct bus_type mcp_bus_type = { |
112 | .name = "mcp", | 78 | .name = "mcp", |
113 | .match = mcp_bus_match, | 79 | .match = mcp_bus_match, |
114 | .uevent = mcp_bus_uevent, | ||
115 | .probe = mcp_bus_probe, | 80 | .probe = mcp_bus_probe, |
116 | .remove = mcp_bus_remove, | 81 | .remove = mcp_bus_remove, |
117 | .suspend = mcp_bus_suspend, | 82 | .suspend = mcp_bus_suspend, |
@@ -128,9 +93,11 @@ static struct bus_type mcp_bus_type = { | |||
128 | */ | 93 | */ |
129 | void mcp_set_telecom_divisor(struct mcp *mcp, unsigned int div) | 94 | void mcp_set_telecom_divisor(struct mcp *mcp, unsigned int div) |
130 | { | 95 | { |
131 | spin_lock_irq(&mcp->lock); | 96 | unsigned long flags; |
97 | |||
98 | spin_lock_irqsave(&mcp->lock, flags); | ||
132 | mcp->ops->set_telecom_divisor(mcp, div); | 99 | mcp->ops->set_telecom_divisor(mcp, div); |
133 | spin_unlock_irq(&mcp->lock); | 100 | spin_unlock_irqrestore(&mcp->lock, flags); |
134 | } | 101 | } |
135 | EXPORT_SYMBOL(mcp_set_telecom_divisor); | 102 | EXPORT_SYMBOL(mcp_set_telecom_divisor); |
136 | 103 | ||
@@ -143,9 +110,11 @@ EXPORT_SYMBOL(mcp_set_telecom_divisor); | |||
143 | */ | 110 | */ |
144 | void mcp_set_audio_divisor(struct mcp *mcp, unsigned int div) | 111 | void mcp_set_audio_divisor(struct mcp *mcp, unsigned int div) |
145 | { | 112 | { |
146 | spin_lock_irq(&mcp->lock); | 113 | unsigned long flags; |
114 | |||
115 | spin_lock_irqsave(&mcp->lock, flags); | ||
147 | mcp->ops->set_audio_divisor(mcp, div); | 116 | mcp->ops->set_audio_divisor(mcp, div); |
148 | spin_unlock_irq(&mcp->lock); | 117 | spin_unlock_irqrestore(&mcp->lock, flags); |
149 | } | 118 | } |
150 | EXPORT_SYMBOL(mcp_set_audio_divisor); | 119 | EXPORT_SYMBOL(mcp_set_audio_divisor); |
151 | 120 | ||
@@ -198,10 +167,11 @@ EXPORT_SYMBOL(mcp_reg_read); | |||
198 | */ | 167 | */ |
199 | void mcp_enable(struct mcp *mcp) | 168 | void mcp_enable(struct mcp *mcp) |
200 | { | 169 | { |
201 | spin_lock_irq(&mcp->lock); | 170 | unsigned long flags; |
171 | spin_lock_irqsave(&mcp->lock, flags); | ||
202 | if (mcp->use_count++ == 0) | 172 | if (mcp->use_count++ == 0) |
203 | mcp->ops->enable(mcp); | 173 | mcp->ops->enable(mcp); |
204 | spin_unlock_irq(&mcp->lock); | 174 | spin_unlock_irqrestore(&mcp->lock, flags); |
205 | } | 175 | } |
206 | EXPORT_SYMBOL(mcp_enable); | 176 | EXPORT_SYMBOL(mcp_enable); |
207 | 177 | ||
@@ -247,14 +217,9 @@ struct mcp *mcp_host_alloc(struct device *parent, size_t size) | |||
247 | } | 217 | } |
248 | EXPORT_SYMBOL(mcp_host_alloc); | 218 | EXPORT_SYMBOL(mcp_host_alloc); |
249 | 219 | ||
250 | int mcp_host_register(struct mcp *mcp, void *pdata) | 220 | int mcp_host_register(struct mcp *mcp) |
251 | { | 221 | { |
252 | if (!mcp->codec) | ||
253 | return -EINVAL; | ||
254 | |||
255 | mcp->attached_device.platform_data = pdata; | ||
256 | dev_set_name(&mcp->attached_device, "mcp0"); | 222 | dev_set_name(&mcp->attached_device, "mcp0"); |
257 | request_module("%s%s", MCP_MODULE_PREFIX, mcp->codec); | ||
258 | return device_register(&mcp->attached_device); | 223 | return device_register(&mcp->attached_device); |
259 | } | 224 | } |
260 | EXPORT_SYMBOL(mcp_host_register); | 225 | EXPORT_SYMBOL(mcp_host_register); |
diff --git a/drivers/mfd/mcp-sa11x0.c b/drivers/mfd/mcp-sa11x0.c index 9adc2eb69492..02c53a0766c4 100644 --- a/drivers/mfd/mcp-sa11x0.c +++ b/drivers/mfd/mcp-sa11x0.c | |||
@@ -19,7 +19,6 @@ | |||
19 | #include <linux/spinlock.h> | 19 | #include <linux/spinlock.h> |
20 | #include <linux/platform_device.h> | 20 | #include <linux/platform_device.h> |
21 | #include <linux/mfd/mcp.h> | 21 | #include <linux/mfd/mcp.h> |
22 | #include <linux/io.h> | ||
23 | 22 | ||
24 | #include <mach/dma.h> | 23 | #include <mach/dma.h> |
25 | #include <mach/hardware.h> | 24 | #include <mach/hardware.h> |
@@ -27,19 +26,12 @@ | |||
27 | #include <asm/system.h> | 26 | #include <asm/system.h> |
28 | #include <mach/mcp.h> | 27 | #include <mach/mcp.h> |
29 | 28 | ||
30 | /* Register offsets */ | 29 | #include <mach/assabet.h> |
31 | #define MCCR0 0x00 | 30 | |
32 | #define MCDR0 0x08 | ||
33 | #define MCDR1 0x0C | ||
34 | #define MCDR2 0x10 | ||
35 | #define MCSR 0x18 | ||
36 | #define MCCR1 0x00 | ||
37 | 31 | ||
38 | struct mcp_sa11x0 { | 32 | struct mcp_sa11x0 { |
39 | u32 mccr0; | 33 | u32 mccr0; |
40 | u32 mccr1; | 34 | u32 mccr1; |
41 | unsigned char *mccr0_base; | ||
42 | unsigned char *mccr1_base; | ||
43 | }; | 35 | }; |
44 | 36 | ||
45 | #define priv(mcp) ((struct mcp_sa11x0 *)mcp_priv(mcp)) | 37 | #define priv(mcp) ((struct mcp_sa11x0 *)mcp_priv(mcp)) |
@@ -47,25 +39,25 @@ struct mcp_sa11x0 { | |||
47 | static void | 39 | static void |
48 | mcp_sa11x0_set_telecom_divisor(struct mcp *mcp, unsigned int divisor) | 40 | mcp_sa11x0_set_telecom_divisor(struct mcp *mcp, unsigned int divisor) |
49 | { | 41 | { |
50 | struct mcp_sa11x0 *priv = priv(mcp); | 42 | unsigned int mccr0; |
51 | 43 | ||
52 | divisor /= 32; | 44 | divisor /= 32; |
53 | 45 | ||
54 | priv->mccr0 &= ~0x00007f00; | 46 | mccr0 = Ser4MCCR0 & ~0x00007f00; |
55 | priv->mccr0 |= divisor << 8; | 47 | mccr0 |= divisor << 8; |
56 | __raw_writel(priv->mccr0, priv->mccr0_base + MCCR0); | 48 | Ser4MCCR0 = mccr0; |
57 | } | 49 | } |
58 | 50 | ||
59 | static void | 51 | static void |
60 | mcp_sa11x0_set_audio_divisor(struct mcp *mcp, unsigned int divisor) | 52 | mcp_sa11x0_set_audio_divisor(struct mcp *mcp, unsigned int divisor) |
61 | { | 53 | { |
62 | struct mcp_sa11x0 *priv = priv(mcp); | 54 | unsigned int mccr0; |
63 | 55 | ||
64 | divisor /= 32; | 56 | divisor /= 32; |
65 | 57 | ||
66 | priv->mccr0 &= ~0x0000007f; | 58 | mccr0 = Ser4MCCR0 & ~0x0000007f; |
67 | priv->mccr0 |= divisor; | 59 | mccr0 |= divisor; |
68 | __raw_writel(priv->mccr0, priv->mccr0_base + MCCR0); | 60 | Ser4MCCR0 = mccr0; |
69 | } | 61 | } |
70 | 62 | ||
71 | /* | 63 | /* |
@@ -79,16 +71,12 @@ mcp_sa11x0_write(struct mcp *mcp, unsigned int reg, unsigned int val) | |||
79 | { | 71 | { |
80 | int ret = -ETIME; | 72 | int ret = -ETIME; |
81 | int i; | 73 | int i; |
82 | u32 mcpreg; | ||
83 | struct mcp_sa11x0 *priv = priv(mcp); | ||
84 | 74 | ||
85 | mcpreg = reg << 17 | MCDR2_Wr | (val & 0xffff); | 75 | Ser4MCDR2 = reg << 17 | MCDR2_Wr | (val & 0xffff); |
86 | __raw_writel(mcpreg, priv->mccr0_base + MCDR2); | ||
87 | 76 | ||
88 | for (i = 0; i < 2; i++) { | 77 | for (i = 0; i < 2; i++) { |
89 | udelay(mcp->rw_timeout); | 78 | udelay(mcp->rw_timeout); |
90 | mcpreg = __raw_readl(priv->mccr0_base + MCSR); | 79 | if (Ser4MCSR & MCSR_CWC) { |
91 | if (mcpreg & MCSR_CWC) { | ||
92 | ret = 0; | 80 | ret = 0; |
93 | break; | 81 | break; |
94 | } | 82 | } |
@@ -109,18 +97,13 @@ mcp_sa11x0_read(struct mcp *mcp, unsigned int reg) | |||
109 | { | 97 | { |
110 | int ret = -ETIME; | 98 | int ret = -ETIME; |
111 | int i; | 99 | int i; |
112 | u32 mcpreg; | ||
113 | struct mcp_sa11x0 *priv = priv(mcp); | ||
114 | 100 | ||
115 | mcpreg = reg << 17 | MCDR2_Rd; | 101 | Ser4MCDR2 = reg << 17 | MCDR2_Rd; |
116 | __raw_writel(mcpreg, priv->mccr0_base + MCDR2); | ||
117 | 102 | ||
118 | for (i = 0; i < 2; i++) { | 103 | for (i = 0; i < 2; i++) { |
119 | udelay(mcp->rw_timeout); | 104 | udelay(mcp->rw_timeout); |
120 | mcpreg = __raw_readl(priv->mccr0_base + MCSR); | 105 | if (Ser4MCSR & MCSR_CRC) { |
121 | if (mcpreg & MCSR_CRC) { | 106 | ret = Ser4MCDR2 & 0xffff; |
122 | ret = __raw_readl(priv->mccr0_base + MCDR2) | ||
123 | & 0xffff; | ||
124 | break; | 107 | break; |
125 | } | 108 | } |
126 | } | 109 | } |
@@ -133,19 +116,13 @@ mcp_sa11x0_read(struct mcp *mcp, unsigned int reg) | |||
133 | 116 | ||
134 | static void mcp_sa11x0_enable(struct mcp *mcp) | 117 | static void mcp_sa11x0_enable(struct mcp *mcp) |
135 | { | 118 | { |
136 | struct mcp_sa11x0 *priv = priv(mcp); | 119 | Ser4MCSR = -1; |
137 | 120 | Ser4MCCR0 |= MCCR0_MCE; | |
138 | __raw_writel(-1, priv->mccr0_base + MCSR); | ||
139 | priv->mccr0 |= MCCR0_MCE; | ||
140 | __raw_writel(priv->mccr0, priv->mccr0_base + MCCR0); | ||
141 | } | 121 | } |
142 | 122 | ||
143 | static void mcp_sa11x0_disable(struct mcp *mcp) | 123 | static void mcp_sa11x0_disable(struct mcp *mcp) |
144 | { | 124 | { |
145 | struct mcp_sa11x0 *priv = priv(mcp); | 125 | Ser4MCCR0 &= ~MCCR0_MCE; |
146 | |||
147 | priv->mccr0 &= ~MCCR0_MCE; | ||
148 | __raw_writel(priv->mccr0, priv->mccr0_base + MCCR0); | ||
149 | } | 126 | } |
150 | 127 | ||
151 | /* | 128 | /* |
@@ -165,69 +142,50 @@ static int mcp_sa11x0_probe(struct platform_device *pdev) | |||
165 | struct mcp_plat_data *data = pdev->dev.platform_data; | 142 | struct mcp_plat_data *data = pdev->dev.platform_data; |
166 | struct mcp *mcp; | 143 | struct mcp *mcp; |
167 | int ret; | 144 | int ret; |
168 | struct mcp_sa11x0 *priv; | ||
169 | struct resource *res_mem0, *res_mem1; | ||
170 | u32 size0, size1; | ||
171 | 145 | ||
172 | if (!data) | 146 | if (!data) |
173 | return -ENODEV; | 147 | return -ENODEV; |
174 | 148 | ||
175 | if (!data->codec) | 149 | if (!request_mem_region(0x80060000, 0x60, "sa11x0-mcp")) |
176 | return -ENODEV; | ||
177 | |||
178 | res_mem0 = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
179 | if (!res_mem0) | ||
180 | return -ENODEV; | ||
181 | size0 = res_mem0->end - res_mem0->start + 1; | ||
182 | |||
183 | res_mem1 = platform_get_resource(pdev, IORESOURCE_MEM, 1); | ||
184 | if (!res_mem1) | ||
185 | return -ENODEV; | ||
186 | size1 = res_mem1->end - res_mem1->start + 1; | ||
187 | |||
188 | if (!request_mem_region(res_mem0->start, size0, "sa11x0-mcp")) | ||
189 | return -EBUSY; | 150 | return -EBUSY; |
190 | 151 | ||
191 | if (!request_mem_region(res_mem1->start, size1, "sa11x0-mcp")) { | ||
192 | ret = -EBUSY; | ||
193 | goto release; | ||
194 | } | ||
195 | |||
196 | mcp = mcp_host_alloc(&pdev->dev, sizeof(struct mcp_sa11x0)); | 152 | mcp = mcp_host_alloc(&pdev->dev, sizeof(struct mcp_sa11x0)); |
197 | if (!mcp) { | 153 | if (!mcp) { |
198 | ret = -ENOMEM; | 154 | ret = -ENOMEM; |
199 | goto release2; | 155 | goto release; |
200 | } | 156 | } |
201 | 157 | ||
202 | priv = priv(mcp); | ||
203 | |||
204 | mcp->owner = THIS_MODULE; | 158 | mcp->owner = THIS_MODULE; |
205 | mcp->ops = &mcp_sa11x0; | 159 | mcp->ops = &mcp_sa11x0; |
206 | mcp->sclk_rate = data->sclk_rate; | 160 | mcp->sclk_rate = data->sclk_rate; |
207 | mcp->dma_audio_rd = DDAR_DevAdd(res_mem0->start + MCDR0) | 161 | mcp->dma_audio_rd = DMA_Ser4MCP0Rd; |
208 | + DDAR_DevRd + DDAR_Brst4 + DDAR_8BitDev; | 162 | mcp->dma_audio_wr = DMA_Ser4MCP0Wr; |
209 | mcp->dma_audio_wr = DDAR_DevAdd(res_mem0->start + MCDR0) | 163 | mcp->dma_telco_rd = DMA_Ser4MCP1Rd; |
210 | + DDAR_DevWr + DDAR_Brst4 + DDAR_8BitDev; | 164 | mcp->dma_telco_wr = DMA_Ser4MCP1Wr; |
211 | mcp->dma_telco_rd = DDAR_DevAdd(res_mem0->start + MCDR1) | 165 | mcp->gpio_base = data->gpio_base; |
212 | + DDAR_DevRd + DDAR_Brst4 + DDAR_8BitDev; | ||
213 | mcp->dma_telco_wr = DDAR_DevAdd(res_mem0->start + MCDR1) | ||
214 | + DDAR_DevWr + DDAR_Brst4 + DDAR_8BitDev; | ||
215 | mcp->codec = data->codec; | ||
216 | 166 | ||
217 | platform_set_drvdata(pdev, mcp); | 167 | platform_set_drvdata(pdev, mcp); |
218 | 168 | ||
169 | if (machine_is_assabet()) { | ||
170 | ASSABET_BCR_set(ASSABET_BCR_CODEC_RST); | ||
171 | } | ||
172 | |||
173 | /* | ||
174 | * Setup the PPC unit correctly. | ||
175 | */ | ||
176 | PPDR &= ~PPC_RXD4; | ||
177 | PPDR |= PPC_TXD4 | PPC_SCLK | PPC_SFRM; | ||
178 | PSDR |= PPC_RXD4; | ||
179 | PSDR &= ~(PPC_TXD4 | PPC_SCLK | PPC_SFRM); | ||
180 | PPSR &= ~(PPC_TXD4 | PPC_SCLK | PPC_SFRM); | ||
181 | |||
219 | /* | 182 | /* |
220 | * Initialise device. Note that we initially | 183 | * Initialise device. Note that we initially |
221 | * set the sampling rate to minimum. | 184 | * set the sampling rate to minimum. |
222 | */ | 185 | */ |
223 | priv->mccr0_base = ioremap(res_mem0->start, size0); | 186 | Ser4MCSR = -1; |
224 | priv->mccr1_base = ioremap(res_mem1->start, size1); | 187 | Ser4MCCR1 = data->mccr1; |
225 | 188 | Ser4MCCR0 = data->mccr0 | 0x7f7f; | |
226 | __raw_writel(-1, priv->mccr0_base + MCSR); | ||
227 | priv->mccr1 = data->mccr1; | ||
228 | priv->mccr0 = data->mccr0 | 0x7f7f; | ||
229 | __raw_writel(priv->mccr0, priv->mccr0_base + MCCR0); | ||
230 | __raw_writel(priv->mccr1, priv->mccr1_base + MCCR1); | ||
231 | 189 | ||
232 | /* | 190 | /* |
233 | * Calculate the read/write timeout (us) from the bit clock | 191 | * Calculate the read/write timeout (us) from the bit clock |
@@ -237,53 +195,36 @@ static int mcp_sa11x0_probe(struct platform_device *pdev) | |||
237 | mcp->rw_timeout = (64 * 3 * 1000000 + mcp->sclk_rate - 1) / | 195 | mcp->rw_timeout = (64 * 3 * 1000000 + mcp->sclk_rate - 1) / |
238 | mcp->sclk_rate; | 196 | mcp->sclk_rate; |
239 | 197 | ||
240 | ret = mcp_host_register(mcp, data->codec_pdata); | 198 | ret = mcp_host_register(mcp); |
241 | if (ret == 0) | 199 | if (ret == 0) |
242 | goto out; | 200 | goto out; |
243 | 201 | ||
244 | release2: | ||
245 | release_mem_region(res_mem1->start, size1); | ||
246 | release: | 202 | release: |
247 | release_mem_region(res_mem0->start, size0); | 203 | release_mem_region(0x80060000, 0x60); |
248 | platform_set_drvdata(pdev, NULL); | 204 | platform_set_drvdata(pdev, NULL); |
249 | 205 | ||
250 | out: | 206 | out: |
251 | return ret; | 207 | return ret; |
252 | } | 208 | } |
253 | 209 | ||
254 | static int mcp_sa11x0_remove(struct platform_device *pdev) | 210 | static int mcp_sa11x0_remove(struct platform_device *dev) |
255 | { | 211 | { |
256 | struct mcp *mcp = platform_get_drvdata(pdev); | 212 | struct mcp *mcp = platform_get_drvdata(dev); |
257 | struct mcp_sa11x0 *priv = priv(mcp); | ||
258 | struct resource *res_mem; | ||
259 | u32 size; | ||
260 | 213 | ||
261 | platform_set_drvdata(pdev, NULL); | 214 | platform_set_drvdata(dev, NULL); |
262 | mcp_host_unregister(mcp); | 215 | mcp_host_unregister(mcp); |
216 | release_mem_region(0x80060000, 0x60); | ||
263 | 217 | ||
264 | res_mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
265 | if (res_mem) { | ||
266 | size = res_mem->end - res_mem->start + 1; | ||
267 | release_mem_region(res_mem->start, size); | ||
268 | } | ||
269 | res_mem = platform_get_resource(pdev, IORESOURCE_MEM, 1); | ||
270 | if (res_mem) { | ||
271 | size = res_mem->end - res_mem->start + 1; | ||
272 | release_mem_region(res_mem->start, size); | ||
273 | } | ||
274 | iounmap(priv->mccr0_base); | ||
275 | iounmap(priv->mccr1_base); | ||
276 | return 0; | 218 | return 0; |
277 | } | 219 | } |
278 | 220 | ||
279 | static int mcp_sa11x0_suspend(struct platform_device *dev, pm_message_t state) | 221 | static int mcp_sa11x0_suspend(struct platform_device *dev, pm_message_t state) |
280 | { | 222 | { |
281 | struct mcp *mcp = platform_get_drvdata(dev); | 223 | struct mcp *mcp = platform_get_drvdata(dev); |
282 | struct mcp_sa11x0 *priv = priv(mcp); | ||
283 | u32 mccr0; | ||
284 | 224 | ||
285 | mccr0 = priv->mccr0 & ~MCCR0_MCE; | 225 | priv(mcp)->mccr0 = Ser4MCCR0; |
286 | __raw_writel(mccr0, priv->mccr0_base + MCCR0); | 226 | priv(mcp)->mccr1 = Ser4MCCR1; |
227 | Ser4MCCR0 &= ~MCCR0_MCE; | ||
287 | 228 | ||
288 | return 0; | 229 | return 0; |
289 | } | 230 | } |
@@ -291,10 +232,9 @@ static int mcp_sa11x0_suspend(struct platform_device *dev, pm_message_t state) | |||
291 | static int mcp_sa11x0_resume(struct platform_device *dev) | 232 | static int mcp_sa11x0_resume(struct platform_device *dev) |
292 | { | 233 | { |
293 | struct mcp *mcp = platform_get_drvdata(dev); | 234 | struct mcp *mcp = platform_get_drvdata(dev); |
294 | struct mcp_sa11x0 *priv = priv(mcp); | ||
295 | 235 | ||
296 | __raw_writel(priv->mccr0, priv->mccr0_base + MCCR0); | 236 | Ser4MCCR1 = priv(mcp)->mccr1; |
297 | __raw_writel(priv->mccr1, priv->mccr1_base + MCCR1); | 237 | Ser4MCCR0 = priv(mcp)->mccr0; |
298 | 238 | ||
299 | return 0; | 239 | return 0; |
300 | } | 240 | } |
@@ -311,7 +251,6 @@ static struct platform_driver mcp_sa11x0_driver = { | |||
311 | .resume = mcp_sa11x0_resume, | 251 | .resume = mcp_sa11x0_resume, |
312 | .driver = { | 252 | .driver = { |
313 | .name = "sa11x0-mcp", | 253 | .name = "sa11x0-mcp", |
314 | .owner = THIS_MODULE, | ||
315 | }, | 254 | }, |
316 | }; | 255 | }; |
317 | 256 | ||
diff --git a/drivers/mfd/ucb1x00-core.c b/drivers/mfd/ucb1x00-core.c index 91c4f25e0e55..febc90cdef7e 100644 --- a/drivers/mfd/ucb1x00-core.c +++ b/drivers/mfd/ucb1x00-core.c | |||
@@ -36,15 +36,6 @@ static DEFINE_MUTEX(ucb1x00_mutex); | |||
36 | static LIST_HEAD(ucb1x00_drivers); | 36 | static LIST_HEAD(ucb1x00_drivers); |
37 | static LIST_HEAD(ucb1x00_devices); | 37 | static LIST_HEAD(ucb1x00_devices); |
38 | 38 | ||
39 | static struct mcp_device_id ucb1x00_id[] = { | ||
40 | { "ucb1x00", 0 }, /* auto-detection */ | ||
41 | { "ucb1200", UCB_ID_1200 }, | ||
42 | { "ucb1300", UCB_ID_1300 }, | ||
43 | { "tc35143", UCB_ID_TC35143 }, | ||
44 | { } | ||
45 | }; | ||
46 | MODULE_DEVICE_TABLE(mcp, ucb1x00_id); | ||
47 | |||
48 | /** | 39 | /** |
49 | * ucb1x00_io_set_dir - set IO direction | 40 | * ucb1x00_io_set_dir - set IO direction |
50 | * @ucb: UCB1x00 structure describing chip | 41 | * @ucb: UCB1x00 structure describing chip |
@@ -157,16 +148,22 @@ static int ucb1x00_gpio_direction_output(struct gpio_chip *chip, unsigned offset | |||
157 | { | 148 | { |
158 | struct ucb1x00 *ucb = container_of(chip, struct ucb1x00, gpio); | 149 | struct ucb1x00 *ucb = container_of(chip, struct ucb1x00, gpio); |
159 | unsigned long flags; | 150 | unsigned long flags; |
151 | unsigned old, mask = 1 << offset; | ||
160 | 152 | ||
161 | spin_lock_irqsave(&ucb->io_lock, flags); | 153 | spin_lock_irqsave(&ucb->io_lock, flags); |
162 | ucb->io_dir |= (1 << offset); | 154 | old = ucb->io_out; |
163 | ucb1x00_reg_write(ucb, UCB_IO_DIR, ucb->io_dir); | ||
164 | |||
165 | if (value) | 155 | if (value) |
166 | ucb->io_out |= 1 << offset; | 156 | ucb->io_out |= mask; |
167 | else | 157 | else |
168 | ucb->io_out &= ~(1 << offset); | 158 | ucb->io_out &= ~mask; |
169 | ucb1x00_reg_write(ucb, UCB_IO_DATA, ucb->io_out); | 159 | |
160 | if (old != ucb->io_out) | ||
161 | ucb1x00_reg_write(ucb, UCB_IO_DATA, ucb->io_out); | ||
162 | |||
163 | if (!(ucb->io_dir & mask)) { | ||
164 | ucb->io_dir |= mask; | ||
165 | ucb1x00_reg_write(ucb, UCB_IO_DIR, ucb->io_dir); | ||
166 | } | ||
170 | spin_unlock_irqrestore(&ucb->io_lock, flags); | 167 | spin_unlock_irqrestore(&ucb->io_lock, flags); |
171 | 168 | ||
172 | return 0; | 169 | return 0; |
@@ -536,33 +533,17 @@ static struct class ucb1x00_class = { | |||
536 | 533 | ||
537 | static int ucb1x00_probe(struct mcp *mcp) | 534 | static int ucb1x00_probe(struct mcp *mcp) |
538 | { | 535 | { |
539 | const struct mcp_device_id *mid; | ||
540 | struct ucb1x00 *ucb; | 536 | struct ucb1x00 *ucb; |
541 | struct ucb1x00_driver *drv; | 537 | struct ucb1x00_driver *drv; |
542 | struct ucb1x00_plat_data *pdata; | ||
543 | unsigned int id; | 538 | unsigned int id; |
544 | int ret = -ENODEV; | 539 | int ret = -ENODEV; |
545 | int temp; | 540 | int temp; |
546 | 541 | ||
547 | mcp_enable(mcp); | 542 | mcp_enable(mcp); |
548 | id = mcp_reg_read(mcp, UCB_ID); | 543 | id = mcp_reg_read(mcp, UCB_ID); |
549 | mid = mcp_get_device_id(mcp); | ||
550 | 544 | ||
551 | if (mid && mid->driver_data) { | 545 | if (id != UCB_ID_1200 && id != UCB_ID_1300 && id != UCB_ID_TC35143) { |
552 | if (id != mid->driver_data) { | 546 | printk(KERN_WARNING "UCB1x00 ID not found: %04x\n", id); |
553 | printk(KERN_WARNING "%s wrong ID %04x found: %04x\n", | ||
554 | mid->name, (unsigned int) mid->driver_data, id); | ||
555 | goto err_disable; | ||
556 | } | ||
557 | } else { | ||
558 | mid = &ucb1x00_id[1]; | ||
559 | while (mid->driver_data) { | ||
560 | if (id == mid->driver_data) | ||
561 | break; | ||
562 | mid++; | ||
563 | } | ||
564 | printk(KERN_WARNING "%s ID not found: %04x\n", | ||
565 | ucb1x00_id[0].name, id); | ||
566 | goto err_disable; | 547 | goto err_disable; |
567 | } | 548 | } |
568 | 549 | ||
@@ -571,28 +552,28 @@ static int ucb1x00_probe(struct mcp *mcp) | |||
571 | if (!ucb) | 552 | if (!ucb) |
572 | goto err_disable; | 553 | goto err_disable; |
573 | 554 | ||
574 | pdata = mcp->attached_device.platform_data; | 555 | |
575 | ucb->dev.class = &ucb1x00_class; | 556 | ucb->dev.class = &ucb1x00_class; |
576 | ucb->dev.parent = &mcp->attached_device; | 557 | ucb->dev.parent = &mcp->attached_device; |
577 | dev_set_name(&ucb->dev, mid->name); | 558 | dev_set_name(&ucb->dev, "ucb1x00"); |
578 | 559 | ||
579 | spin_lock_init(&ucb->lock); | 560 | spin_lock_init(&ucb->lock); |
580 | spin_lock_init(&ucb->io_lock); | 561 | spin_lock_init(&ucb->io_lock); |
581 | sema_init(&ucb->adc_sem, 1); | 562 | sema_init(&ucb->adc_sem, 1); |
582 | 563 | ||
583 | ucb->id = mid; | 564 | ucb->id = id; |
584 | ucb->mcp = mcp; | 565 | ucb->mcp = mcp; |
585 | ucb->irq = ucb1x00_detect_irq(ucb); | 566 | ucb->irq = ucb1x00_detect_irq(ucb); |
586 | if (ucb->irq == NO_IRQ) { | 567 | if (ucb->irq == NO_IRQ) { |
587 | printk(KERN_ERR "%s: IRQ probe failed\n", mid->name); | 568 | printk(KERN_ERR "UCB1x00: IRQ probe failed\n"); |
588 | ret = -ENODEV; | 569 | ret = -ENODEV; |
589 | goto err_free; | 570 | goto err_free; |
590 | } | 571 | } |
591 | 572 | ||
592 | ucb->gpio.base = -1; | 573 | ucb->gpio.base = -1; |
593 | if (pdata && (pdata->gpio_base >= 0)) { | 574 | if (mcp->gpio_base != 0) { |
594 | ucb->gpio.label = dev_name(&ucb->dev); | 575 | ucb->gpio.label = dev_name(&ucb->dev); |
595 | ucb->gpio.base = pdata->gpio_base; | 576 | ucb->gpio.base = mcp->gpio_base; |
596 | ucb->gpio.ngpio = 10; | 577 | ucb->gpio.ngpio = 10; |
597 | ucb->gpio.set = ucb1x00_gpio_set; | 578 | ucb->gpio.set = ucb1x00_gpio_set; |
598 | ucb->gpio.get = ucb1x00_gpio_get; | 579 | ucb->gpio.get = ucb1x00_gpio_get; |
@@ -605,10 +586,10 @@ static int ucb1x00_probe(struct mcp *mcp) | |||
605 | dev_info(&ucb->dev, "gpio_base not set so no gpiolib support"); | 586 | dev_info(&ucb->dev, "gpio_base not set so no gpiolib support"); |
606 | 587 | ||
607 | ret = request_irq(ucb->irq, ucb1x00_irq, IRQF_TRIGGER_RISING, | 588 | ret = request_irq(ucb->irq, ucb1x00_irq, IRQF_TRIGGER_RISING, |
608 | mid->name, ucb); | 589 | "UCB1x00", ucb); |
609 | if (ret) { | 590 | if (ret) { |
610 | printk(KERN_ERR "%s: unable to grab irq%d: %d\n", | 591 | printk(KERN_ERR "ucb1x00: unable to grab irq%d: %d\n", |
611 | mid->name, ucb->irq, ret); | 592 | ucb->irq, ret); |
612 | goto err_gpio; | 593 | goto err_gpio; |
613 | } | 594 | } |
614 | 595 | ||
@@ -712,6 +693,7 @@ static int ucb1x00_resume(struct mcp *mcp) | |||
712 | struct ucb1x00 *ucb = mcp_get_drvdata(mcp); | 693 | struct ucb1x00 *ucb = mcp_get_drvdata(mcp); |
713 | struct ucb1x00_dev *dev; | 694 | struct ucb1x00_dev *dev; |
714 | 695 | ||
696 | ucb1x00_reg_write(ucb, UCB_IO_DATA, ucb->io_out); | ||
715 | ucb1x00_reg_write(ucb, UCB_IO_DIR, ucb->io_dir); | 697 | ucb1x00_reg_write(ucb, UCB_IO_DIR, ucb->io_dir); |
716 | mutex_lock(&ucb1x00_mutex); | 698 | mutex_lock(&ucb1x00_mutex); |
717 | list_for_each_entry(dev, &ucb->devs, dev_node) { | 699 | list_for_each_entry(dev, &ucb->devs, dev_node) { |
@@ -730,7 +712,6 @@ static struct mcp_driver ucb1x00_driver = { | |||
730 | .remove = ucb1x00_remove, | 712 | .remove = ucb1x00_remove, |
731 | .suspend = ucb1x00_suspend, | 713 | .suspend = ucb1x00_suspend, |
732 | .resume = ucb1x00_resume, | 714 | .resume = ucb1x00_resume, |
733 | .id_table = ucb1x00_id, | ||
734 | }; | 715 | }; |
735 | 716 | ||
736 | static int __init ucb1x00_init(void) | 717 | static int __init ucb1x00_init(void) |
diff --git a/drivers/mfd/ucb1x00-ts.c b/drivers/mfd/ucb1x00-ts.c index 40ec3c118868..63a3cbdfa3f3 100644 --- a/drivers/mfd/ucb1x00-ts.c +++ b/drivers/mfd/ucb1x00-ts.c | |||
@@ -47,7 +47,6 @@ struct ucb1x00_ts { | |||
47 | u16 x_res; | 47 | u16 x_res; |
48 | u16 y_res; | 48 | u16 y_res; |
49 | 49 | ||
50 | unsigned int restart:1; | ||
51 | unsigned int adcsync:1; | 50 | unsigned int adcsync:1; |
52 | }; | 51 | }; |
53 | 52 | ||
@@ -207,15 +206,17 @@ static int ucb1x00_thread(void *_ts) | |||
207 | { | 206 | { |
208 | struct ucb1x00_ts *ts = _ts; | 207 | struct ucb1x00_ts *ts = _ts; |
209 | DECLARE_WAITQUEUE(wait, current); | 208 | DECLARE_WAITQUEUE(wait, current); |
209 | bool frozen, ignore = false; | ||
210 | int valid = 0; | 210 | int valid = 0; |
211 | 211 | ||
212 | set_freezable(); | 212 | set_freezable(); |
213 | add_wait_queue(&ts->irq_wait, &wait); | 213 | add_wait_queue(&ts->irq_wait, &wait); |
214 | while (!kthread_should_stop()) { | 214 | while (!kthread_freezable_should_stop(&frozen)) { |
215 | unsigned int x, y, p; | 215 | unsigned int x, y, p; |
216 | signed long timeout; | 216 | signed long timeout; |
217 | 217 | ||
218 | ts->restart = 0; | 218 | if (frozen) |
219 | ignore = true; | ||
219 | 220 | ||
220 | ucb1x00_adc_enable(ts->ucb); | 221 | ucb1x00_adc_enable(ts->ucb); |
221 | 222 | ||
@@ -258,7 +259,7 @@ static int ucb1x00_thread(void *_ts) | |||
258 | * space. We therefore leave it to user space | 259 | * space. We therefore leave it to user space |
259 | * to do any filtering they please. | 260 | * to do any filtering they please. |
260 | */ | 261 | */ |
261 | if (!ts->restart) { | 262 | if (!ignore) { |
262 | ucb1x00_ts_evt_add(ts, p, x, y); | 263 | ucb1x00_ts_evt_add(ts, p, x, y); |
263 | valid = 1; | 264 | valid = 1; |
264 | } | 265 | } |
@@ -267,8 +268,6 @@ static int ucb1x00_thread(void *_ts) | |||
267 | timeout = HZ / 100; | 268 | timeout = HZ / 100; |
268 | } | 269 | } |
269 | 270 | ||
270 | try_to_freeze(); | ||
271 | |||
272 | schedule_timeout(timeout); | 271 | schedule_timeout(timeout); |
273 | } | 272 | } |
274 | 273 | ||
@@ -340,26 +339,6 @@ static void ucb1x00_ts_close(struct input_dev *idev) | |||
340 | ucb1x00_disable(ts->ucb); | 339 | ucb1x00_disable(ts->ucb); |
341 | } | 340 | } |
342 | 341 | ||
343 | #ifdef CONFIG_PM | ||
344 | static int ucb1x00_ts_resume(struct ucb1x00_dev *dev) | ||
345 | { | ||
346 | struct ucb1x00_ts *ts = dev->priv; | ||
347 | |||
348 | if (ts->rtask != NULL) { | ||
349 | /* | ||
350 | * Restart the TS thread to ensure the | ||
351 | * TS interrupt mode is set up again | ||
352 | * after sleep. | ||
353 | */ | ||
354 | ts->restart = 1; | ||
355 | wake_up(&ts->irq_wait); | ||
356 | } | ||
357 | return 0; | ||
358 | } | ||
359 | #else | ||
360 | #define ucb1x00_ts_resume NULL | ||
361 | #endif | ||
362 | |||
363 | 342 | ||
364 | /* | 343 | /* |
365 | * Initialisation. | 344 | * Initialisation. |
@@ -382,7 +361,7 @@ static int ucb1x00_ts_add(struct ucb1x00_dev *dev) | |||
382 | ts->adcsync = adcsync ? UCB_SYNC : UCB_NOSYNC; | 361 | ts->adcsync = adcsync ? UCB_SYNC : UCB_NOSYNC; |
383 | 362 | ||
384 | idev->name = "Touchscreen panel"; | 363 | idev->name = "Touchscreen panel"; |
385 | idev->id.product = ts->ucb->id->driver_data; | 364 | idev->id.product = ts->ucb->id; |
386 | idev->open = ucb1x00_ts_open; | 365 | idev->open = ucb1x00_ts_open; |
387 | idev->close = ucb1x00_ts_close; | 366 | idev->close = ucb1x00_ts_close; |
388 | 367 | ||
@@ -425,7 +404,6 @@ static void ucb1x00_ts_remove(struct ucb1x00_dev *dev) | |||
425 | static struct ucb1x00_driver ucb1x00_ts_driver = { | 404 | static struct ucb1x00_driver ucb1x00_ts_driver = { |
426 | .add = ucb1x00_ts_add, | 405 | .add = ucb1x00_ts_add, |
427 | .remove = ucb1x00_ts_remove, | 406 | .remove = ucb1x00_ts_remove, |
428 | .resume = ucb1x00_ts_resume, | ||
429 | }; | 407 | }; |
430 | 408 | ||
431 | static int __init ucb1x00_ts_init(void) | 409 | static int __init ucb1x00_ts_init(void) |