History

drivers/pinctrl: Add the concept of an "init" state

For pinctrl the "default" state is applied to pins before the driver's probe function is called. This is normally a sensible thing to do, but in some cases can cause problems. That's because the pins will change state before the driver is given a chance to program how those pins should behave. As an example you might have a regulator that is controlled by a PWM (output high = high voltage, output low = low voltage). The firmware might leave this pin as driven high. If we allow the driver core to reconfigure this pin as a PWM pin before the PWM's probe function runs then you might end up running at too low of a voltage while we probe. Let's introudce a new "init" state. If this is defined we'll set pinctrl to this state before probe and then "default" after probe (unless the driver explicitly changed states already). An alternative idea that was thought of was to use the pre-existing "sleep" or "idle" states and add a boolean property that we should start in that mode. This was not done because the "init" state is needed for correctness and those other states are only present (and only transitioned in to and out of) when (optional) power management is enabled. Changes in v3: - Moved declarations to pinctrl/devinfo.h - Fixed author/SoB Changes in v2: - Added comment to pinctrl_init_done() as per Linus W.

Douglas Anderson committed 11 years ago

Commit ef0eebc1 parent bac7f4c5 files · +65 −2Browse files

Unified · Split

5 files
  1. drivers/base/dd.c +2 −0
  2. drivers/base/pinctrl.c +13 −2
  3. drivers/pinctrl/core.c +32 −0
  4. include/linux/pinctrl/devinfo.h +10 −0
  5. include/linux/pinctrl/pinctrl-state.h +8 −0
drivers/base/dd.c+2−0
@@ -322,6 +322,8 @@ static int really_probe(struct device *dev, struct device_driver *drv) · 321 unmodified lines
322 goto probe_failed;322 goto probe_failed;
323 }323 }
324 324
325 pinctrl_init_done(dev);
326
325 if (dev->pm_domain && dev->pm_domain->sync)327 if (dev->pm_domain && dev->pm_domain->sync)
326 dev->pm_domain->sync(dev);328 dev->pm_domain->sync(dev);
327 329
drivers/base/pinctrl.c+13−2
@@ -42,9 +42,20 @@ int pinctrl_bind_pins(struct device *dev) · 41 unmodified lines
42 goto cleanup_get;42 goto cleanup_get;
43 }43 }
44 44
45 ret = pinctrl_select_state(dev->pins->p, dev->pins->default_state);45 dev->pins->init_state = pinctrl_lookup_state(dev->pins->p,
46 PINCTRL_STATE_INIT);
47 if (IS_ERR(dev->pins->init_state)) {
48 /* Not supplying this state is perfectly legal */
49 dev_dbg(dev, "no init pinctrl state\n");
50
51 ret = pinctrl_select_state(dev->pins->p,
52 dev->pins->default_state);
53 } else {
54 ret = pinctrl_select_state(dev->pins->p, dev->pins->init_state);
55 }
56
46 if (ret) {57 if (ret) {
47 dev_dbg(dev, "failed to activate default pinctrl state\n");58 dev_dbg(dev, "failed to activate initial pinctrl state\n");
48 goto cleanup_get;59 goto cleanup_get;
49 }60 }
50 61
drivers/pinctrl/core.c+32−0
@@ -1240,6 +1240,38 @@ int pinctrl_force_default(struct pinctrl_dev *pctldev) · 1239 unmodified lines
1240}1240}
1241EXPORT_SYMBOL_GPL(pinctrl_force_default);1241EXPORT_SYMBOL_GPL(pinctrl_force_default);
1242 1242
1243/**
1244 * pinctrl_init_done() - tell pinctrl probe is done
1245 *
1246 * We'll use this time to switch the pins from "init" to "default" unless the
1247 * driver selected some other state.
1248 *
1249 * @dev: device to that's done probing
1250 */
1251int pinctrl_init_done(struct device *dev)
1252{
1253 struct dev_pin_info *pins = dev->pins;
1254 int ret;
1255
1256 if (!pins)
1257 return 0;
1258
1259 if (IS_ERR(pins->init_state))
1260 return 0; /* No such state */
1261
1262 if (pins->p->state != pins->init_state)
1263 return 0; /* Not at init anyway */
1264
1265 if (IS_ERR(pins->default_state))
1266 return 0; /* No default state */
1267
1268 ret = pinctrl_select_state(pins->p, pins->default_state);
1269 if (ret)
1270 dev_err(dev, "failed to activate default pinctrl state\n");
1271
1272 return ret;
1273}
1274
1243#ifdef CONFIG_PM1275#ifdef CONFIG_PM
1244 1276
1245/**1277/**
include/linux/pinctrl/devinfo.h+10−0
@@ -24,10 +24,14 @@ · 23 unmodified lines
24 * struct dev_pin_info - pin state container for devices24 * struct dev_pin_info - pin state container for devices
25 * @p: pinctrl handle for the containing device25 * @p: pinctrl handle for the containing device
26 * @default_state: the default state for the handle, if found26 * @default_state: the default state for the handle, if found
27 * @init_state: the state at probe time, if found
28 * @sleep_state: the state at suspend time, if found
29 * @idle_state: the state at idle (runtime suspend) time, if found
27 */30 */
28struct dev_pin_info {31struct dev_pin_info {
29 struct pinctrl *p;32 struct pinctrl *p;
30 struct pinctrl_state *default_state;33 struct pinctrl_state *default_state;
34 struct pinctrl_state *init_state;
31#ifdef CONFIG_PM35#ifdef CONFIG_PM
32 struct pinctrl_state *sleep_state;36 struct pinctrl_state *sleep_state;
33 struct pinctrl_state *idle_state;37 struct pinctrl_state *idle_state;
@@ -35,6 +39,7 @@ struct dev_pin_info { · 1 unmodified line
35};39};
36 40
37extern int pinctrl_bind_pins(struct device *dev);41extern int pinctrl_bind_pins(struct device *dev);
42extern int pinctrl_init_done(struct device *dev);
38 43
39#else44#else
40 45
@@ -45,5 +50,10 @@ static inline int pinctrl_bind_pins(struct device *dev) · 4 unmodified lines
45 return 0;50 return 0;
46}51}
47 52
53static inline int pinctrl_init_done(struct device *dev)
54{
55 return 0;
56}
57
48#endif /* CONFIG_PINCTRL */58#endif /* CONFIG_PINCTRL */
49#endif /* PINCTRL_DEVINFO_H */59#endif /* PINCTRL_DEVINFO_H */
include/linux/pinctrl/pinctrl-state.h+8−0
@@ -9,6 +9,13 @@ · 8 unmodified lines
9 * hogs to configure muxing and pins at boot, and also as a state9 * hogs to configure muxing and pins at boot, and also as a state
10 * to go into when returning from sleep and idle in10 * to go into when returning from sleep and idle in
11 * .pm_runtime_resume() or ordinary .resume() for example.11 * .pm_runtime_resume() or ordinary .resume() for example.
12 * @PINCTRL_STATE_INIT: normally the pinctrl will be set to "default"
13 * before the driver's probe() function is called. There are some
14 * drivers where that is not appropriate becausing doing so would
15 * glitch the pins. In those cases you can add an "init" pinctrl
16 * which is the state of the pins before drive probe. After probe
17 * if the pins are still in "init" state they'll be moved to
18 * "default".
12 * @PINCTRL_STATE_IDLE: the state the pinctrl handle shall be put into19 * @PINCTRL_STATE_IDLE: the state the pinctrl handle shall be put into
13 * when the pins are idle. This is a state where the system is relaxed20 * when the pins are idle. This is a state where the system is relaxed
14 * but not fully sleeping - some power may be on but clocks gated for21 * but not fully sleeping - some power may be on but clocks gated for
@@ -20,5 +27,6 @@ · 5 unmodified lines
20 * ordinary .suspend() function.27 * ordinary .suspend() function.
21 */28 */
22#define PINCTRL_STATE_DEFAULT "default"29#define PINCTRL_STATE_DEFAULT "default"
30#define PINCTRL_STATE_INIT "init"
23#define PINCTRL_STATE_IDLE "idle"31#define PINCTRL_STATE_IDLE "idle"
24#define PINCTRL_STATE_SLEEP "sleep"32#define PINCTRL_STATE_SLEEP "sleep"

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t