blob: 9f5e0e4ab02adf19c16223b7946b7411ef7bcd3c [file] [log] [blame]
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +01001/*
2 * drivers/usb/otg/ab8500_usb.c
3 *
4 * USB transceiver driver for AB8500 chip
5 *
6 * Copyright (C) 2010 ST-Ericsson AB
7 * Mian Yousaf Kaukab <mian.yousaf.kaukab@stericsson.com>
8 *
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 *
23 */
24
25#include <linux/module.h>
26#include <linux/platform_device.h>
27#include <linux/usb/otg.h>
28#include <linux/slab.h>
29#include <linux/notifier.h>
30#include <linux/interrupt.h>
31#include <linux/delay.h>
32#include <linux/mfd/abx500.h>
Linus Walleijee66e652011-12-02 14:16:33 +010033#include <linux/mfd/abx500/ab8500.h>
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +010034
35#define AB8500_MAIN_WD_CTRL_REG 0x01
36#define AB8500_USB_LINE_STAT_REG 0x80
37#define AB8500_USB_PHY_CTRL_REG 0x8A
38
39#define AB8500_BIT_OTG_STAT_ID (1 << 0)
40#define AB8500_BIT_PHY_CTRL_HOST_EN (1 << 0)
41#define AB8500_BIT_PHY_CTRL_DEVICE_EN (1 << 1)
42#define AB8500_BIT_WD_CTRL_ENABLE (1 << 0)
43#define AB8500_BIT_WD_CTRL_KICK (1 << 1)
44
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +010045#define AB8500_WD_KICK_DELAY_US 100 /* usec */
46#define AB8500_WD_V11_DISABLE_DELAY_US 100 /* usec */
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +010047
48/* Usb line status register */
49enum ab8500_usb_link_status {
50 USB_LINK_NOT_CONFIGURED = 0,
51 USB_LINK_STD_HOST_NC,
52 USB_LINK_STD_HOST_C_NS,
53 USB_LINK_STD_HOST_C_S,
54 USB_LINK_HOST_CHG_NM,
55 USB_LINK_HOST_CHG_HS,
56 USB_LINK_HOST_CHG_HS_CHIRP,
57 USB_LINK_DEDICATED_CHG,
58 USB_LINK_ACA_RID_A,
59 USB_LINK_ACA_RID_B,
60 USB_LINK_ACA_RID_C_NM,
61 USB_LINK_ACA_RID_C_HS,
62 USB_LINK_ACA_RID_C_HS_CHIRP,
63 USB_LINK_HM_IDGND,
64 USB_LINK_RESERVED,
65 USB_LINK_NOT_VALID_LINK
66};
67
68struct ab8500_usb {
Heikki Krogerus144713f2012-02-13 13:24:05 +020069 struct usb_phy phy;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +010070 struct device *dev;
Fabio Baltieri73f226c2013-03-08 10:27:08 +080071 struct ab8500 *ab8500;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +010072 int irq_num_link_status;
73 unsigned vbus_draw;
74 struct delayed_work dwork;
75 struct work_struct phy_dis_work;
76 unsigned long link_status_wait;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +010077};
78
Heikki Krogerus144713f2012-02-13 13:24:05 +020079static inline struct ab8500_usb *phy_to_ab(struct usb_phy *x)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +010080{
Heikki Krogerus144713f2012-02-13 13:24:05 +020081 return container_of(x, struct ab8500_usb, phy);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +010082}
83
84static void ab8500_usb_wd_workaround(struct ab8500_usb *ab)
85{
86 abx500_set_register_interruptible(ab->dev,
87 AB8500_SYS_CTRL2_BLOCK,
88 AB8500_MAIN_WD_CTRL_REG,
89 AB8500_BIT_WD_CTRL_ENABLE);
90
91 udelay(AB8500_WD_KICK_DELAY_US);
92
93 abx500_set_register_interruptible(ab->dev,
94 AB8500_SYS_CTRL2_BLOCK,
95 AB8500_MAIN_WD_CTRL_REG,
96 (AB8500_BIT_WD_CTRL_ENABLE
97 | AB8500_BIT_WD_CTRL_KICK));
98
Fabio Baltieri73f226c2013-03-08 10:27:08 +080099 udelay(AB8500_WD_V11_DISABLE_DELAY_US);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100100
101 abx500_set_register_interruptible(ab->dev,
102 AB8500_SYS_CTRL2_BLOCK,
103 AB8500_MAIN_WD_CTRL_REG,
104 0);
105}
106
107static void ab8500_usb_phy_ctrl(struct ab8500_usb *ab, bool sel_host,
108 bool enable)
109{
110 u8 ctrl_reg;
111 abx500_get_register_interruptible(ab->dev,
112 AB8500_USB,
113 AB8500_USB_PHY_CTRL_REG,
114 &ctrl_reg);
115 if (sel_host) {
116 if (enable)
117 ctrl_reg |= AB8500_BIT_PHY_CTRL_HOST_EN;
118 else
119 ctrl_reg &= ~AB8500_BIT_PHY_CTRL_HOST_EN;
120 } else {
121 if (enable)
122 ctrl_reg |= AB8500_BIT_PHY_CTRL_DEVICE_EN;
123 else
124 ctrl_reg &= ~AB8500_BIT_PHY_CTRL_DEVICE_EN;
125 }
126
127 abx500_set_register_interruptible(ab->dev,
128 AB8500_USB,
129 AB8500_USB_PHY_CTRL_REG,
130 ctrl_reg);
131
132 /* Needed to enable the phy.*/
133 if (enable)
134 ab8500_usb_wd_workaround(ab);
135}
136
137#define ab8500_usb_host_phy_en(ab) ab8500_usb_phy_ctrl(ab, true, true)
138#define ab8500_usb_host_phy_dis(ab) ab8500_usb_phy_ctrl(ab, true, false)
139#define ab8500_usb_peri_phy_en(ab) ab8500_usb_phy_ctrl(ab, false, true)
140#define ab8500_usb_peri_phy_dis(ab) ab8500_usb_phy_ctrl(ab, false, false)
141
142static int ab8500_usb_link_status_update(struct ab8500_usb *ab)
143{
144 u8 reg;
145 enum ab8500_usb_link_status lsts;
146 void *v = NULL;
Heikki Krogerusde07e182012-02-13 13:24:03 +0200147 enum usb_phy_events event;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100148
149 abx500_get_register_interruptible(ab->dev,
150 AB8500_USB,
151 AB8500_USB_LINE_STAT_REG,
152 &reg);
153
154 lsts = (reg >> 3) & 0x0F;
155
156 switch (lsts) {
157 case USB_LINK_NOT_CONFIGURED:
158 case USB_LINK_RESERVED:
159 case USB_LINK_NOT_VALID_LINK:
160 /* TODO: Disable regulators. */
161 ab8500_usb_host_phy_dis(ab);
162 ab8500_usb_peri_phy_dis(ab);
Heikki Krogerus144713f2012-02-13 13:24:05 +0200163 ab->phy.state = OTG_STATE_B_IDLE;
164 ab->phy.otg->default_a = false;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100165 ab->vbus_draw = 0;
166 event = USB_EVENT_NONE;
167 break;
168
169 case USB_LINK_STD_HOST_NC:
170 case USB_LINK_STD_HOST_C_NS:
171 case USB_LINK_STD_HOST_C_S:
172 case USB_LINK_HOST_CHG_NM:
173 case USB_LINK_HOST_CHG_HS:
174 case USB_LINK_HOST_CHG_HS_CHIRP:
Heikki Krogerus144713f2012-02-13 13:24:05 +0200175 if (ab->phy.otg->gadget) {
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100176 /* TODO: Enable regulators. */
177 ab8500_usb_peri_phy_en(ab);
Heikki Krogerus144713f2012-02-13 13:24:05 +0200178 v = ab->phy.otg->gadget;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100179 }
180 event = USB_EVENT_VBUS;
181 break;
182
183 case USB_LINK_HM_IDGND:
Heikki Krogerus144713f2012-02-13 13:24:05 +0200184 if (ab->phy.otg->host) {
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100185 /* TODO: Enable regulators. */
186 ab8500_usb_host_phy_en(ab);
Heikki Krogerus144713f2012-02-13 13:24:05 +0200187 v = ab->phy.otg->host;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100188 }
Heikki Krogerus144713f2012-02-13 13:24:05 +0200189 ab->phy.state = OTG_STATE_A_IDLE;
190 ab->phy.otg->default_a = true;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100191 event = USB_EVENT_ID;
192 break;
193
194 case USB_LINK_ACA_RID_A:
195 case USB_LINK_ACA_RID_B:
196 /* TODO */
197 case USB_LINK_ACA_RID_C_NM:
198 case USB_LINK_ACA_RID_C_HS:
199 case USB_LINK_ACA_RID_C_HS_CHIRP:
200 case USB_LINK_DEDICATED_CHG:
201 /* TODO: vbus_draw */
202 event = USB_EVENT_CHARGER;
203 break;
204 }
205
Heikki Krogerus144713f2012-02-13 13:24:05 +0200206 atomic_notifier_call_chain(&ab->phy.notifier, event, v);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100207
208 return 0;
209}
210
211static void ab8500_usb_delayed_work(struct work_struct *work)
212{
213 struct ab8500_usb *ab = container_of(work, struct ab8500_usb,
214 dwork.work);
215
216 ab8500_usb_link_status_update(ab);
217}
218
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100219static irqreturn_t ab8500_usb_v20_irq(int irq, void *data)
220{
221 struct ab8500_usb *ab = (struct ab8500_usb *) data;
222
223 ab8500_usb_link_status_update(ab);
224
225 return IRQ_HANDLED;
226}
227
228static void ab8500_usb_phy_disable_work(struct work_struct *work)
229{
230 struct ab8500_usb *ab = container_of(work, struct ab8500_usb,
231 phy_dis_work);
232
Heikki Krogerus144713f2012-02-13 13:24:05 +0200233 if (!ab->phy.otg->host)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100234 ab8500_usb_host_phy_dis(ab);
235
Heikki Krogerus144713f2012-02-13 13:24:05 +0200236 if (!ab->phy.otg->gadget)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100237 ab8500_usb_peri_phy_dis(ab);
238}
239
Heikki Krogerus144713f2012-02-13 13:24:05 +0200240static int ab8500_usb_set_power(struct usb_phy *phy, unsigned mA)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100241{
242 struct ab8500_usb *ab;
243
Heikki Krogerus144713f2012-02-13 13:24:05 +0200244 if (!phy)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100245 return -ENODEV;
246
Heikki Krogerus144713f2012-02-13 13:24:05 +0200247 ab = phy_to_ab(phy);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100248
249 ab->vbus_draw = mA;
250
251 if (mA)
Heikki Krogerus144713f2012-02-13 13:24:05 +0200252 atomic_notifier_call_chain(&ab->phy.notifier,
253 USB_EVENT_ENUMERATED, ab->phy.otg->gadget);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100254 return 0;
255}
256
257/* TODO: Implement some way for charging or other drivers to read
258 * ab->vbus_draw.
259 */
260
Heikki Krogerus86753812012-02-13 13:24:02 +0200261static int ab8500_usb_set_suspend(struct usb_phy *x, int suspend)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100262{
263 /* TODO */
264 return 0;
265}
266
Heikki Krogerus144713f2012-02-13 13:24:05 +0200267static int ab8500_usb_set_peripheral(struct usb_otg *otg,
268 struct usb_gadget *gadget)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100269{
270 struct ab8500_usb *ab;
271
272 if (!otg)
273 return -ENODEV;
274
Heikki Krogerus144713f2012-02-13 13:24:05 +0200275 ab = phy_to_ab(otg->phy);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100276
277 /* Some drivers call this function in atomic context.
278 * Do not update ab8500 registers directly till this
279 * is fixed.
280 */
281
282 if (!gadget) {
283 /* TODO: Disable regulators. */
Heikki Krogerus144713f2012-02-13 13:24:05 +0200284 otg->gadget = NULL;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100285 schedule_work(&ab->phy_dis_work);
286 } else {
Heikki Krogerus144713f2012-02-13 13:24:05 +0200287 otg->gadget = gadget;
288 otg->phy->state = OTG_STATE_B_IDLE;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100289
290 /* Phy will not be enabled if cable is already
291 * plugged-in. Schedule to enable phy.
292 * Use same delay to avoid any race condition.
293 */
294 schedule_delayed_work(&ab->dwork, ab->link_status_wait);
295 }
296
297 return 0;
298}
299
Heikki Krogerus144713f2012-02-13 13:24:05 +0200300static int ab8500_usb_set_host(struct usb_otg *otg, struct usb_bus *host)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100301{
302 struct ab8500_usb *ab;
303
304 if (!otg)
305 return -ENODEV;
306
Heikki Krogerus144713f2012-02-13 13:24:05 +0200307 ab = phy_to_ab(otg->phy);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100308
309 /* Some drivers call this function in atomic context.
310 * Do not update ab8500 registers directly till this
311 * is fixed.
312 */
313
314 if (!host) {
315 /* TODO: Disable regulators. */
Heikki Krogerus144713f2012-02-13 13:24:05 +0200316 otg->host = NULL;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100317 schedule_work(&ab->phy_dis_work);
318 } else {
Heikki Krogerus144713f2012-02-13 13:24:05 +0200319 otg->host = host;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100320 /* Phy will not be enabled if cable is already
321 * plugged-in. Schedule to enable phy.
322 * Use same delay to avoid any race condition.
323 */
324 schedule_delayed_work(&ab->dwork, ab->link_status_wait);
325 }
326
327 return 0;
328}
329
330static void ab8500_usb_irq_free(struct ab8500_usb *ab)
331{
Fabio Baltieri73f226c2013-03-08 10:27:08 +0800332 free_irq(ab->irq_num_link_status, ab);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100333}
334
335static int ab8500_usb_v2_res_setup(struct platform_device *pdev,
336 struct ab8500_usb *ab)
337{
338 int err;
339
340 ab->irq_num_link_status = platform_get_irq_byname(pdev,
341 "USB_LINK_STATUS");
342 if (ab->irq_num_link_status < 0) {
343 dev_err(&pdev->dev, "Link status irq not found\n");
344 return ab->irq_num_link_status;
345 }
346
347 err = request_threaded_irq(ab->irq_num_link_status, NULL,
348 ab8500_usb_v20_irq,
349 IRQF_NO_SUSPEND | IRQF_SHARED,
350 "usb-link-status", ab);
351 if (err < 0) {
352 dev_err(ab->dev,
353 "request_irq failed for link status irq\n");
354 return err;
355 }
356
357 return 0;
358}
359
Bill Pemberton41ac7b32012-11-19 13:21:48 -0500360static int ab8500_usb_probe(struct platform_device *pdev)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100361{
362 struct ab8500_usb *ab;
Fabio Baltieri73f226c2013-03-08 10:27:08 +0800363 struct ab8500 *ab8500;
Heikki Krogerus144713f2012-02-13 13:24:05 +0200364 struct usb_otg *otg;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100365 int err;
366 int rev;
367
Fabio Baltieri73f226c2013-03-08 10:27:08 +0800368 ab8500 = dev_get_drvdata(pdev->dev.parent);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100369 rev = abx500_get_chip_id(&pdev->dev);
Fabio Baltieri73f226c2013-03-08 10:27:08 +0800370
371 if (is_ab8500_1p1_or_earlier(ab8500)) {
372 dev_err(&pdev->dev, "Unsupported AB8500 chip rev=%d\n", rev);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100373 return -ENODEV;
374 }
375
376 ab = kzalloc(sizeof *ab, GFP_KERNEL);
377 if (!ab)
378 return -ENOMEM;
379
Heikki Krogerus144713f2012-02-13 13:24:05 +0200380 otg = kzalloc(sizeof *otg, GFP_KERNEL);
Dan Carpenter5f0b3f92012-03-02 11:08:14 +0300381 if (!otg) {
Heikki Krogerus144713f2012-02-13 13:24:05 +0200382 kfree(ab);
383 return -ENOMEM;
384 }
385
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100386 ab->dev = &pdev->dev;
Fabio Baltieri73f226c2013-03-08 10:27:08 +0800387 ab->ab8500 = ab8500;
Heikki Krogerus144713f2012-02-13 13:24:05 +0200388 ab->phy.dev = ab->dev;
389 ab->phy.otg = otg;
390 ab->phy.label = "ab8500";
391 ab->phy.set_suspend = ab8500_usb_set_suspend;
392 ab->phy.set_power = ab8500_usb_set_power;
393 ab->phy.state = OTG_STATE_UNDEFINED;
394
395 otg->phy = &ab->phy;
396 otg->set_host = ab8500_usb_set_host;
397 otg->set_peripheral = ab8500_usb_set_peripheral;
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100398
399 platform_set_drvdata(pdev, ab);
400
Heikki Krogerus144713f2012-02-13 13:24:05 +0200401 ATOMIC_INIT_NOTIFIER_HEAD(&ab->phy.notifier);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100402
403 /* v1: Wait for link status to become stable.
404 * all: Updates form set_host and set_peripheral as they are atomic.
405 */
406 INIT_DELAYED_WORK(&ab->dwork, ab8500_usb_delayed_work);
407
408 /* all: Disable phy when called from set_host and set_peripheral */
409 INIT_WORK(&ab->phy_dis_work, ab8500_usb_phy_disable_work);
410
Fabio Baltieri73f226c2013-03-08 10:27:08 +0800411 err = ab8500_usb_v2_res_setup(pdev, ab);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100412 if (err < 0)
413 goto fail0;
414
Kishon Vijay Abraham I662dca52012-06-22 17:02:46 +0530415 err = usb_add_phy(&ab->phy, USB_PHY_TYPE_USB2);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100416 if (err) {
417 dev_err(&pdev->dev, "Can't register transceiver\n");
418 goto fail1;
419 }
420
Fabio Baltieri73f226c2013-03-08 10:27:08 +0800421 dev_info(&pdev->dev, "revision 0x%2x driver initialized\n", rev);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100422
423 return 0;
424fail1:
425 ab8500_usb_irq_free(ab);
426fail0:
Heikki Krogerus144713f2012-02-13 13:24:05 +0200427 kfree(otg);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100428 kfree(ab);
429 return err;
430}
431
Bill Pembertonfb4e98a2012-11-19 13:26:20 -0500432static int ab8500_usb_remove(struct platform_device *pdev)
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100433{
434 struct ab8500_usb *ab = platform_get_drvdata(pdev);
435
436 ab8500_usb_irq_free(ab);
437
438 cancel_delayed_work_sync(&ab->dwork);
439
440 cancel_work_sync(&ab->phy_dis_work);
441
Kishon Vijay Abraham I662dca52012-06-22 17:02:46 +0530442 usb_remove_phy(&ab->phy);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100443
444 ab8500_usb_host_phy_dis(ab);
445 ab8500_usb_peri_phy_dis(ab);
446
447 platform_set_drvdata(pdev, NULL);
448
Heikki Krogerus144713f2012-02-13 13:24:05 +0200449 kfree(ab->phy.otg);
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100450 kfree(ab);
451
452 return 0;
453}
454
455static struct platform_driver ab8500_usb_driver = {
456 .probe = ab8500_usb_probe,
Bill Pemberton76904172012-11-19 13:21:08 -0500457 .remove = ab8500_usb_remove,
Mian Yousaf Kaukab96915232010-12-07 15:00:09 +0100458 .driver = {
459 .name = "ab8500-usb",
460 .owner = THIS_MODULE,
461 },
462};
463
464static int __init ab8500_usb_init(void)
465{
466 return platform_driver_register(&ab8500_usb_driver);
467}
468subsys_initcall(ab8500_usb_init);
469
470static void __exit ab8500_usb_exit(void)
471{
472 platform_driver_unregister(&ab8500_usb_driver);
473}
474module_exit(ab8500_usb_exit);
475
476MODULE_ALIAS("platform:ab8500_usb");
477MODULE_AUTHOR("ST-Ericsson AB");
478MODULE_DESCRIPTION("AB8500 usb transceiver driver");
479MODULE_LICENSE("GPL");