0154-reset-Add-reset-controller-API.patch 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529
  1. From d6cfbdfa001891894efe078a49ad82ac8a932dbb Mon Sep 17 00:00:00 2001
  2. From: John Crispin <[email protected]>
  3. Date: Mon, 20 May 2013 15:42:01 +0200
  4. Subject: [PATCH 154/164] reset: Add reset controller API
  5. backport from v3.10-rc1
  6. 61fc41317666be400802ac793f47de816ef7bd57
  7. 6034bb22d8387708075c083385e5d2e1072a4f33
  8. 4e11f848c65b1c87782cb232a6e3b47a9d4c1f98
  9. This adds a simple API for devices to request being reset
  10. by separate reset controller hardware and implements the
  11. reset signal device tree binding.
  12. Signed-off-by: Philipp Zabel <[email protected]>
  13. Reviewed-by: Stephen Warren <[email protected]>
  14. Reviewed-by: Shawn Guo <[email protected]>
  15. Reviewed-by: Marek Vasut <[email protected]>
  16. Reviewed-by: Pavel Machek <[email protected]>
  17. ---
  18. Documentation/devicetree/bindings/reset/reset.txt | 75 ++++++
  19. drivers/Kconfig | 2 +
  20. drivers/Makefile | 3 +
  21. drivers/reset/Kconfig | 13 +
  22. drivers/reset/Makefile | 1 +
  23. drivers/reset/core.c | 297 +++++++++++++++++++++
  24. include/linux/reset-controller.h | 51 ++++
  25. include/linux/reset.h | 17 ++
  26. 8 files changed, 459 insertions(+)
  27. create mode 100644 Documentation/devicetree/bindings/reset/reset.txt
  28. create mode 100644 drivers/reset/Kconfig
  29. create mode 100644 drivers/reset/Makefile
  30. create mode 100644 drivers/reset/core.c
  31. create mode 100644 include/linux/reset-controller.h
  32. create mode 100644 include/linux/reset.h
  33. --- /dev/null
  34. +++ b/Documentation/devicetree/bindings/reset/reset.txt
  35. @@ -0,0 +1,75 @@
  36. += Reset Signal Device Tree Bindings =
  37. +
  38. +This binding is intended to represent the hardware reset signals present
  39. +internally in most IC (SoC, FPGA, ...) designs. Reset signals for whole
  40. +standalone chips are most likely better represented as GPIOs, although there
  41. +are likely to be exceptions to this rule.
  42. +
  43. +Hardware blocks typically receive a reset signal. This signal is generated by
  44. +a reset provider (e.g. power management or clock module) and received by a
  45. +reset consumer (the module being reset, or a module managing when a sub-
  46. +ordinate module is reset). This binding exists to represent the provider and
  47. +consumer, and provide a way to couple the two together.
  48. +
  49. +A reset signal is represented by the phandle of the provider, plus a reset
  50. +specifier - a list of DT cells that represents the reset signal within the
  51. +provider. The length (number of cells) and semantics of the reset specifier
  52. +are dictated by the binding of the reset provider, although common schemes
  53. +are described below.
  54. +
  55. +A word on where to place reset signal consumers in device tree: It is possible
  56. +in hardware for a reset signal to affect multiple logically separate HW blocks
  57. +at once. In this case, it would be unwise to represent this reset signal in
  58. +the DT node of each affected HW block, since if activated, an unrelated block
  59. +may be reset. Instead, reset signals should be represented in the DT node
  60. +where it makes most sense to control it; this may be a bus node if all
  61. +children of the bus are affected by the reset signal, or an individual HW
  62. +block node for dedicated reset signals. The intent of this binding is to give
  63. +appropriate software access to the reset signals in order to manage the HW,
  64. +rather than to slavishly enumerate the reset signal that affects each HW
  65. +block.
  66. +
  67. += Reset providers =
  68. +
  69. +Required properties:
  70. +#reset-cells: Number of cells in a reset specifier; Typically 0 for nodes
  71. + with a single reset output and 1 for nodes with multiple
  72. + reset outputs.
  73. +
  74. +For example:
  75. +
  76. + rst: reset-controller {
  77. + #reset-cells = <1>;
  78. + };
  79. +
  80. += Reset consumers =
  81. +
  82. +Required properties:
  83. +resets: List of phandle and reset specifier pairs, one pair
  84. + for each reset signal that affects the device, or that the
  85. + device manages. Note: if the reset provider specifies '0' for
  86. + #reset-cells, then only the phandle portion of the pair will
  87. + appear.
  88. +
  89. +Optional properties:
  90. +reset-names: List of reset signal name strings sorted in the same order as
  91. + the resets property. Consumers drivers will use reset-names to
  92. + match reset signal names with reset specifiers.
  93. +
  94. +For example:
  95. +
  96. + device {
  97. + resets = <&rst 20>;
  98. + reset-names = "reset";
  99. + };
  100. +
  101. +This represents a device with a single reset signal named "reset".
  102. +
  103. + bus {
  104. + resets = <&rst 10> <&rst 11> <&rst 12> <&rst 11>;
  105. + reset-names = "i2s1", "i2s2", "dma", "mixer";
  106. + };
  107. +
  108. +This represents a bus that controls the reset signal of each of four sub-
  109. +ordinate devices. Consider for example a bus that fails to operate unless no
  110. +child device has reset asserted.
  111. --- a/drivers/Kconfig
  112. +++ b/drivers/Kconfig
  113. @@ -164,4 +164,6 @@ source "drivers/irqchip/Kconfig"
  114. source "drivers/ipack/Kconfig"
  115. +source "drivers/reset/Kconfig"
  116. +
  117. endmenu
  118. --- a/drivers/Makefile
  119. +++ b/drivers/Makefile
  120. @@ -38,6 +38,9 @@ obj-$(CONFIG_XEN) += xen/
  121. # regulators early, since some subsystems rely on them to initialize
  122. obj-$(CONFIG_REGULATOR) += regulator/
  123. +# reset controllers early, since gpu drivers might rely on them to initialize
  124. +obj-$(CONFIG_RESET_CONTROLLER) += reset/
  125. +
  126. # tty/ comes before char/ so that the VT console is the boot-time
  127. # default.
  128. obj-y += tty/
  129. --- /dev/null
  130. +++ b/drivers/reset/Kconfig
  131. @@ -0,0 +1,13 @@
  132. +config ARCH_HAS_RESET_CONTROLLER
  133. + bool
  134. +
  135. +menuconfig RESET_CONTROLLER
  136. + bool "Reset Controller Support"
  137. + default y if ARCH_HAS_RESET_CONTROLLER
  138. + help
  139. + Generic Reset Controller support.
  140. +
  141. + This framework is designed to abstract reset handling of devices
  142. + via GPIOs or SoC-internal reset controller modules.
  143. +
  144. + If unsure, say no.
  145. --- /dev/null
  146. +++ b/drivers/reset/Makefile
  147. @@ -0,0 +1 @@
  148. +obj-$(CONFIG_RESET_CONTROLLER) += core.o
  149. --- /dev/null
  150. +++ b/drivers/reset/core.c
  151. @@ -0,0 +1,297 @@
  152. +/*
  153. + * Reset Controller framework
  154. + *
  155. + * Copyright 2013 Philipp Zabel, Pengutronix
  156. + *
  157. + * This program is free software; you can redistribute it and/or modify
  158. + * it under the terms of the GNU General Public License as published by
  159. + * the Free Software Foundation; either version 2 of the License, or
  160. + * (at your option) any later version.
  161. + */
  162. +#include <linux/device.h>
  163. +#include <linux/err.h>
  164. +#include <linux/export.h>
  165. +#include <linux/kernel.h>
  166. +#include <linux/module.h>
  167. +#include <linux/of.h>
  168. +#include <linux/reset.h>
  169. +#include <linux/reset-controller.h>
  170. +#include <linux/slab.h>
  171. +
  172. +static DEFINE_MUTEX(reset_controller_list_mutex);
  173. +static LIST_HEAD(reset_controller_list);
  174. +
  175. +/**
  176. + * struct reset_control - a reset control
  177. + * @rcdev: a pointer to the reset controller device
  178. + * this reset control belongs to
  179. + * @id: ID of the reset controller in the reset
  180. + * controller device
  181. + */
  182. +struct reset_control {
  183. + struct reset_controller_dev *rcdev;
  184. + struct device *dev;
  185. + unsigned int id;
  186. +};
  187. +
  188. +/**
  189. + * of_reset_simple_xlate - translate reset_spec to the reset line number
  190. + * @rcdev: a pointer to the reset controller device
  191. + * @reset_spec: reset line specifier as found in the device tree
  192. + * @flags: a flags pointer to fill in (optional)
  193. + *
  194. + * This simple translation function should be used for reset controllers
  195. + * with 1:1 mapping, where reset lines can be indexed by number without gaps.
  196. + */
  197. +int of_reset_simple_xlate(struct reset_controller_dev *rcdev,
  198. + const struct of_phandle_args *reset_spec)
  199. +{
  200. + if (WARN_ON(reset_spec->args_count != rcdev->of_reset_n_cells))
  201. + return -EINVAL;
  202. +
  203. + if (reset_spec->args[0] >= rcdev->nr_resets)
  204. + return -EINVAL;
  205. +
  206. + return reset_spec->args[0];
  207. +}
  208. +EXPORT_SYMBOL_GPL(of_reset_simple_xlate);
  209. +
  210. +/**
  211. + * reset_controller_register - register a reset controller device
  212. + * @rcdev: a pointer to the initialized reset controller device
  213. + */
  214. +int reset_controller_register(struct reset_controller_dev *rcdev)
  215. +{
  216. + if (!rcdev->of_xlate) {
  217. + rcdev->of_reset_n_cells = 1;
  218. + rcdev->of_xlate = of_reset_simple_xlate;
  219. + }
  220. +
  221. + mutex_lock(&reset_controller_list_mutex);
  222. + list_add(&rcdev->list, &reset_controller_list);
  223. + mutex_unlock(&reset_controller_list_mutex);
  224. +
  225. + return 0;
  226. +}
  227. +EXPORT_SYMBOL_GPL(reset_controller_register);
  228. +
  229. +/**
  230. + * reset_controller_unregister - unregister a reset controller device
  231. + * @rcdev: a pointer to the reset controller device
  232. + */
  233. +void reset_controller_unregister(struct reset_controller_dev *rcdev)
  234. +{
  235. + mutex_lock(&reset_controller_list_mutex);
  236. + list_del(&rcdev->list);
  237. + mutex_unlock(&reset_controller_list_mutex);
  238. +}
  239. +EXPORT_SYMBOL_GPL(reset_controller_unregister);
  240. +
  241. +/**
  242. + * reset_control_reset - reset the controlled device
  243. + * @rstc: reset controller
  244. + */
  245. +int reset_control_reset(struct reset_control *rstc)
  246. +{
  247. + if (rstc->rcdev->ops->reset)
  248. + return rstc->rcdev->ops->reset(rstc->rcdev, rstc->id);
  249. +
  250. + return -ENOSYS;
  251. +}
  252. +EXPORT_SYMBOL_GPL(reset_control_reset);
  253. +
  254. +/**
  255. + * reset_control_assert - asserts the reset line
  256. + * @rstc: reset controller
  257. + */
  258. +int reset_control_assert(struct reset_control *rstc)
  259. +{
  260. + if (rstc->rcdev->ops->assert)
  261. + return rstc->rcdev->ops->assert(rstc->rcdev, rstc->id);
  262. +
  263. + return -ENOSYS;
  264. +}
  265. +EXPORT_SYMBOL_GPL(reset_control_assert);
  266. +
  267. +/**
  268. + * reset_control_deassert - deasserts the reset line
  269. + * @rstc: reset controller
  270. + */
  271. +int reset_control_deassert(struct reset_control *rstc)
  272. +{
  273. + if (rstc->rcdev->ops->deassert)
  274. + return rstc->rcdev->ops->deassert(rstc->rcdev, rstc->id);
  275. +
  276. + return -ENOSYS;
  277. +}
  278. +EXPORT_SYMBOL_GPL(reset_control_deassert);
  279. +
  280. +/**
  281. + * reset_control_get - Lookup and obtain a reference to a reset controller.
  282. + * @dev: device to be reset by the controller
  283. + * @id: reset line name
  284. + *
  285. + * Returns a struct reset_control or IS_ERR() condition containing errno.
  286. + *
  287. + * Use of id names is optional.
  288. + */
  289. +struct reset_control *reset_control_get(struct device *dev, const char *id)
  290. +{
  291. + struct reset_control *rstc = ERR_PTR(-EPROBE_DEFER);
  292. + struct reset_controller_dev *r, *rcdev;
  293. + struct of_phandle_args args;
  294. + int index = 0;
  295. + int rstc_id;
  296. + int ret;
  297. +
  298. + if (!dev)
  299. + return ERR_PTR(-EINVAL);
  300. +
  301. + if (id)
  302. + index = of_property_match_string(dev->of_node,
  303. + "reset-names", id);
  304. + ret = of_parse_phandle_with_args(dev->of_node, "resets", "#reset-cells",
  305. + index, &args);
  306. + if (ret)
  307. + return ERR_PTR(ret);
  308. +
  309. + mutex_lock(&reset_controller_list_mutex);
  310. + rcdev = NULL;
  311. + list_for_each_entry(r, &reset_controller_list, list) {
  312. + if (args.np == r->of_node) {
  313. + rcdev = r;
  314. + break;
  315. + }
  316. + }
  317. + of_node_put(args.np);
  318. +
  319. + if (!rcdev) {
  320. + mutex_unlock(&reset_controller_list_mutex);
  321. + return ERR_PTR(-ENODEV);
  322. + }
  323. +
  324. + rstc_id = rcdev->of_xlate(rcdev, &args);
  325. + if (rstc_id < 0) {
  326. + mutex_unlock(&reset_controller_list_mutex);
  327. + return ERR_PTR(rstc_id);
  328. + }
  329. +
  330. + try_module_get(rcdev->owner);
  331. + mutex_unlock(&reset_controller_list_mutex);
  332. +
  333. + rstc = kzalloc(sizeof(*rstc), GFP_KERNEL);
  334. + if (!rstc) {
  335. + module_put(rcdev->owner);
  336. + return ERR_PTR(-ENOMEM);
  337. + }
  338. +
  339. + rstc->dev = dev;
  340. + rstc->rcdev = rcdev;
  341. + rstc->id = rstc_id;
  342. +
  343. + return rstc;
  344. +}
  345. +EXPORT_SYMBOL_GPL(reset_control_get);
  346. +
  347. +/**
  348. + * reset_control_put - free the reset controller
  349. + * @rstc: reset controller
  350. + */
  351. +
  352. +void reset_control_put(struct reset_control *rstc)
  353. +{
  354. + if (IS_ERR(rstc))
  355. + return;
  356. +
  357. + module_put(rstc->rcdev->owner);
  358. + kfree(rstc);
  359. +}
  360. +EXPORT_SYMBOL_GPL(reset_control_put);
  361. +
  362. +static void devm_reset_control_release(struct device *dev, void *res)
  363. +{
  364. + reset_control_put(*(struct reset_control **)res);
  365. +}
  366. +
  367. +/**
  368. + * devm_reset_control_get - resource managed reset_control_get()
  369. + * @dev: device to be reset by the controller
  370. + * @id: reset line name
  371. + *
  372. + * Managed reset_control_get(). For reset controllers returned from this
  373. + * function, reset_control_put() is called automatically on driver detach.
  374. + * See reset_control_get() for more information.
  375. + */
  376. +struct reset_control *devm_reset_control_get(struct device *dev, const char *id)
  377. +{
  378. + struct reset_control **ptr, *rstc;
  379. +
  380. + ptr = devres_alloc(devm_reset_control_release, sizeof(*ptr),
  381. + GFP_KERNEL);
  382. + if (!ptr)
  383. + return ERR_PTR(-ENOMEM);
  384. +
  385. + rstc = reset_control_get(dev, id);
  386. + if (!IS_ERR(rstc)) {
  387. + *ptr = rstc;
  388. + devres_add(dev, ptr);
  389. + } else {
  390. + devres_free(ptr);
  391. + }
  392. +
  393. + return rstc;
  394. +}
  395. +EXPORT_SYMBOL_GPL(devm_reset_control_get);
  396. +
  397. +static int devm_reset_control_match(struct device *dev, void *res, void *data)
  398. +{
  399. + struct reset_control **rstc = res;
  400. + if (WARN_ON(!rstc || !*rstc))
  401. + return 0;
  402. + return *rstc == data;
  403. +}
  404. +
  405. +/**
  406. + * devm_reset_control_put - resource managed reset_control_put()
  407. + * @rstc: reset controller to free
  408. + *
  409. + * Deallocate a reset control allocated withd devm_reset_control_get().
  410. + * This function will not need to be called normally, as devres will take
  411. + * care of freeing the resource.
  412. + */
  413. +void devm_reset_control_put(struct reset_control *rstc)
  414. +{
  415. + int ret;
  416. +
  417. + ret = devres_release(rstc->dev, devm_reset_control_release,
  418. + devm_reset_control_match, rstc);
  419. + if (ret)
  420. + WARN_ON(ret);
  421. +}
  422. +EXPORT_SYMBOL_GPL(devm_reset_control_put);
  423. +
  424. +/**
  425. + * device_reset - find reset controller associated with the device
  426. + * and perform reset
  427. + * @dev: device to be reset by the controller
  428. + *
  429. + * Convenience wrapper for reset_control_get() and reset_control_reset().
  430. + * This is useful for the common case of devices with single, dedicated reset
  431. + * lines.
  432. + */
  433. +int device_reset(struct device *dev)
  434. +{
  435. + struct reset_control *rstc;
  436. + int ret;
  437. +
  438. + rstc = reset_control_get(dev, NULL);
  439. + if (IS_ERR(rstc))
  440. + return PTR_ERR(rstc);
  441. +
  442. + ret = reset_control_reset(rstc);
  443. +
  444. + reset_control_put(rstc);
  445. +
  446. + return ret;
  447. +}
  448. +EXPORT_SYMBOL_GPL(device_reset);
  449. --- /dev/null
  450. +++ b/include/linux/reset-controller.h
  451. @@ -0,0 +1,51 @@
  452. +#ifndef _LINUX_RESET_CONTROLLER_H_
  453. +#define _LINUX_RESET_CONTROLLER_H_
  454. +
  455. +#include <linux/list.h>
  456. +
  457. +struct reset_controller_dev;
  458. +
  459. +/**
  460. + * struct reset_control_ops
  461. + *
  462. + * @reset: for self-deasserting resets, does all necessary
  463. + * things to reset the device
  464. + * @assert: manually assert the reset line, if supported
  465. + * @deassert: manually deassert the reset line, if supported
  466. + */
  467. +struct reset_control_ops {
  468. + int (*reset)(struct reset_controller_dev *rcdev, unsigned long id);
  469. + int (*assert)(struct reset_controller_dev *rcdev, unsigned long id);
  470. + int (*deassert)(struct reset_controller_dev *rcdev, unsigned long id);
  471. +};
  472. +
  473. +struct module;
  474. +struct device_node;
  475. +
  476. +/**
  477. + * struct reset_controller_dev - reset controller entity that might
  478. + * provide multiple reset controls
  479. + * @ops: a pointer to device specific struct reset_control_ops
  480. + * @owner: kernel module of the reset controller driver
  481. + * @list: internal list of reset controller devices
  482. + * @of_node: corresponding device tree node as phandle target
  483. + * @of_reset_n_cells: number of cells in reset line specifiers
  484. + * @of_xlate: translation function to translate from specifier as found in the
  485. + * device tree to id as given to the reset control ops
  486. + * @nr_resets: number of reset controls in this reset controller device
  487. + */
  488. +struct reset_controller_dev {
  489. + struct reset_control_ops *ops;
  490. + struct module *owner;
  491. + struct list_head list;
  492. + struct device_node *of_node;
  493. + int of_reset_n_cells;
  494. + int (*of_xlate)(struct reset_controller_dev *rcdev,
  495. + const struct of_phandle_args *reset_spec);
  496. + unsigned int nr_resets;
  497. +};
  498. +
  499. +int reset_controller_register(struct reset_controller_dev *rcdev);
  500. +void reset_controller_unregister(struct reset_controller_dev *rcdev);
  501. +
  502. +#endif
  503. --- /dev/null
  504. +++ b/include/linux/reset.h
  505. @@ -0,0 +1,17 @@
  506. +#ifndef _LINUX_RESET_H_
  507. +#define _LINUX_RESET_H_
  508. +
  509. +struct device;
  510. +struct reset_control;
  511. +
  512. +int reset_control_reset(struct reset_control *rstc);
  513. +int reset_control_assert(struct reset_control *rstc);
  514. +int reset_control_deassert(struct reset_control *rstc);
  515. +
  516. +struct reset_control *reset_control_get(struct device *dev, const char *id);
  517. +void reset_control_put(struct reset_control *rstc);
  518. +struct reset_control *devm_reset_control_get(struct device *dev, const char *id);
  519. +
  520. +int device_reset(struct device *dev);
  521. +
  522. +#endif