gpio.c 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952
  1. /******************************************************************************
  2. 版权所有:
  3. 文件名称: gpio.c
  4. 文件版本: 01.01
  5. 创建作者: zhaoyang
  6. 创建日期: 2023-12-14
  7. 功能说明: gpio驱动程序。
  8. 其它说明:
  9. 修改记录:
  10. [new]-->applay
  11. B_DO_ADJ --> GPIOD_17 --> gpio113
  12. B_DO_0 --> GPIOD_03 --> gpio99
  13. B_DO_1 --> GPIOD_19 --> gpio115
  14. B_DO_2 --> GPIOD_02 --> gpio98
  15. B_DO_3 --> GPIOD_09 --> gpio105
  16. B_DO_4 --> GPIOD_18 --> gpio114
  17. B_DO_5 --> GPIOD_16 --> gpio112
  18. B_DO_6 --> GPIOD_07 --> gpio103
  19. B_DO_7 --> GPIOD_08 --> gpio104
  20. B_DO_8 --> GPIOD_06 --> gpio102
  21. T536 start ↓↓↓↓↓↓
  22. RUN_LED --> PB7 --> gpio39
  23. ERR_LED --> PF4 --> gpio164
  24. ESAM_PWR --> PL7 --> gpio159
  25. LINE_LOSS_SET --> PM5 --> gpio389
  26. T536 end ↑↑↑↑↑↑
  27. */
  28. /*------------------------------- 头文件 --------------------------------------
  29. */
  30. #include "bspconfig.h"
  31. #include "gpio.h"
  32. #include "head.h"
  33. #include <rtdm/gpio.h>
  34. /*------------------------------- 宏定义 --------------------------------------
  35. */
  36. #if CFG_BSP_DEBUG
  37. #define _GPIO_DEBUG
  38. #endif
  39. /*------------------------------ 全局变量 -------------------------------------
  40. */
  41. typedef enum {
  42. SYS_GPIO = 0,
  43. RTDM_GPIO = 1,
  44. } GPIO_TYPE;
  45. unsigned short kc_pwm0_stu;
  46. unsigned short kc_pwm1_stu;
  47. unsigned short kc_kout0_stu;
  48. unsigned short kc_kout1_stu;
  49. extern uint32_t g_yx_buf[2]; //预留64个遥信
  50. /*------------------------------ 函数声明 -------------------------------------
  51. */
  52. extern unsigned int change_di_ch(unsigned int di);
  53. int gpio_val_fd[DO_NUM];
  54. int gpio_dev_type[DO_NUM] = {SYS_GPIO,}; //0:系统GPIO, 1:RTDM GPIO
  55. const int gpio_val[DO_NUM] = {98, 99, 115, 98, 105, 114, 112, 103, 104, 102};
  56. int gpio_val_fd_other[GPIO_NUM_OTHER];
  57. int gpio_dev_type_other[GPIO_NUM_OTHER] = {SYS_GPIO,};
  58. const int gpio_val_other[GPIO_NUM_OTHER] ={39,164,359,389};
  59. // static int gpio_watchdog_val = 0;
  60. static int gpio_run_led_val = 0;
  61. /*------------------------------ 外部函数 -------------------------------------
  62. */
  63. #if 1
  64. int sysfs_gpio_unexport(int gpio)
  65. {
  66. char path[64];
  67. int fd;
  68. snprintf(path, sizeof(path), "/sys/class/gpio/unexport");
  69. fd = open(path, O_WRONLY);
  70. if (fd < 0) {
  71. perror("Failed to open unexport");
  72. return -1;
  73. }
  74. char buf[16];
  75. snprintf(buf, sizeof(buf), "%d", gpio);
  76. if (write(fd, buf, strlen(buf)) < 0) {
  77. perror("Failed to set GPIO");
  78. close(fd);
  79. return -1;
  80. }
  81. close(fd);
  82. return 0;
  83. }
  84. int sysfs_gpio_export(int gpio) {
  85. char path[64];
  86. int fd;
  87. // 检查是否已导出
  88. snprintf(path, sizeof(path), "/sys/class/gpio/gpio%d", gpio);
  89. if (access(path, F_OK) == 0) {
  90. sysfs_gpio_unexport(gpio); // bugfix: 避免重复导出
  91. msleep(50); //短暂等待让内核处理
  92. }
  93. snprintf(path, sizeof(path), "/sys/class/gpio/export");
  94. fd = open(path, O_WRONLY);
  95. if (fd < 0) {
  96. perror("Failed to open export");
  97. return -1;
  98. }
  99. char buf[16];
  100. snprintf(buf, sizeof(buf), "%d", gpio);
  101. if (write(fd, buf, strlen(buf)) < 0) {
  102. perror("Failed to export GPIO");
  103. close(fd);
  104. return -1;
  105. }
  106. close(fd);
  107. return 0;
  108. }
  109. int sysfs_gpio_set_direction(int gpio, int is_output) {
  110. char path[64];
  111. int fd;
  112. snprintf(path, sizeof(path), "/sys/class/gpio/gpio%d/direction", gpio);
  113. fd = open(path, O_WRONLY);
  114. if (fd < 0) {
  115. perror("Failed to open direction");
  116. return -1;
  117. }
  118. if (write(fd, is_output ? "out" : "in", is_output ? 3 : 2) < 0) {
  119. perror("Failed to set direction");
  120. close(fd);
  121. return -1;
  122. }
  123. close(fd);
  124. return 0;
  125. }
  126. int sysfs_gpio_set_edge_detect(int gpio, int edge)
  127. {
  128. char path[64];
  129. int fd;
  130. snprintf(path, sizeof(path), "/sys/class/gpio/gpio%d/edge", gpio);
  131. fd = open(path, O_WRONLY);
  132. if (fd < 0) {
  133. perror("Failed to open edge");
  134. close(fd);
  135. return -1;
  136. }
  137. if (write(fd, edge, strlen(edge)) < 0) {
  138. perror("Failed to set edge");
  139. close(fd);
  140. return -1;
  141. }
  142. close(fd);
  143. return 0;
  144. }
  145. int sysfs_gpio_set_value(int gpio, int value) {
  146. char path[64];
  147. int fd = -1;
  148. snprintf(path, sizeof(path), "/sys/class/gpio/gpio%d/value", gpio);
  149. fd = open(path, O_WRONLY);
  150. if (fd < 0) {
  151. perror("Failed to open value");
  152. return -1;
  153. }
  154. if (write(fd, value ? "1" : "0", 1) < 0) {
  155. perror("Failed to set value");
  156. close(fd);
  157. return -1;
  158. }
  159. return fd;
  160. }
  161. int sysfs_gpio_init(int gpio, int direction)
  162. {
  163. #define GPIO_LOW 0
  164. int ret;
  165. ret = sysfs_gpio_export(gpio);
  166. if(ret < 0)
  167. {
  168. printf("sysfs_gpio_export error\n");
  169. return -1;
  170. }
  171. ret = sysfs_gpio_set_direction(gpio, direction);
  172. if(ret < 0)
  173. {
  174. printf("sysfs_gpio_set_direction error\n");
  175. }
  176. return sysfs_gpio_set_value(gpio, GPIO_LOW); // 初始化IO为低电平
  177. }
  178. int is_rtdm_device(int fd) {
  179. if(gpio_dev_type[fd] > SYS_GPIO)
  180. return 1;
  181. else
  182. if(gpio_dev_type[fd] == SYS_GPIO)
  183. return 0;
  184. else
  185. return -1;
  186. }
  187. int rt_write(int fd, char *buf, int len) {
  188. int value;
  189. if(len <= 0 || buf == NULL) {
  190. return -1;
  191. }
  192. if (is_rtdm_device(fd) == 1) {
  193. // Xenomai RTDM设备:需要转换为二进制值
  194. value = atoi(buf);
  195. if(value != 0 && value != 1) {
  196. printf("value :%d ERR, Please enter '0' or '1'\n", value);
  197. return -1;
  198. }
  199. return write(fd, &value, sizeof(value));
  200. }
  201. else
  202. {
  203. // 常规系统设备:直接传递字符串
  204. return write(fd, buf, len);
  205. }
  206. }
  207. int rtdm_gpio_init(int gpio, int direction)
  208. {
  209. #define GPIO_LOW 0
  210. char path[64];
  211. int fd = -1, ret;
  212. int value = 1;
  213. snprintf(path, sizeof(path), "/dev/rtdm/3604000.pinctrl/gpio%d", gpio);
  214. fd = open(path, O_RDWR);
  215. if (fd < 0) {
  216. perror("open");
  217. return -1;
  218. }
  219. ret = ioctl(fd, GPIO_RTIOC_DIR_OUT, &value);
  220. if (ret < 0) {
  221. perror("ioctl DIR_OUT");
  222. close(fd);
  223. return -1;
  224. }
  225. rt_write(gpio_val_fd[DO_OUT0], "0", 2); // 初始化IO为低电平
  226. return fd;
  227. }
  228. int gpio_init(void)
  229. {
  230. #define GPIO_OUTPUT 1
  231. int i;
  232. #ifdef NW_AREA_MAIN_2021
  233. for (i = 0; i < DO_NUM; i ++)
  234. {
  235. gpio_val_fd[i] = rtdm_gpio_init(gpio_val[i], GPIO_OUTPUT);
  236. if(gpio_val_fd[i] < 0)
  237. {
  238. gpio_val_fd[i] = sysfs_gpio_init(gpio_val[i], GPIO_OUTPUT);
  239. if(gpio_val_fd[i] < 0)
  240. {
  241. printf("gpio_val_fd[%d] error\n", i);
  242. gpio_val_fd[i] = -1;
  243. gpio_dev_type[i] = -1;
  244. return -1;
  245. }
  246. }
  247. else {
  248. gpio_dev_type[i] = gpio_val_fd[i]; // 保存RTDM设备类型句柄,这里有风险,fd句柄可能为0
  249. }
  250. }
  251. #endif
  252. for (i = 0; i < GPIO_NUM_OTHER; i ++)
  253. {
  254. gpio_val_fd_other[i] = -1; //rtdm_gpio_init(gpio_val_other[i], GPIO_OUTPUT);
  255. if(gpio_val_fd_other[i] < 0)
  256. {
  257. gpio_val_fd_other[i] = sysfs_gpio_init(gpio_val_other[i], GPIO_OUTPUT);
  258. if(gpio_val_fd_other[i] < 0)
  259. {
  260. printf("gpio_val_fd_other[%d] error\n", i);
  261. gpio_val_fd_other[i] = -1;
  262. gpio_dev_type_other[i] = -1;
  263. return -1;
  264. }
  265. }
  266. else {
  267. gpio_dev_type_other[i] = gpio_val_fd_other[i]; // 保存RTDM设备类型句柄,这里有风险,fd句柄可能为0
  268. }
  269. }
  270. msleep(10);// 延时10ms
  271. kc_pwm0_stu = 0;
  272. kc_pwm1_stu = 0;
  273. kc_kout0_stu=0;
  274. kc_kout1_stu=0;
  275. //其他与底层GPIO相关的配置再此处添加 比如 LED WATCHDOG
  276. write(gpio_val_fd_other[ERR_LED], "0", 2);
  277. write(gpio_val_fd_other[RUN_LED], "0", 2);
  278. gpio_run_led_val = 0;
  279. //上电默认切换到外部232串口
  280. //后续根据投退判断是否需要切换到线损的维护口
  281. write(gpio_val_fd_other[LINE_LOSS_SET], "0", 2);
  282. //开启esam供电
  283. write(gpio_val_fd_other[ESAM_PWR], "0", 2);
  284. #ifdef NW_AREA_MAIN_2021
  285. for (i = 0; i < DO_NUM; i ++)
  286. {
  287. write(gpio_val_fd[i], "1", 2);
  288. }
  289. #endif
  290. return 0;
  291. }
  292. int gpio_exit(void)
  293. {
  294. int i;
  295. #ifdef NW_AREA_MAIN_2021
  296. for (i = 0; i < DO_NUM; i ++)
  297. {
  298. if(gpio_val_fd[i] >= 0)
  299. {
  300. close(gpio_val_fd[i]);
  301. gpio_val_fd[i] = -1;
  302. }
  303. sysfs_gpio_unexport(gpio_val[i]);
  304. }
  305. #endif
  306. for (i = 0; i < GPIO_NUM_OTHER; i ++)
  307. {
  308. if(gpio_val_fd_other[i] >= 0)
  309. {
  310. close(gpio_val_fd_other[i]);
  311. gpio_val_fd_other[i] = -1;
  312. }
  313. sysfs_gpio_unexport(gpio_val_other[i]);
  314. }
  315. return 0;
  316. }
  317. #else
  318. /******************************************************************************
  319. 函数名称: gpio_init
  320. 函数版本: 01.01
  321. 创建作者: sunxi
  322. 创建日期: 2008-06-26
  323. 函数说明: gpio初始化。
  324. 参数说明: 无
  325. 返回值: 成功返回0.
  326. 修改记录:
  327. */
  328. int gpio_init(void)
  329. {
  330. int i, j;
  331. int exportfd, directionfd;
  332. char num[10];
  333. char path[50] = "";
  334. //do
  335. exportfd = open("/sys/class/gpio/export", O_WRONLY);
  336. if (exportfd < 0)
  337. {
  338. printf("Cannot open GPIO to export it\n");
  339. return -1;
  340. }
  341. #ifdef NW_AREA_MAIN_2021
  342. for (i = 0; i < DO_NUM; i ++)
  343. {
  344. sprintf(num, "%d", gpio_val[i]);
  345. write(exportfd, num, 4);
  346. gpio_val_fd[i] = -1;
  347. }
  348. #endif
  349. for (i = 0; i < GPIO_NUM_OTHER; i ++)
  350. {
  351. sprintf(num, "%d", gpio_val_other[i]);
  352. write(exportfd, num, 4);
  353. gpio_val_fd_other[i] = -1;
  354. }
  355. close(exportfd);
  356. #ifdef NW_AREA_MAIN_2021
  357. for (i = 0; i < DO_NUM; i ++)
  358. {
  359. sprintf(path, "/sys/class/gpio/gpio%d/value", gpio_val[i]);
  360. gpio_val_fd[i] = open(path, O_RDWR);
  361. if (gpio_val_fd[i] < 0)
  362. {
  363. printf("Cannot open GPIO%d value!\n", gpio_val[i]);
  364. for(j = 0; j < i; j ++)
  365. {
  366. close(gpio_val_fd[j]);
  367. gpio_val_fd[j] = -1;
  368. }
  369. return -4;
  370. }
  371. }
  372. // Update the direction of the GPIO to be an output
  373. for (i = 0; i < DO_NUM; i ++)
  374. {
  375. sprintf(path, "/sys/class/gpio/gpio%d/direction", gpio_val[i]);
  376. directionfd = open(path, O_RDWR);
  377. if (directionfd < 0)
  378. {
  379. printf("Cannot open GPIO%d direction!\n", gpio_val[i]);
  380. return -2;
  381. }
  382. write(directionfd, "out", 4);
  383. write(gpio_val_fd[i], "1", 2);
  384. close(directionfd);
  385. }
  386. #endif
  387. msleep(10);// 延时10ms
  388. for (i = 0; i < GPIO_NUM_OTHER; i ++)
  389. {
  390. sprintf(path, "/sys/class/gpio/gpio%d/value", gpio_val_other[i]);
  391. gpio_val_fd_other[i] = open(path, O_RDWR);
  392. if (gpio_val_fd_other[i] < 0)
  393. {
  394. printf("Cannot open GPIO%d value!\n", gpio_val_other[i]);
  395. for(j = 0; j < i; j ++)
  396. {
  397. close(gpio_val_fd_other[j]);
  398. gpio_val_fd_other[j] = -1;
  399. }
  400. #ifdef NW_AREA_MAIN_2021
  401. for(j = 0; j < DO_NUM; j ++)
  402. {
  403. close(gpio_val_fd[j]);
  404. gpio_val_fd[j] = -1;
  405. }
  406. #endif
  407. return -5;
  408. }
  409. }
  410. for (i = 0; i < GPIO_NUM_OTHER; i ++)
  411. {
  412. sprintf(path, "/sys/class/gpio/gpio%d/direction", gpio_val_other[i]);
  413. directionfd = open(path, O_RDWR);
  414. if (directionfd < 0)
  415. {
  416. printf("Cannot open GPIO%d direction!\n", gpio_val_other[i]);
  417. return -3;
  418. }
  419. write(directionfd, "out", 4);
  420. close(directionfd);
  421. }
  422. kc_pwm0_stu = 0;
  423. kc_pwm1_stu = 0;
  424. kc_kout0_stu=0;
  425. kc_kout1_stu=0;
  426. //其他与底层GPIO相关的配置再此处添加 比如 LED WATCHDOG jack.liu 202009010
  427. // write(gpio_val_fd_other[WATCHDOG], "0", 2);//TODO: 需根据实际硬件重新对应匹配
  428. // gpio_watchdog_val = 0;
  429. write(gpio_val_fd_other[RUN_LED], "0", 2);
  430. gpio_run_led_val = 0;
  431. //上电默认切换到外部232串口
  432. //后续根据投退判断是否需要切换到线损的维护口
  433. write(gpio_val_fd_other[LINE_LOSS_SET], "0", 2);
  434. //首次上电,开出合闸,会导致第六路也开出,需要初始化关闭
  435. // write(gpio_val_fd[DO_OUT1], "1", 2);
  436. //开启esam供电
  437. write(gpio_val_fd_other[ESAM_PWR], "0", 2);
  438. #ifdef NW_AREA_MAIN_2021
  439. for (i = 0; i < DO_NUM; i ++)
  440. {
  441. write(gpio_val_fd[i], "1", 2);
  442. }
  443. #endif
  444. return 0;
  445. }
  446. int gpio_exit(void)
  447. {
  448. int i;
  449. int unexportfd;
  450. char num[10];
  451. unexportfd = open("/sys/class/gpio/unexport", O_WRONLY);
  452. if (unexportfd < 0)
  453. {
  454. printf("Cannot open GPIO to unexport it\n");
  455. return -1;
  456. }
  457. #ifdef NW_AREA_MAIN_2021
  458. for (i = 0; i < DO_NUM; i ++)
  459. {
  460. if(gpio_val_fd[i] >= 0)
  461. {
  462. close(gpio_val_fd[i]);
  463. gpio_val_fd[i] = -1;
  464. }
  465. sprintf(num, "%d", gpio_val[i]);
  466. write(unexportfd, num, 4);
  467. }
  468. #endif
  469. for (i = 0; i < GPIO_NUM_OTHER; i ++)
  470. {
  471. if(gpio_val_fd_other[i] >= 0)
  472. {
  473. close(gpio_val_fd_other[i]);
  474. gpio_val_fd_other[i] = -1;
  475. }
  476. sprintf(num, "%d", gpio_val_other[i]);
  477. write(unexportfd, num, 4);
  478. }
  479. close(unexportfd);
  480. return 0;
  481. }
  482. #endif
  483. /******************************************************************************
  484. 函数名称: gpio_get_kin
  485. 函数版本: 01.01
  486. 创建作者: sunxi
  487. 创建日期: 2008-09-16
  488. 函数说明: 得到开入的状态。
  489. 参数说明: 无
  490. 返回值: 返回开入的状态,每个bit代表一个开入量。
  491. 修改记录:
  492. */
  493. unsigned int gpio_get_kin(unsigned int addr)
  494. {
  495. register unsigned int dw;
  496. unsigned int value[3];
  497. value[0] = *(volatile unsigned int *)addr;
  498. value[1] = *(volatile unsigned int *)addr;
  499. value[2] = *(volatile unsigned int *)addr;
  500. dw = (value[0] & value[1]) | (value[0] & value[2]) | (value[1] & value[2]);
  501. return dw;
  502. }
  503. /******************************************************************************
  504. 函数名称: gpio_get_di
  505. 函数版本: 01.01
  506. 创建作者:
  507. 创建日期: 2014-11-28
  508. 函数说明: 得到开入的状态
  509. 参数说明: 无
  510. 返回值: 返回开入的状态,每个bit代表一个开入量。
  511. 修改记录:
  512. */
  513. unsigned int gpio_get_di(void)
  514. {
  515. return 0;
  516. #ifndef GW_AREA_MAIN_2021
  517. unsigned int dw = 0;
  518. dw = g_yx_buf[0];//这里保存的是共享内存的yx值,156us更新一次
  519. return change_di_ch(~dw);//取反---因为没有短接时,值为1. 所以要取反为0才行
  520. #endif
  521. }
  522. /******************************************************************************
  523. 函数名称: gpio_di_fj
  524. 函数版本: 01.01
  525. 创建作者:
  526. 创建日期: 2014-11-28
  527. 函数说明: 读取开出返校遥信值,控制板遥信为YX17~YX18
  528. YX17:选择, YX18:执行
  529. 参数说明: 无
  530. 返回值: 返回遥信值
  531. 修改记录:
  532. */
  533. #ifdef DO_KOUT_CHECK
  534. unsigned short gpio_di_fj(unsigned char index)//(void)
  535. #else
  536. unsigned short gpio_di_fj(void)
  537. #endif
  538. {
  539. unsigned int di=0;
  540. unsigned short ret=0;
  541. di = gpio_get_di();
  542. #ifdef DO_KOUT_CHECK
  543. //V4-20;
  544. //ret = (unsigned short)((di >>19) & 0x0001);
  545. ret = (unsigned short)((di >>index) & 0x0001);
  546. #else
  547. ret = (unsigned short)((di >> 23) & 0x0001);//dtu
  548. #endif
  549. return ret;
  550. }
  551. static void gpio_kouten_do(int on, unsigned int kouten)
  552. {
  553. // if (kouten > KOUT_EN1)
  554. // return;
  555. // if(on)
  556. // {
  557. // write(gpio_val_fd_other[KOUT_EN0+kouten], "1", 2);
  558. // }
  559. // else
  560. // {
  561. // write(gpio_val_fd_other[KOUT_EN0+kouten], "0", 2);
  562. // }
  563. }
  564. /******************************************************************************
  565. 函数名称: gpio_kout_do
  566. 函数版本: 01.01
  567. 创建作者:
  568. 创建日期: 2014-11-28
  569. 函数说明: 开出
  570. 参数说明: on: 1开出, 0回收
  571. kout: 那一路
  572. 返回值: 无
  573. 修改记录:
  574. */
  575. void gpio_kout_do(int on, unsigned int kout)
  576. {
  577. //if (kout > (DO_NUM-DO_OUT0))
  578. // return;
  579. if(on)
  580. {
  581. if((kout==6) || (kout==7))
  582. {
  583. // gpio_kouten_do(1,KOUT_EN1);
  584. kc_kout1_stu |= (1 << kout);
  585. }
  586. else
  587. {
  588. // gpio_kouten_do(1,KOUT_EN0);
  589. kc_kout0_stu |= (1 << kout);
  590. }
  591. write(gpio_val_fd[kout+DO_OUT0], "0", 2);
  592. }
  593. else
  594. {
  595. write(gpio_val_fd[kout+DO_OUT0], "1", 2);
  596. if((kout==6) || (kout==7))
  597. {
  598. kc_kout1_stu &= ~(1 << kout);
  599. }
  600. else
  601. {
  602. kc_kout0_stu &= ~(1 << kout);
  603. }
  604. if ((kc_pwm1_stu== 0) &&(kc_kout1_stu == 0))
  605. {
  606. // gpio_kouten_do(0,KOUT_EN1);
  607. }
  608. if ((kc_kout0_stu == 0) && (kc_pwm0_stu==0))
  609. {
  610. // gpio_kouten_do(0,KOUT_EN0);
  611. }
  612. }
  613. }
  614. /******************************************************************************
  615. 函数名称: gpio_pwm_do
  616. 函数版本: 01.01
  617. 创建作者:
  618. 创建日期: 2014-11-28
  619. 函数说明: pwm开出,由于存在kc_pwm_stu,只允许在同一控制路径中开出(例如同一中断或同一线程).
  620. 参数说明: on: 1开出, 0回收
  621. 返回值: 无
  622. 修改记录:
  623. */
  624. void gpio_pwm_do(int on, unsigned int kout)
  625. {
  626. // if (kout >= DO_NUM)
  627. // return;
  628. if(on)
  629. {
  630. if((kout==0) || (kout==1))
  631. {
  632. // gpio_kouten_do(1,KOUT_EN1);
  633. kc_pwm1_stu |= (1 << kout);
  634. }
  635. else
  636. {
  637. // gpio_kouten_do(1,KOUT_EN0);
  638. kc_pwm0_stu |= (1 << kout);
  639. }
  640. write(gpio_val_fd[kout], "0", 2);
  641. }
  642. else
  643. {
  644. write(gpio_val_fd[kout], "1", 2);
  645. if((kout==0) || (kout==1))
  646. {
  647. kc_pwm1_stu &= ~(1 << kout);
  648. }
  649. else
  650. {
  651. kc_pwm0_stu &= ~(1 << kout);
  652. }
  653. if ((kc_pwm1_stu== 0) &&(kc_kout1_stu == 0))
  654. {
  655. // gpio_kouten_do(0,KOUT_EN1);
  656. }
  657. if ((kc_kout0_stu == 0) && (kc_pwm0_stu==0))
  658. {
  659. // gpio_kouten_do(0,KOUT_EN0);
  660. }
  661. }
  662. }
  663. /******************************************************************************
  664. 函数名称: gpio_get_wirelessin
  665. 函数版本: 01.01
  666. 创建作者: sunxi
  667. 创建日期: 2008-09-16
  668. 函数说明: 得到无线遥控的状态。
  669. 参数说明: 无
  670. 返回值: 返回开入的状态,每个bit代表一个开入量。
  671. 修改记录:
  672. */
  673. unsigned int gpio_get_wirelessin(void)
  674. {
  675. register unsigned int dw = 0;
  676. return dw;
  677. }
  678. unsigned int gpio_get_version(void)
  679. {
  680. register unsigned int dw = 0;
  681. return dw;
  682. }
  683. unsigned int gpio_get_addr(void)
  684. {
  685. register unsigned int dw = 0;
  686. return dw;
  687. }
  688. /******************************************************************************
  689. 函数名称: gpio_watchdog_reset
  690. 函数版本: 01.01
  691. 创建作者: sunxi
  692. 创建日期: 2008-09-16
  693. 函数说明: 复位看门狗。
  694. 参数说明: 无。
  695. 返回值: 无。
  696. 修改记录:
  697. */
  698. // void gpio_watchdog_reset(void)
  699. // {
  700. // if(gpio_watchdog_val)
  701. // {
  702. // gpio_watchdog_val = 0;
  703. // write(gpio_val_fd_other[WATCHDOG], "0", 2);
  704. // }
  705. // else
  706. // {
  707. // gpio_watchdog_val = 1;
  708. // write(gpio_val_fd_other[WATCHDOG], "1", 2);
  709. // }
  710. // return;
  711. // }
  712. void _led_run_err(void)
  713. {
  714. // 上电就亮错误灯,有错误就继续亮没有就熄灭
  715. static uint8 err_led = 2;
  716. if(rt_err_count())
  717. {
  718. //错误指示灯常亮且运行熄灭
  719. if(!(err_led&0x01))
  720. {
  721. err_led |= 1;
  722. write(gpio_val_fd_other[ERR_LED], "0", 2);
  723. write(gpio_val_fd_other[RUN_LED], "1", 2);
  724. }
  725. return;
  726. }
  727. if(err_led)
  728. {
  729. err_led = 0;
  730. write(gpio_val_fd_other[ERR_LED], "1", 2);
  731. }
  732. //运行指示灯,每隔1s改变状态一次
  733. if(!gpio_run_led_val)
  734. {
  735. gpio_run_led_val = 1;
  736. write(gpio_val_fd_other[RUN_LED], "0", 2);
  737. }
  738. else
  739. {
  740. gpio_run_led_val = 0;
  741. write(gpio_val_fd_other[RUN_LED], "1", 2);
  742. }
  743. }
  744. void esam_power_ctrl(int on)
  745. {
  746. if(on)
  747. write(gpio_val_fd_other[ESAM_PWR], "1", 2);
  748. else
  749. write(gpio_val_fd_other[ESAM_PWR], "0", 2);
  750. }
  751. #ifdef GW_AREA_MAIN_2021
  752. void line_loss_maintain(bool bmaintain)
  753. {
  754. if(bmaintain)
  755. {
  756. write(gpio_val_fd_other[LINE_LOSS_SET], "1", 2);
  757. }
  758. else
  759. {
  760. write(gpio_val_fd_other[LINE_LOSS_SET], "0", 2);
  761. }
  762. }
  763. #endif
  764. /*------------------------------ 内部函数 -------------------------------------
  765. */
  766. /*------------------------------ 测试函数 -------------------------------------
  767. */
  768. #ifdef _GPIO_DEBUG
  769. #include "ustimer.h"
  770. #include "rt.h"
  771. int gpio_test(void)
  772. {
  773. int ret = 0;
  774. //unsigned int i;
  775. //gpio_kouten_do(1,KOUT_EN1);
  776. #if 1
  777. while(1)
  778. {
  779. sleep(5);
  780. gpio_kout_do(1,DO_OUT2-DO_OUT0);
  781. //gpio_kout_do(1,DO_OUT3-DO_OUT0);
  782. // gpio_pwm_do(1,DO_PWM1);
  783. sleep(5);
  784. gpio_kout_do(0,DO_OUT2-DO_OUT0);
  785. //gpio_kout_do(0,DO_OUT3-DO_OUT0);
  786. // gpio_pwm_do(0,DO_PWM1);
  787. /*
  788. for(i=DO_OUT0; i<DO_NUM; i++)
  789. {
  790. rt_printf("kout number = %d!\n\r", i);
  791. //msleep();
  792. sleep(1);
  793. gpio_kout_do(1,i-DO_OUT0);
  794. sleep(1);
  795. gpio_kout_do(0,i-DO_OUT0);
  796. }
  797. */
  798. }
  799. #endif
  800. return ret;
  801. }
  802. #endif