gpio.c 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268
  1. /*
  2. * Control GPIO pins on the fly
  3. *
  4. * Copyright (c) 2008-2011 Analog Devices Inc.
  5. *
  6. * Licensed under the GPL-2 or later.
  7. */
  8. #include <common.h>
  9. #include <command.h>
  10. #include <errno.h>
  11. #include <dm.h>
  12. #include <malloc.h>
  13. #include <asm/gpio.h>
  14. #include <linux/err.h>
  15. __weak int name_to_gpio(const char *name)
  16. {
  17. return simple_strtoul(name, NULL, 10);
  18. }
  19. enum gpio_cmd {
  20. GPIOC_INPUT,
  21. GPIOC_SET,
  22. GPIOC_CLEAR,
  23. GPIOC_TOGGLE,
  24. };
  25. #if defined(CONFIG_DM_GPIO) && !defined(gpio_status)
  26. /* A few flags used by show_gpio() */
  27. enum {
  28. FLAG_SHOW_ALL = 1 << 0,
  29. FLAG_SHOW_BANK = 1 << 1,
  30. FLAG_SHOW_NEWLINE = 1 << 2,
  31. };
  32. static void gpio_get_description(struct udevice *dev, const char *bank_name,
  33. int offset, int *flagsp, bool show_all)
  34. {
  35. char buf[80];
  36. int ret;
  37. ret = gpio_get_function(dev, offset, NULL);
  38. if (ret < 0)
  39. goto err;
  40. if (!show_all && !(*flagsp & FLAG_SHOW_ALL) && ret == GPIOF_UNUSED)
  41. return;
  42. if ((*flagsp & FLAG_SHOW_BANK) && bank_name) {
  43. if (*flagsp & FLAG_SHOW_NEWLINE) {
  44. putc('\n');
  45. *flagsp &= ~FLAG_SHOW_NEWLINE;
  46. }
  47. printf("Bank %s:\n", bank_name);
  48. *flagsp &= ~FLAG_SHOW_BANK;
  49. }
  50. ret = gpio_get_status(dev, offset, buf, sizeof(buf));
  51. if (ret)
  52. goto err;
  53. printf("%s\n", buf);
  54. return;
  55. err:
  56. printf("Error %d\n", ret);
  57. }
  58. static int do_gpio_status(bool all, const char *gpio_name)
  59. {
  60. struct udevice *dev;
  61. int banklen;
  62. int flags;
  63. int ret;
  64. flags = 0;
  65. if (gpio_name && !*gpio_name)
  66. gpio_name = NULL;
  67. for (ret = uclass_first_device(UCLASS_GPIO, &dev);
  68. dev;
  69. ret = uclass_next_device(&dev)) {
  70. const char *bank_name;
  71. int num_bits;
  72. flags |= FLAG_SHOW_BANK;
  73. if (all)
  74. flags |= FLAG_SHOW_ALL;
  75. bank_name = gpio_get_bank_info(dev, &num_bits);
  76. if (!num_bits) {
  77. debug("GPIO device %s has no bits\n", dev->name);
  78. continue;
  79. }
  80. banklen = bank_name ? strlen(bank_name) : 0;
  81. if (!gpio_name || !bank_name ||
  82. !strncasecmp(gpio_name, bank_name, banklen)) {
  83. const char *p;
  84. int offset;
  85. p = gpio_name + banklen;
  86. if (gpio_name && *p) {
  87. offset = simple_strtoul(p, NULL, 10);
  88. gpio_get_description(dev, bank_name, offset,
  89. &flags, true);
  90. } else {
  91. for (offset = 0; offset < num_bits; offset++) {
  92. gpio_get_description(dev, bank_name,
  93. offset, &flags, false);
  94. }
  95. }
  96. }
  97. /* Add a newline between bank names */
  98. if (!(flags & FLAG_SHOW_BANK))
  99. flags |= FLAG_SHOW_NEWLINE;
  100. }
  101. return ret;
  102. }
  103. #endif
  104. static int do_gpio(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
  105. {
  106. unsigned int gpio;
  107. enum gpio_cmd sub_cmd;
  108. int value;
  109. const char *str_cmd, *str_gpio = NULL;
  110. int ret;
  111. #ifdef CONFIG_DM_GPIO
  112. bool all = false;
  113. #endif
  114. if (argc < 2)
  115. show_usage:
  116. return CMD_RET_USAGE;
  117. str_cmd = argv[1];
  118. argc -= 2;
  119. argv += 2;
  120. #ifdef CONFIG_DM_GPIO
  121. if (argc > 0 && !strcmp(*argv, "-a")) {
  122. all = true;
  123. argc--;
  124. argv++;
  125. }
  126. #endif
  127. if (argc > 0)
  128. str_gpio = *argv;
  129. if (!strncmp(str_cmd, "status", 2)) {
  130. /* Support deprecated gpio_status() */
  131. #ifdef gpio_status
  132. gpio_status();
  133. return 0;
  134. #elif defined(CONFIG_DM_GPIO)
  135. return cmd_process_error(cmdtp, do_gpio_status(all, str_gpio));
  136. #else
  137. goto show_usage;
  138. #endif
  139. }
  140. if (!str_gpio)
  141. goto show_usage;
  142. /* parse the behavior */
  143. switch (*str_cmd) {
  144. case 'i':
  145. sub_cmd = GPIOC_INPUT;
  146. break;
  147. case 's':
  148. sub_cmd = GPIOC_SET;
  149. break;
  150. case 'c':
  151. sub_cmd = GPIOC_CLEAR;
  152. break;
  153. case 't':
  154. sub_cmd = GPIOC_TOGGLE;
  155. break;
  156. default:
  157. goto show_usage;
  158. }
  159. #if defined(CONFIG_DM_GPIO)
  160. /*
  161. * TODO(sjg@chromium.org): For now we must fit into the existing GPIO
  162. * framework, so we look up the name here and convert it to a GPIO number.
  163. * Once all GPIO drivers are converted to driver model, we can change the
  164. * code here to use the GPIO uclass interface instead of the numbered
  165. * GPIO compatibility layer.
  166. */
  167. ret = gpio_lookup_name(str_gpio, NULL, NULL, &gpio);
  168. if (ret) {
  169. printf("GPIO: '%s' not found\n", str_gpio);
  170. return cmd_process_error(cmdtp, ret);
  171. }
  172. #else
  173. /* turn the gpio name into a gpio number */
  174. gpio = name_to_gpio(str_gpio);
  175. if (gpio < 0)
  176. goto show_usage;
  177. #endif
  178. /* grab the pin before we tweak it */
  179. ret = gpio_request(gpio, "cmd_gpio");
  180. if (ret && ret != -EBUSY) {
  181. printf("gpio: requesting pin %u failed\n", gpio);
  182. return -1;
  183. }
  184. /* finally, let's do it: set direction and exec command */
  185. if (sub_cmd == GPIOC_INPUT) {
  186. gpio_direction_input(gpio);
  187. value = gpio_get_value(gpio);
  188. } else {
  189. switch (sub_cmd) {
  190. case GPIOC_SET:
  191. value = 1;
  192. break;
  193. case GPIOC_CLEAR:
  194. value = 0;
  195. break;
  196. case GPIOC_TOGGLE:
  197. value = gpio_get_value(gpio);
  198. if (!IS_ERR_VALUE(value))
  199. value = !value;
  200. break;
  201. default:
  202. goto show_usage;
  203. }
  204. gpio_direction_output(gpio, value);
  205. }
  206. printf("gpio: pin %s (gpio %u) value is ", str_gpio, gpio);
  207. if (IS_ERR_VALUE(value)) {
  208. printf("unknown (ret=%d)\n", value);
  209. goto err;
  210. } else {
  211. printf("%d\n", value);
  212. }
  213. if (sub_cmd != GPIOC_INPUT && !IS_ERR_VALUE(value)) {
  214. int nval = gpio_get_value(gpio);
  215. if (IS_ERR_VALUE(nval)) {
  216. printf(" Warning: no access to GPIO output value\n");
  217. goto err;
  218. } else if (nval != value) {
  219. printf(" Warning: value of pin is still %d\n", nval);
  220. goto err;
  221. }
  222. }
  223. if (ret != -EBUSY)
  224. gpio_free(gpio);
  225. /*
  226. * Whilst wrong, the legacy gpio input command returns the pin
  227. * value, or CMD_RET_FAILURE (which is indistinguishable from a
  228. * valid pin value).
  229. */
  230. return (sub_cmd == GPIOC_INPUT) ? value : CMD_RET_SUCCESS;
  231. err:
  232. if (ret != -EBUSY)
  233. gpio_free(gpio);
  234. return CMD_RET_FAILURE;
  235. }
  236. U_BOOT_CMD(gpio, 4, 0, do_gpio,
  237. "query and control gpio pins",
  238. "<input|set|clear|toggle> <pin>\n"
  239. " - input/set/clear/toggle the specified pin\n"
  240. "gpio status [-a] [<bank> | <pin>] - show [all/claimed] GPIOs");