gpio.c 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619
  1. // Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD
  2. //
  3. // Licensed under the Apache License, Version 2.0 (the "License");
  4. // you may not use this file except in compliance with the License.
  5. // You may obtain a copy of the License at
  6. // http://www.apache.org/licenses/LICENSE-2.0
  7. //
  8. // Unless required by applicable law or agreed to in writing, software
  9. // distributed under the License is distributed on an "AS IS" BASIS,
  10. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  11. // See the License for the specific language governing permissions and
  12. // limitations under the License.
  13. #include <esp_types.h>
  14. #include "esp_err.h"
  15. #include "esp_intr.h"
  16. #include "esp_intr_alloc.h"
  17. #include "freertos/FreeRTOS.h"
  18. #include "freertos/xtensa_api.h"
  19. #include "driver/gpio.h"
  20. #include "driver/rtc_io.h"
  21. #include "soc/soc.h"
  22. #include "esp_log.h"
  23. #include "soc/gpio_periph.h"
  24. #if !CONFIG_FREERTOS_UNICORE
  25. #include "esp_ipc.h"
  26. #endif
  27. #define GPIO_CHECK(a, str, ret_val) \
  28. if (!(a)) { \
  29. ESP_LOGE(GPIO_TAG,"%s(%d): %s", __FUNCTION__, __LINE__, str); \
  30. return (ret_val); \
  31. }
  32. #define GPIO_ISR_CORE_ID_UNINIT (3)
  33. typedef struct {
  34. gpio_isr_t fn; /*!< isr function */
  35. void* args; /*!< isr function args */
  36. } gpio_isr_func_t;
  37. // Used by the IPC call to register the interrupt service routine.
  38. typedef struct {
  39. int source; /*!< ISR source */
  40. int intr_alloc_flags; /*!< ISR alloc flag */
  41. void (*fn)(void*); /*!< ISR function */
  42. void *arg; /*!< ISR function args*/
  43. void *handle; /*!< ISR handle */
  44. esp_err_t ret;
  45. } gpio_isr_alloc_t;
  46. static const char* GPIO_TAG = "gpio";
  47. static gpio_isr_func_t* gpio_isr_func = NULL;
  48. static gpio_isr_handle_t gpio_isr_handle;
  49. static uint32_t isr_core_id = GPIO_ISR_CORE_ID_UNINIT;
  50. static portMUX_TYPE gpio_spinlock = portMUX_INITIALIZER_UNLOCKED;
  51. esp_err_t gpio_pullup_en(gpio_num_t gpio_num)
  52. {
  53. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  54. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  55. rtc_gpio_pullup_en(gpio_num);
  56. } else {
  57. REG_SET_BIT(GPIO_PIN_MUX_REG[gpio_num], FUN_PU);
  58. }
  59. return ESP_OK;
  60. }
  61. esp_err_t gpio_pullup_dis(gpio_num_t gpio_num)
  62. {
  63. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  64. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  65. rtc_gpio_pullup_dis(gpio_num);
  66. } else {
  67. REG_CLR_BIT(GPIO_PIN_MUX_REG[gpio_num], FUN_PU);
  68. }
  69. return ESP_OK;
  70. }
  71. esp_err_t gpio_pulldown_en(gpio_num_t gpio_num)
  72. {
  73. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  74. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  75. rtc_gpio_pulldown_en(gpio_num);
  76. } else {
  77. REG_SET_BIT(GPIO_PIN_MUX_REG[gpio_num], FUN_PD);
  78. }
  79. return ESP_OK;
  80. }
  81. esp_err_t gpio_pulldown_dis(gpio_num_t gpio_num)
  82. {
  83. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  84. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  85. rtc_gpio_pulldown_dis(gpio_num);
  86. } else {
  87. REG_CLR_BIT(GPIO_PIN_MUX_REG[gpio_num], FUN_PD);
  88. }
  89. return ESP_OK;
  90. }
  91. esp_err_t gpio_set_intr_type(gpio_num_t gpio_num, gpio_int_type_t intr_type)
  92. {
  93. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  94. GPIO_CHECK(intr_type < GPIO_INTR_MAX, "GPIO interrupt type error", ESP_ERR_INVALID_ARG);
  95. GPIO.pin[gpio_num].int_type = intr_type;
  96. return ESP_OK;
  97. }
  98. static void gpio_intr_status_clr(gpio_num_t gpio_num)
  99. {
  100. if (gpio_num < 32) {
  101. GPIO.status_w1tc = BIT(gpio_num);
  102. } else {
  103. GPIO.status1_w1tc.intr_st = BIT(gpio_num - 32);
  104. }
  105. }
  106. static esp_err_t gpio_intr_enable_on_core (gpio_num_t gpio_num, uint32_t core_id)
  107. {
  108. gpio_intr_status_clr(gpio_num);
  109. if (core_id == 0) {
  110. GPIO.pin[gpio_num].int_ena = GPIO_PRO_CPU_INTR_ENA; //enable pro cpu intr
  111. } else {
  112. GPIO.pin[gpio_num].int_ena = GPIO_APP_CPU_INTR_ENA; //enable pro cpu intr
  113. }
  114. return ESP_OK;
  115. }
  116. esp_err_t gpio_intr_enable(gpio_num_t gpio_num)
  117. {
  118. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  119. portENTER_CRITICAL(&gpio_spinlock);
  120. if(isr_core_id == GPIO_ISR_CORE_ID_UNINIT) {
  121. isr_core_id = xPortGetCoreID();
  122. }
  123. portEXIT_CRITICAL(&gpio_spinlock);
  124. return gpio_intr_enable_on_core (gpio_num, isr_core_id);
  125. }
  126. esp_err_t gpio_intr_disable(gpio_num_t gpio_num)
  127. {
  128. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  129. GPIO.pin[gpio_num].int_ena = 0; //disable GPIO intr
  130. gpio_intr_status_clr(gpio_num);
  131. return ESP_OK;
  132. }
  133. static esp_err_t gpio_output_disable(gpio_num_t gpio_num)
  134. {
  135. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  136. if (gpio_num < 32) {
  137. GPIO.enable_w1tc = (0x1 << gpio_num);
  138. } else {
  139. GPIO.enable1_w1tc.data = (0x1 << (gpio_num - 32));
  140. }
  141. // Ensure no other output signal is routed via GPIO matrix to this pin
  142. REG_WRITE(GPIO_FUNC0_OUT_SEL_CFG_REG + (gpio_num * 4),
  143. SIG_GPIO_OUT_IDX);
  144. return ESP_OK;
  145. }
  146. static esp_err_t gpio_output_enable(gpio_num_t gpio_num)
  147. {
  148. GPIO_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(gpio_num), "GPIO output gpio_num error", ESP_ERR_INVALID_ARG);
  149. if (gpio_num < 32) {
  150. GPIO.enable_w1ts = (0x1 << gpio_num);
  151. } else {
  152. GPIO.enable1_w1ts.data = (0x1 << (gpio_num - 32));
  153. }
  154. gpio_matrix_out(gpio_num, SIG_GPIO_OUT_IDX, false, false);
  155. return ESP_OK;
  156. }
  157. esp_err_t gpio_set_level(gpio_num_t gpio_num, uint32_t level)
  158. {
  159. GPIO_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(gpio_num), "GPIO output gpio_num error", ESP_ERR_INVALID_ARG);
  160. if (level) {
  161. if (gpio_num < 32) {
  162. GPIO.out_w1ts = (1 << gpio_num);
  163. } else {
  164. GPIO.out1_w1ts.data = (1 << (gpio_num - 32));
  165. }
  166. } else {
  167. if (gpio_num < 32) {
  168. GPIO.out_w1tc = (1 << gpio_num);
  169. } else {
  170. GPIO.out1_w1tc.data = (1 << (gpio_num - 32));
  171. }
  172. }
  173. return ESP_OK;
  174. }
  175. int gpio_get_level(gpio_num_t gpio_num)
  176. {
  177. if (gpio_num < 32) {
  178. return (GPIO.in >> gpio_num) & 0x1;
  179. } else {
  180. return (GPIO.in1.data >> (gpio_num - 32)) & 0x1;
  181. }
  182. }
  183. esp_err_t gpio_set_pull_mode(gpio_num_t gpio_num, gpio_pull_mode_t pull)
  184. {
  185. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  186. GPIO_CHECK(pull <= GPIO_FLOATING, "GPIO pull mode error", ESP_ERR_INVALID_ARG);
  187. esp_err_t ret = ESP_OK;
  188. switch (pull) {
  189. case GPIO_PULLUP_ONLY:
  190. gpio_pulldown_dis(gpio_num);
  191. gpio_pullup_en(gpio_num);
  192. break;
  193. case GPIO_PULLDOWN_ONLY:
  194. gpio_pulldown_en(gpio_num);
  195. gpio_pullup_dis(gpio_num);
  196. break;
  197. case GPIO_PULLUP_PULLDOWN:
  198. gpio_pulldown_en(gpio_num);
  199. gpio_pullup_en(gpio_num);
  200. break;
  201. case GPIO_FLOATING:
  202. gpio_pulldown_dis(gpio_num);
  203. gpio_pullup_dis(gpio_num);
  204. break;
  205. default:
  206. ESP_LOGE(GPIO_TAG, "Unknown pull up/down mode,gpio_num=%u,pull=%u", gpio_num, pull);
  207. ret = ESP_ERR_INVALID_ARG;
  208. break;
  209. }
  210. return ret;
  211. }
  212. esp_err_t gpio_set_direction(gpio_num_t gpio_num, gpio_mode_t mode)
  213. {
  214. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  215. if (gpio_num >= 34 && (mode & GPIO_MODE_DEF_OUTPUT)) {
  216. ESP_LOGE(GPIO_TAG, "io_num=%d can only be input", gpio_num);
  217. return ESP_ERR_INVALID_ARG;
  218. }
  219. esp_err_t ret = ESP_OK;
  220. if (mode & GPIO_MODE_DEF_INPUT) {
  221. PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[gpio_num]);
  222. } else {
  223. PIN_INPUT_DISABLE(GPIO_PIN_MUX_REG[gpio_num]);
  224. }
  225. if (mode & GPIO_MODE_DEF_OUTPUT) {
  226. gpio_output_enable(gpio_num);
  227. } else {
  228. gpio_output_disable(gpio_num);
  229. }
  230. if (mode & GPIO_MODE_DEF_OD) {
  231. GPIO.pin[gpio_num].pad_driver = 1;
  232. } else {
  233. GPIO.pin[gpio_num].pad_driver = 0;
  234. }
  235. return ret;
  236. }
  237. esp_err_t gpio_config(const gpio_config_t *pGPIOConfig)
  238. {
  239. uint64_t gpio_pin_mask = (pGPIOConfig->pin_bit_mask);
  240. uint32_t io_reg = 0;
  241. uint32_t io_num = 0;
  242. uint8_t input_en = 0;
  243. uint8_t output_en = 0;
  244. uint8_t od_en = 0;
  245. uint8_t pu_en = 0;
  246. uint8_t pd_en = 0;
  247. if (pGPIOConfig->pin_bit_mask == 0 || pGPIOConfig->pin_bit_mask >= (((uint64_t) 1) << GPIO_PIN_COUNT)) {
  248. ESP_LOGE(GPIO_TAG, "GPIO_PIN mask error ");
  249. return ESP_ERR_INVALID_ARG;
  250. }
  251. if ((pGPIOConfig->mode) & (GPIO_MODE_DEF_OUTPUT)) {
  252. //GPIO 34/35/36/37/38/39 can only be used as input mode;
  253. if ((gpio_pin_mask & ( GPIO_SEL_34 | GPIO_SEL_35 | GPIO_SEL_36 | GPIO_SEL_37 | GPIO_SEL_38 | GPIO_SEL_39))) {
  254. ESP_LOGE(GPIO_TAG, "GPIO34-39 can only be used as input mode");
  255. return ESP_ERR_INVALID_ARG;
  256. }
  257. }
  258. do {
  259. io_reg = GPIO_PIN_MUX_REG[io_num];
  260. if (((gpio_pin_mask >> io_num) & BIT(0))) {
  261. if (!io_reg) {
  262. ESP_LOGE(GPIO_TAG, "IO%d is not a valid GPIO",io_num);
  263. return ESP_ERR_INVALID_ARG;
  264. }
  265. if(RTC_GPIO_IS_VALID_GPIO(io_num)){
  266. rtc_gpio_deinit(io_num);
  267. }
  268. if ((pGPIOConfig->mode) & GPIO_MODE_DEF_INPUT) {
  269. input_en = 1;
  270. PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[io_num]);
  271. } else {
  272. PIN_INPUT_DISABLE(GPIO_PIN_MUX_REG[io_num]);
  273. }
  274. if ((pGPIOConfig->mode) & GPIO_MODE_DEF_OD) {
  275. od_en = 1;
  276. GPIO.pin[io_num].pad_driver = 1; /*0x01 Open-drain */
  277. } else {
  278. GPIO.pin[io_num].pad_driver = 0; /*0x00 Normal gpio output */
  279. }
  280. if ((pGPIOConfig->mode) & GPIO_MODE_DEF_OUTPUT) {
  281. output_en = 1;
  282. gpio_output_enable(io_num);
  283. } else {
  284. gpio_output_disable(io_num);
  285. }
  286. if (pGPIOConfig->pull_up_en) {
  287. pu_en = 1;
  288. gpio_pullup_en(io_num);
  289. } else {
  290. gpio_pullup_dis(io_num);
  291. }
  292. if (pGPIOConfig->pull_down_en) {
  293. pd_en = 1;
  294. gpio_pulldown_en(io_num);
  295. } else {
  296. gpio_pulldown_dis(io_num);
  297. }
  298. ESP_LOGI(GPIO_TAG, "GPIO[%d]| InputEn: %d| OutputEn: %d| OpenDrain: %d| Pullup: %d| Pulldown: %d| Intr:%d ", io_num, input_en, output_en, od_en, pu_en, pd_en, pGPIOConfig->intr_type);
  299. gpio_set_intr_type(io_num, pGPIOConfig->intr_type);
  300. if (pGPIOConfig->intr_type) {
  301. gpio_intr_enable(io_num);
  302. } else {
  303. gpio_intr_disable(io_num);
  304. }
  305. PIN_FUNC_SELECT(io_reg, PIN_FUNC_GPIO); /*function number 2 is GPIO_FUNC for each pin */
  306. }
  307. io_num++;
  308. } while (io_num < GPIO_PIN_COUNT);
  309. return ESP_OK;
  310. }
  311. esp_err_t gpio_reset_pin(gpio_num_t gpio_num)
  312. {
  313. assert(gpio_num >= 0 && GPIO_IS_VALID_GPIO(gpio_num));
  314. gpio_config_t cfg = {
  315. .pin_bit_mask = BIT64(gpio_num),
  316. .mode = GPIO_MODE_DISABLE,
  317. //for powersave reasons, the GPIO should not be floating, select pullup
  318. .pull_up_en = true,
  319. .pull_down_en = false,
  320. .intr_type = GPIO_INTR_DISABLE,
  321. };
  322. gpio_config(&cfg);
  323. return ESP_OK;
  324. }
  325. void IRAM_ATTR gpio_intr_service(void* arg)
  326. {
  327. //GPIO intr process
  328. uint32_t gpio_num = 0;
  329. //read status to get interrupt status for GPIO0-31
  330. const uint32_t gpio_intr_status = (isr_core_id == 0) ? GPIO.pcpu_int : GPIO.acpu_int;
  331. //read status1 to get interrupt status for GPIO32-39
  332. const uint32_t gpio_intr_status_h = (isr_core_id == 0) ? GPIO.pcpu_int1.intr : GPIO.acpu_int1.intr;
  333. if (gpio_isr_func == NULL) {
  334. return;
  335. }
  336. do {
  337. if (gpio_num < 32) {
  338. if (gpio_intr_status & BIT(gpio_num)) { //gpio0-gpio31
  339. if (gpio_isr_func[gpio_num].fn != NULL) {
  340. gpio_isr_func[gpio_num].fn(gpio_isr_func[gpio_num].args);
  341. }
  342. GPIO.status_w1tc = BIT(gpio_num);
  343. }
  344. } else {
  345. if (gpio_intr_status_h & BIT(gpio_num - 32)) {
  346. if (gpio_isr_func[gpio_num].fn != NULL) {
  347. gpio_isr_func[gpio_num].fn(gpio_isr_func[gpio_num].args);
  348. }
  349. GPIO.status1_w1tc.intr_st = BIT(gpio_num - 32);
  350. }
  351. }
  352. } while (++gpio_num < GPIO_PIN_COUNT);
  353. }
  354. esp_err_t gpio_isr_handler_add(gpio_num_t gpio_num, gpio_isr_t isr_handler, void* args)
  355. {
  356. GPIO_CHECK(gpio_isr_func != NULL, "GPIO isr service is not installed, call gpio_install_isr_service() first", ESP_ERR_INVALID_STATE);
  357. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  358. portENTER_CRITICAL(&gpio_spinlock);
  359. gpio_intr_disable(gpio_num);
  360. if (gpio_isr_func) {
  361. gpio_isr_func[gpio_num].fn = isr_handler;
  362. gpio_isr_func[gpio_num].args = args;
  363. }
  364. gpio_intr_enable_on_core (gpio_num, esp_intr_get_cpu(gpio_isr_handle));
  365. portEXIT_CRITICAL(&gpio_spinlock);
  366. return ESP_OK;
  367. }
  368. esp_err_t gpio_isr_handler_remove(gpio_num_t gpio_num)
  369. {
  370. GPIO_CHECK(gpio_isr_func != NULL, "GPIO isr service is not installed, call gpio_install_isr_service() first", ESP_ERR_INVALID_STATE);
  371. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  372. portENTER_CRITICAL(&gpio_spinlock);
  373. gpio_intr_disable(gpio_num);
  374. if (gpio_isr_func) {
  375. gpio_isr_func[gpio_num].fn = NULL;
  376. gpio_isr_func[gpio_num].args = NULL;
  377. }
  378. portEXIT_CRITICAL(&gpio_spinlock);
  379. return ESP_OK;
  380. }
  381. esp_err_t gpio_install_isr_service(int intr_alloc_flags)
  382. {
  383. GPIO_CHECK(gpio_isr_func == NULL, "GPIO isr service already installed", ESP_ERR_INVALID_STATE);
  384. esp_err_t ret;
  385. portENTER_CRITICAL(&gpio_spinlock);
  386. gpio_isr_func = (gpio_isr_func_t*) calloc(GPIO_NUM_MAX, sizeof(gpio_isr_func_t));
  387. portEXIT_CRITICAL(&gpio_spinlock);
  388. if (gpio_isr_func == NULL) {
  389. ret = ESP_ERR_NO_MEM;
  390. } else {
  391. ret = gpio_isr_register(gpio_intr_service, NULL, intr_alloc_flags, &gpio_isr_handle);
  392. }
  393. return ret;
  394. }
  395. void gpio_uninstall_isr_service()
  396. {
  397. if (gpio_isr_func == NULL) {
  398. return;
  399. }
  400. portENTER_CRITICAL(&gpio_spinlock);
  401. esp_intr_free(gpio_isr_handle);
  402. free(gpio_isr_func);
  403. gpio_isr_func = NULL;
  404. isr_core_id = GPIO_ISR_CORE_ID_UNINIT;
  405. portEXIT_CRITICAL(&gpio_spinlock);
  406. return;
  407. }
  408. static void gpio_isr_register_on_core_static(void *param)
  409. {
  410. gpio_isr_alloc_t *p = (gpio_isr_alloc_t *)param;
  411. //We need to check the return value.
  412. p->ret = esp_intr_alloc(p->source, p->intr_alloc_flags, p->fn, p->arg, p->handle);
  413. }
  414. esp_err_t gpio_isr_register(void (*fn)(void*), void * arg, int intr_alloc_flags, gpio_isr_handle_t *handle)
  415. {
  416. GPIO_CHECK(fn, "GPIO ISR null", ESP_ERR_INVALID_ARG);
  417. gpio_isr_alloc_t p;
  418. p.source = ETS_GPIO_INTR_SOURCE;
  419. p.intr_alloc_flags = intr_alloc_flags;
  420. p.fn = fn;
  421. p.arg = arg;
  422. p.handle = handle;
  423. portENTER_CRITICAL(&gpio_spinlock);
  424. if(isr_core_id == GPIO_ISR_CORE_ID_UNINIT) {
  425. isr_core_id = xPortGetCoreID();
  426. }
  427. portEXIT_CRITICAL(&gpio_spinlock);
  428. esp_err_t ret;
  429. #if CONFIG_FREERTOS_UNICORE
  430. gpio_isr_register_on_core_static(&p);
  431. ret = ESP_OK;
  432. #else /* CONFIG_FREERTOS_UNICORE */
  433. ret = esp_ipc_call_blocking(isr_core_id, gpio_isr_register_on_core_static, (void *)&p);
  434. #endif /* !CONFIG_FREERTOS_UNICORE */
  435. if(ret != ESP_OK || p.ret != ESP_OK) {
  436. return ESP_ERR_NOT_FOUND;
  437. }
  438. return ESP_OK;
  439. }
  440. esp_err_t gpio_wakeup_enable(gpio_num_t gpio_num, gpio_int_type_t intr_type)
  441. {
  442. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  443. esp_err_t ret = ESP_OK;
  444. if (( intr_type == GPIO_INTR_LOW_LEVEL ) || ( intr_type == GPIO_INTR_HIGH_LEVEL )) {
  445. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  446. ret = rtc_gpio_wakeup_enable(gpio_num, intr_type);
  447. } else {
  448. GPIO.pin[gpio_num].int_type = intr_type;
  449. GPIO.pin[gpio_num].wakeup_enable = 0x1;
  450. }
  451. } else {
  452. ESP_LOGE(GPIO_TAG, "GPIO wakeup only supports level mode, but edge mode set. gpio_num:%u", gpio_num);
  453. ret = ESP_ERR_INVALID_ARG;
  454. }
  455. return ret;
  456. }
  457. esp_err_t gpio_wakeup_disable(gpio_num_t gpio_num)
  458. {
  459. GPIO_CHECK(GPIO_IS_VALID_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  460. esp_err_t ret = ESP_OK;
  461. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  462. ret = rtc_gpio_wakeup_disable(gpio_num);
  463. } else {
  464. GPIO.pin[gpio_num].wakeup_enable = 0;
  465. }
  466. return ret;
  467. }
  468. esp_err_t gpio_set_drive_capability(gpio_num_t gpio_num, gpio_drive_cap_t strength)
  469. {
  470. GPIO_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  471. GPIO_CHECK(strength < GPIO_DRIVE_CAP_MAX, "GPIO drive capability error", ESP_ERR_INVALID_ARG);
  472. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  473. rtc_gpio_set_drive_capability(gpio_num, strength);
  474. } else {
  475. SET_PERI_REG_BITS(GPIO_PIN_MUX_REG[gpio_num], FUN_DRV_V, strength, FUN_DRV_S);
  476. }
  477. return ESP_OK;
  478. }
  479. esp_err_t gpio_get_drive_capability(gpio_num_t gpio_num, gpio_drive_cap_t* strength)
  480. {
  481. GPIO_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(gpio_num), "GPIO number error", ESP_ERR_INVALID_ARG);
  482. GPIO_CHECK(strength != NULL, "GPIO drive capability pointer error", ESP_ERR_INVALID_ARG);
  483. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  484. return rtc_gpio_get_drive_capability(gpio_num, strength);
  485. } else {
  486. *strength = GET_PERI_REG_BITS2(GPIO_PIN_MUX_REG[gpio_num], FUN_DRV_V, FUN_DRV_S);
  487. }
  488. return ESP_OK;
  489. }
  490. static const uint32_t GPIO_HOLD_MASK[34] = {
  491. 0,
  492. GPIO_SEL_1,
  493. 0,
  494. GPIO_SEL_0,
  495. 0,
  496. GPIO_SEL_8,
  497. GPIO_SEL_2,
  498. GPIO_SEL_3,
  499. GPIO_SEL_4,
  500. GPIO_SEL_5,
  501. GPIO_SEL_6,
  502. GPIO_SEL_7,
  503. 0,
  504. 0,
  505. 0,
  506. 0,
  507. GPIO_SEL_9,
  508. GPIO_SEL_10,
  509. GPIO_SEL_11,
  510. GPIO_SEL_12,
  511. 0,
  512. GPIO_SEL_14,
  513. GPIO_SEL_15,
  514. GPIO_SEL_16,
  515. 0,
  516. 0,
  517. 0,
  518. 0,
  519. 0,
  520. 0,
  521. 0,
  522. 0,
  523. 0,
  524. 0,
  525. };
  526. esp_err_t gpio_hold_en(gpio_num_t gpio_num)
  527. {
  528. GPIO_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(gpio_num), "Only output-capable GPIO support this function", ESP_ERR_NOT_SUPPORTED);
  529. esp_err_t r = ESP_OK;
  530. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  531. r = rtc_gpio_hold_en(gpio_num);
  532. } else if (GPIO_HOLD_MASK[gpio_num]) {
  533. SET_PERI_REG_MASK(RTC_IO_DIG_PAD_HOLD_REG, GPIO_HOLD_MASK[gpio_num]);
  534. } else {
  535. r = ESP_ERR_NOT_SUPPORTED;
  536. }
  537. return r == ESP_OK ? ESP_OK : ESP_ERR_NOT_SUPPORTED;
  538. }
  539. esp_err_t gpio_hold_dis(gpio_num_t gpio_num)
  540. {
  541. GPIO_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(gpio_num), "Only output-capable GPIO support this function", ESP_ERR_NOT_SUPPORTED);
  542. esp_err_t r = ESP_OK;
  543. if (RTC_GPIO_IS_VALID_GPIO(gpio_num)) {
  544. r = rtc_gpio_hold_dis(gpio_num);
  545. } else if (GPIO_HOLD_MASK[gpio_num]) {
  546. CLEAR_PERI_REG_MASK(RTC_IO_DIG_PAD_HOLD_REG, GPIO_HOLD_MASK[gpio_num]);
  547. } else {
  548. r = ESP_ERR_NOT_SUPPORTED;
  549. }
  550. return r == ESP_OK ? ESP_OK : ESP_ERR_NOT_SUPPORTED;
  551. }
  552. void gpio_deep_sleep_hold_en(void)
  553. {
  554. portENTER_CRITICAL(&gpio_spinlock);
  555. SET_PERI_REG_MASK(RTC_CNTL_DIG_ISO_REG, RTC_CNTL_DG_PAD_AUTOHOLD_EN_M);
  556. portEXIT_CRITICAL(&gpio_spinlock);
  557. }
  558. void gpio_deep_sleep_hold_dis(void)
  559. {
  560. portENTER_CRITICAL(&gpio_spinlock);
  561. CLEAR_PERI_REG_MASK(RTC_CNTL_DIG_ISO_REG, RTC_CNTL_DG_PAD_AUTOHOLD_EN_M);
  562. portEXIT_CRITICAL(&gpio_spinlock);
  563. }
  564. void gpio_iomux_in(uint32_t gpio, uint32_t signal_idx)
  565. {
  566. GPIO.func_in_sel_cfg[signal_idx].sig_in_sel = 0;
  567. PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[gpio]);
  568. }
  569. void gpio_iomux_out(uint8_t gpio_num, int func, bool oen_inv)
  570. {
  571. GPIO.func_out_sel_cfg[gpio_num].oen_sel = 0;
  572. GPIO.func_out_sel_cfg[gpio_num].oen_inv_sel = oen_inv;
  573. PIN_FUNC_SELECT(GPIO_PIN_MUX_REG[gpio_num], func);
  574. }