greybus: arche-platform: Return immediately if in same state from state change fns
[cascardo/linux.git] / drivers / staging / greybus / arche-platform.c
1 /*
2  * Arche Platform driver to enable Unipro link.
3  *
4  * Copyright 2014-2015 Google Inc.
5  * Copyright 2014-2015 Linaro Ltd.
6  *
7  * Released under the GPLv2 only.
8  */
9
10 #include <linux/clk.h>
11 #include <linux/delay.h>
12 #include <linux/gpio.h>
13 #include <linux/init.h>
14 #include <linux/module.h>
15 #include <linux/of_gpio.h>
16 #include <linux/of_platform.h>
17 #include <linux/pinctrl/consumer.h>
18 #include <linux/platform_device.h>
19 #include <linux/pm.h>
20 #include "arche_platform.h"
21
22 #include <linux/usb/usb3613.h>
23
24 struct arche_platform_drvdata {
25         /* Control GPIO signals to and from AP <=> SVC */
26         int svc_reset_gpio;
27         bool is_reset_act_hi;
28         int svc_sysboot_gpio;
29         int wake_detect_gpio; /* bi-dir,maps to WAKE_MOD & WAKE_FRAME signals */
30
31         enum arche_platform_state state;
32
33         unsigned int svc_refclk_req;
34         struct clk *svc_ref_clk;
35
36         struct pinctrl *pinctrl;
37         struct pinctrl_state *pin_default;
38
39         int num_apbs;
40
41         struct delayed_work delayed_work;
42         struct device *dev;
43 };
44
45 static inline void svc_reset_onoff(unsigned int gpio, bool onoff)
46 {
47         gpio_set_value(gpio, onoff);
48 }
49
50 static int apb_cold_boot(struct device *dev, void *data)
51 {
52         int ret;
53
54         ret = apb_ctrl_coldboot(dev);
55         if (ret)
56                 dev_warn(dev, "failed to coldboot\n");
57
58         /*Child nodes are independent, so do not exit coldboot operation */
59         return 0;
60 }
61
62 static int apb_fw_flashing_state(struct device *dev, void *data)
63 {
64         int ret;
65
66         ret = apb_ctrl_fw_flashing(dev);
67         if (ret)
68                 dev_warn(dev, "failed to switch to fw flashing state\n");
69
70         /*Child nodes are independent, so do not exit coldboot operation */
71         return 0;
72 }
73
74 static int apb_poweroff(struct device *dev, void *data)
75 {
76         apb_ctrl_poweroff(dev);
77
78         return 0;
79 }
80
81 /**
82  * svc_delayed_work - Time to give SVC to boot.
83  */
84 static void svc_delayed_work(struct work_struct *work)
85 {
86         struct arche_platform_drvdata *arche_pdata =
87                 container_of(work, struct arche_platform_drvdata, delayed_work.work);
88         int timeout = 50;
89
90         /*
91          * 1.   SVC and AP boot independently, with AP<-->SVC wake/detect pin
92          *      deasserted (LOW in this case)
93          * 2.1. SVC allows 360 milliseconds to elapse after switch boots to work
94          *      around bug described in ENG-330.
95          * 2.2. AP asserts wake/detect pin (HIGH) (this can proceed in parallel with 2.1)
96          * 3.   SVC detects assertion of wake/detect pin, and sends "wake out" signal to AP
97          * 4.   AP receives "wake out" signal, takes AP Bridges through their power
98          *      on reset sequence as defined in the bridge ASIC reference manuals
99          * 5. AP takes USB3613 through its power on reset sequence
100          * 6. AP enumerates AP Bridges
101          */
102         gpio_set_value(arche_pdata->wake_detect_gpio, 1);
103         gpio_direction_input(arche_pdata->wake_detect_gpio);
104         do {
105                 /* Read the wake_detect GPIO, for WAKE_OUT event from SVC */
106                 if (gpio_get_value(arche_pdata->wake_detect_gpio) == 0)
107                         break;
108
109                 msleep(100);
110         } while(timeout--);
111
112         if (timeout < 0) {
113                 /* FIXME: We may want to limit retries here */
114                 dev_warn(arche_pdata->dev,
115                         "Timed out on wake/detect, rescheduling handshake\n");
116                 gpio_direction_output(arche_pdata->wake_detect_gpio, 0);
117                 schedule_delayed_work(&arche_pdata->delayed_work, msecs_to_jiffies(2000));
118                 return;
119         }
120
121         /* Bring APB out of reset: cold boot sequence */
122         device_for_each_child(arche_pdata->dev, NULL, apb_cold_boot);
123
124         /* re-assert wake_detect to confirm SVC WAKE_OUT */
125         gpio_direction_output(arche_pdata->wake_detect_gpio, 1);
126
127         /* Enable HUB3613 into HUB mode. */
128         if (usb3613_hub_mode_ctrl(true))
129                 dev_warn(arche_pdata->dev, "failed to control hub device\n");
130 }
131
132 static int arche_platform_coldboot_seq(struct arche_platform_drvdata *arche_pdata)
133 {
134         int ret;
135
136         if (arche_pdata->state == ARCHE_PLATFORM_STATE_ACTIVE)
137                 return 0;
138
139         dev_info(arche_pdata->dev, "Booting from cold boot state\n");
140
141         svc_reset_onoff(arche_pdata->svc_reset_gpio,
142                         arche_pdata->is_reset_act_hi);
143
144         gpio_set_value(arche_pdata->svc_sysboot_gpio, 0);
145         usleep_range(100, 200);
146
147         ret = clk_prepare_enable(arche_pdata->svc_ref_clk);
148         if (ret) {
149                 dev_err(arche_pdata->dev, "failed to enable svc_ref_clk: %d\n",
150                                 ret);
151                 return ret;
152         }
153
154         /* bring SVC out of reset */
155         svc_reset_onoff(arche_pdata->svc_reset_gpio,
156                         !arche_pdata->is_reset_act_hi);
157
158         arche_pdata->state = ARCHE_PLATFORM_STATE_ACTIVE;
159
160         return 0;
161 }
162
163 static void arche_platform_fw_flashing_seq(struct arche_platform_drvdata *arche_pdata)
164 {
165         if (arche_pdata->state == ARCHE_PLATFORM_STATE_FW_FLASHING)
166                 return;
167
168         dev_info(arche_pdata->dev, "Switching to FW flashing state\n");
169
170         svc_reset_onoff(arche_pdata->svc_reset_gpio,
171                         arche_pdata->is_reset_act_hi);
172
173         gpio_set_value(arche_pdata->svc_sysboot_gpio, 1);
174
175         usleep_range(100, 200);
176         svc_reset_onoff(arche_pdata->svc_reset_gpio,
177                         !arche_pdata->is_reset_act_hi);
178
179         arche_pdata->state = ARCHE_PLATFORM_STATE_FW_FLASHING;
180
181 }
182
183 static void arche_platform_poweroff_seq(struct arche_platform_drvdata *arche_pdata)
184 {
185         if (arche_pdata->state == ARCHE_PLATFORM_STATE_OFF)
186                 return;
187
188         /* Send disconnect/detach event to SVC */
189         gpio_set_value(arche_pdata->wake_detect_gpio, 0);
190         usleep_range(100, 200);
191
192         clk_disable_unprepare(arche_pdata->svc_ref_clk);
193         /* As part of exit, put APB back in reset state */
194         svc_reset_onoff(arche_pdata->svc_reset_gpio,
195                         arche_pdata->is_reset_act_hi);
196
197         arche_pdata->state = ARCHE_PLATFORM_STATE_OFF;
198 }
199
200 static ssize_t state_store(struct device *dev,
201                 struct device_attribute *attr, const char *buf, size_t count)
202 {
203         struct platform_device *pdev = to_platform_device(dev);
204         struct arche_platform_drvdata *arche_pdata = platform_get_drvdata(pdev);
205         int ret = 0;
206
207         if (sysfs_streq(buf, "off")) {
208                 if (arche_pdata->state == ARCHE_PLATFORM_STATE_OFF)
209                         return count;
210
211                 /*  If SVC goes down, bring down APB's as well */
212                 device_for_each_child(arche_pdata->dev, NULL, apb_poweroff);
213
214                 arche_platform_poweroff_seq(arche_pdata);
215
216                 ret = usb3613_hub_mode_ctrl(false);
217                 if (ret)
218                         dev_warn(arche_pdata->dev, "failed to control hub device\n");
219                         /* TODO: Should we do anything more here ?? */
220         } else if (sysfs_streq(buf, "active")) {
221                 if (arche_pdata->state == ARCHE_PLATFORM_STATE_ACTIVE)
222                         return count;
223
224                 ret = arche_platform_coldboot_seq(arche_pdata);
225                 /* Give enough time for SVC to boot and then handshake with SVC */
226                 schedule_delayed_work(&arche_pdata->delayed_work, msecs_to_jiffies(2000));
227         } else if (sysfs_streq(buf, "standby")) {
228                 if (arche_pdata->state == ARCHE_PLATFORM_STATE_STANDBY)
229                         return count;
230
231                 dev_warn(arche_pdata->dev, "standby state not supported\n");
232         } else if (sysfs_streq(buf, "fw_flashing")) {
233                 if (arche_pdata->state == ARCHE_PLATFORM_STATE_FW_FLASHING)
234                         return count;
235
236                 /* First we want to make sure we power off everything
237                  * and then enter FW flashing state */
238                 device_for_each_child(arche_pdata->dev, NULL, apb_poweroff);
239
240                 arche_platform_poweroff_seq(arche_pdata);
241
242                 ret = usb3613_hub_mode_ctrl(false);
243                 if (ret)
244                         dev_warn(arche_pdata->dev, "failed to control hub device\n");
245                         /* TODO: Should we do anything more here ?? */
246
247                 arche_platform_fw_flashing_seq(arche_pdata);
248
249                 device_for_each_child(arche_pdata->dev, NULL, apb_fw_flashing_state);
250         } else {
251                 dev_err(arche_pdata->dev, "unknown state\n");
252                 ret = -EINVAL;
253         }
254
255         return ret ? ret : count;
256 }
257
258 static ssize_t state_show(struct device *dev,
259                 struct device_attribute *attr, char *buf)
260 {
261         struct arche_platform_drvdata *arche_pdata = dev_get_drvdata(dev);
262
263         switch (arche_pdata->state) {
264         case ARCHE_PLATFORM_STATE_OFF:
265                 return sprintf(buf, "off\n");
266         case ARCHE_PLATFORM_STATE_ACTIVE:
267                 return sprintf(buf, "active\n");
268         case ARCHE_PLATFORM_STATE_STANDBY:
269                 return sprintf(buf, "standby\n");
270         case ARCHE_PLATFORM_STATE_FW_FLASHING:
271                 return sprintf(buf, "fw_flashing\n");
272         default:
273                 return sprintf(buf, "unknown state\n");
274         }
275 }
276
277 static DEVICE_ATTR_RW(state);
278
279 static int arche_platform_probe(struct platform_device *pdev)
280 {
281         struct arche_platform_drvdata *arche_pdata;
282         struct device *dev = &pdev->dev;
283         struct device_node *np = dev->of_node;
284         int ret;
285
286         arche_pdata = devm_kzalloc(&pdev->dev, sizeof(*arche_pdata), GFP_KERNEL);
287         if (!arche_pdata)
288                 return -ENOMEM;
289
290         /* setup svc reset gpio */
291         arche_pdata->is_reset_act_hi = of_property_read_bool(np,
292                                         "svc,reset-active-high");
293         arche_pdata->svc_reset_gpio = of_get_named_gpio(np, "svc,reset-gpio", 0);
294         if (arche_pdata->svc_reset_gpio < 0) {
295                 dev_err(dev, "failed to get reset-gpio\n");
296                 return arche_pdata->svc_reset_gpio;
297         }
298         ret = devm_gpio_request(dev, arche_pdata->svc_reset_gpio, "svc-reset");
299         if (ret) {
300                 dev_err(dev, "failed to request svc-reset gpio:%d\n", ret);
301                 return ret;
302         }
303         ret = gpio_direction_output(arche_pdata->svc_reset_gpio,
304                                         arche_pdata->is_reset_act_hi);
305         if (ret) {
306                 dev_err(dev, "failed to set svc-reset gpio dir:%d\n", ret);
307                 return ret;
308         }
309         arche_pdata->state = ARCHE_PLATFORM_STATE_OFF;
310
311         arche_pdata->svc_sysboot_gpio = of_get_named_gpio(np,
312                                         "svc,sysboot-gpio", 0);
313         if (arche_pdata->svc_sysboot_gpio < 0) {
314                 dev_err(dev, "failed to get sysboot gpio\n");
315                 return arche_pdata->svc_sysboot_gpio;
316         }
317         ret = devm_gpio_request(dev, arche_pdata->svc_sysboot_gpio, "sysboot0");
318         if (ret) {
319                 dev_err(dev, "failed to request sysboot0 gpio:%d\n", ret);
320                 return ret;
321         }
322         ret = gpio_direction_output(arche_pdata->svc_sysboot_gpio, 0);
323         if (ret) {
324                 dev_err(dev, "failed to set svc-reset gpio dir:%d\n", ret);
325                 return ret;
326         }
327
328         /* setup the clock request gpio first */
329         arche_pdata->svc_refclk_req = of_get_named_gpio(np,
330                                         "svc,refclk-req-gpio", 0);
331         if (arche_pdata->svc_refclk_req < 0) {
332                 dev_err(dev, "failed to get svc clock-req gpio\n");
333                 return arche_pdata->svc_refclk_req;
334         }
335         ret = devm_gpio_request(dev, arche_pdata->svc_refclk_req, "svc-clk-req");
336         if (ret) {
337                 dev_err(dev, "failed to request svc-clk-req gpio: %d\n", ret);
338                 return ret;
339         }
340         ret = gpio_direction_input(arche_pdata->svc_refclk_req);
341         if (ret) {
342                 dev_err(dev, "failed to set svc-clk-req gpio dir :%d\n", ret);
343                 return ret;
344         }
345
346         /* setup refclk2 to follow the pin */
347         arche_pdata->svc_ref_clk = devm_clk_get(dev, "svc_ref_clk");
348         if (IS_ERR(arche_pdata->svc_ref_clk)) {
349                 ret = PTR_ERR(arche_pdata->svc_ref_clk);
350                 dev_err(dev, "failed to get svc_ref_clk: %d\n", ret);
351                 return ret;
352         }
353
354         platform_set_drvdata(pdev, arche_pdata);
355
356         arche_pdata->num_apbs = of_get_child_count(np);
357         dev_dbg(dev, "Number of APB's available - %d\n", arche_pdata->num_apbs);
358
359         arche_pdata->wake_detect_gpio = of_get_named_gpio(np, "svc,wake-detect-gpio", 0);
360         if (arche_pdata->wake_detect_gpio < 0) {
361                 dev_err(dev, "failed to get wake detect gpio\n");
362                 ret = arche_pdata->wake_detect_gpio;
363                 return ret;
364         }
365
366         ret = devm_gpio_request(dev, arche_pdata->wake_detect_gpio, "wake detect");
367         if (ret) {
368                 dev_err(dev, "Failed requesting wake_detect gpio %d\n",
369                                 arche_pdata->wake_detect_gpio);
370                 return ret;
371         }
372         /* deassert wake detect */
373         gpio_direction_output(arche_pdata->wake_detect_gpio, 0);
374
375         arche_pdata->dev = &pdev->dev;
376
377         ret = device_create_file(dev, &dev_attr_state);
378         if (ret) {
379                 dev_err(dev, "failed to create state file in sysfs\n");
380                 return ret;
381         }
382
383         ret = arche_platform_coldboot_seq(arche_pdata);
384         if (ret) {
385                 dev_err(dev, "Failed to cold boot svc %d\n", ret);
386                 return ret;
387         }
388
389         ret = of_platform_populate(np, NULL, NULL, dev);
390         if (ret) {
391                 dev_err(dev, "failed to populate child nodes %d\n", ret);
392                 return ret;
393         }
394
395         INIT_DELAYED_WORK(&arche_pdata->delayed_work, svc_delayed_work);
396         schedule_delayed_work(&arche_pdata->delayed_work, msecs_to_jiffies(2000));
397
398         dev_info(dev, "Device registered successfully\n");
399         return 0;
400 }
401
402 static int arche_remove_child(struct device *dev, void *unused)
403 {
404         struct platform_device *pdev = to_platform_device(dev);
405
406         platform_device_unregister(pdev);
407
408         return 0;
409 }
410
411 static int arche_platform_remove(struct platform_device *pdev)
412 {
413         struct arche_platform_drvdata *arche_pdata = platform_get_drvdata(pdev);
414
415         device_remove_file(&pdev->dev, &dev_attr_state);
416         cancel_delayed_work_sync(&arche_pdata->delayed_work);
417         device_for_each_child(&pdev->dev, NULL, arche_remove_child);
418         arche_platform_poweroff_seq(arche_pdata);
419         platform_set_drvdata(pdev, NULL);
420
421         if (usb3613_hub_mode_ctrl(false))
422                 dev_warn(arche_pdata->dev, "failed to control hub device\n");
423                 /* TODO: Should we do anything more here ?? */
424         return 0;
425 }
426
427 static int arche_platform_suspend(struct device *dev)
428 {
429         /*
430          * If timing profile premits, we may shutdown bridge
431          * completely
432          *
433          * TODO: sequence ??
434          *
435          * Also, need to make sure we meet precondition for unipro suspend
436          * Precondition: Definition ???
437          */
438         return 0;
439 }
440
441 static int arche_platform_resume(struct device *dev)
442 {
443         /*
444          * Atleast for ES2 we have to meet the delay requirement between
445          * unipro switch and AP bridge init, depending on whether bridge is in
446          * OFF state or standby state.
447          *
448          * Based on whether bridge is in standby or OFF state we may have to
449          * assert multiple signals. Please refer to WDM spec, for more info.
450          *
451          */
452         return 0;
453 }
454
455 static SIMPLE_DEV_PM_OPS(arche_platform_pm_ops,
456                         arche_platform_suspend,
457                         arche_platform_resume);
458
459 static struct of_device_id arche_platform_of_match[] = {
460         { .compatible = "google,arche-platform", }, /* Use PID/VID of SVC device */
461         { },
462 };
463
464 static struct of_device_id arche_apb_ctrl_of_match[] = {
465         { .compatible = "usbffff,2", },
466         { },
467 };
468
469 static struct of_device_id arche_combined_id[] = {
470         { .compatible = "google,arche-platform", }, /* Use PID/VID of SVC device */
471         { .compatible = "usbffff,2", },
472         { },
473 };
474 MODULE_DEVICE_TABLE(of, arche_combined_id);
475
476 static struct platform_driver arche_platform_device_driver = {
477         .probe          = arche_platform_probe,
478         .remove         = arche_platform_remove,
479         .driver         = {
480                 .name   = "arche-platform-ctrl",
481                 .pm     = &arche_platform_pm_ops,
482                 .of_match_table = arche_platform_of_match,
483         }
484 };
485
486 static struct platform_driver arche_apb_ctrl_device_driver = {
487         .probe          = arche_apb_ctrl_probe,
488         .remove         = arche_apb_ctrl_remove,
489         .driver         = {
490                 .name   = "arche-apb-ctrl",
491                 .pm     = &arche_apb_ctrl_pm_ops,
492                 .of_match_table = arche_apb_ctrl_of_match,
493         }
494 };
495
496 static int __init arche_init(void)
497 {
498         int retval;
499
500         retval = platform_driver_register(&arche_platform_device_driver);
501         if (retval)
502                 return retval;
503
504         retval = platform_driver_register(&arche_apb_ctrl_device_driver);
505         if (retval)
506                 platform_driver_unregister(&arche_platform_device_driver);
507
508         return retval;
509 }
510 module_init(arche_init);
511
512 static void __exit arche_exit(void)
513 {
514         platform_driver_unregister(&arche_apb_ctrl_device_driver);
515         platform_driver_unregister(&arche_platform_device_driver);
516 }
517 module_exit(arche_exit);
518
519 MODULE_LICENSE("GPL");
520 MODULE_AUTHOR("Vaibhav Hiremath <vaibhav.hiremath@linaro.org>");
521 MODULE_DESCRIPTION("Arche Platform Driver");