uart_dev.c 27 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946
  1. /**
  2. * @file uart.c
  3. * @author JL
  4. * @brief 串口UART模块C文件
  5. * @version 1.2
  6. * @date 2018-11-22
  7. */
  8. #include "asm/clock.h"
  9. #include "asm/uart_dev.h"
  10. #include "asm/cpu.h"
  11. #include "generic/gpio.h"
  12. #include "spinlock.h"
  13. #ifdef SUPPORT_MS_EXTENSIONS
  14. #pragma bss_seg(".uart_bss")
  15. #pragma data_seg(".uart_data")
  16. #pragma const_seg(".uart_const")
  17. #pragma code_seg(".uart_code")
  18. #endif
  19. #define UART_CLK clk_get("uart")
  20. #define UART_OT_CLK clk_get("lsb")
  21. static uart_bus_t uart0;
  22. static uart_bus_t uart1;
  23. static uart_bus_t uart2;
  24. /* _WEAK_ */
  25. /* extern */
  26. const u32 CONFIG_UART0_ENABLE = 1;
  27. /* _WEAK_ */
  28. /* extern */
  29. const u32 CONFIG_UART1_ENABLE = 1;
  30. /* _WEAK_ */
  31. /* extern */
  32. const u32 CONFIG_UART2_ENABLE = 1;
  33. /* _WEAK_ */
  34. /* extern */
  35. const u32 CONFIG_UART0_ENABLE_TX_DMA = 1;
  36. /* _WEAK_ */
  37. /* extern */
  38. const u32 CONFIG_UART1_ENABLE_TX_DMA = 1;
  39. /* _WEAK_ */
  40. /* extern */
  41. const u32 CONFIG_UART2_ENABLE_TX_DMA = 1;
  42. static u32 kfifo_get(KFIFO *kfifo, u8 *buffer, u32 len)
  43. {
  44. unsigned int i;
  45. len = MIN(len, kfifo->buf_in - kfifo->buf_out);
  46. i = MIN(len, kfifo->buf_size - (kfifo->buf_out & (kfifo->buf_size - 1)));
  47. memcpy(buffer, kfifo->buffer + (kfifo->buf_out & (kfifo->buf_size - 1)), i);
  48. memcpy(buffer + i, kfifo->buffer, len - i);
  49. kfifo->buf_out += len;
  50. return len;
  51. }
  52. static u32 kfifo_length(KFIFO *kfifo)
  53. {
  54. return kfifo->buf_in - kfifo->buf_out;
  55. }
  56. /**
  57. * @brief ut0发送一个byte
  58. *
  59. * @param a 要发送的字节
  60. */
  61. static void UT0_putbyte(char a)
  62. {
  63. if (JL_UART0->CON0 & BIT(0)) {
  64. JL_UART0->BUF = a;
  65. __asm__ volatile("csync");
  66. while ((JL_UART0->CON0 & BIT(15)) == 0);
  67. JL_UART0->CON0 |= BIT(13);
  68. }
  69. }
  70. /**
  71. * @brief ut0接收一个byte
  72. *
  73. * @param buf 字节存放地址
  74. * @param timeout 接收超时时间,单位1ms
  75. * @return 返回0:接收失败;返回1:接收成功
  76. */
  77. static u8 UT0_getbyte(u8 *buf, u32 timeout)
  78. {
  79. u32 _timeout, _t_sleep;
  80. timeout = ut_msecs_to_jiffies(timeout);
  81. if (JL_UART0->CON0 & BIT(6)) {
  82. //DMA_MODE
  83. if (!kfifo_length(&uart0.kfifo)) {
  84. UT_OSSemPend(&uart0.sem_rx, timeout);
  85. }
  86. UT_OSSemSet(&uart0.sem_rx, 0);
  87. return kfifo_get(&uart0.kfifo, buf, 1);
  88. } else {
  89. _timeout = timeout + ut_get_jiffies();
  90. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  91. while (!(JL_UART0->CON0 & BIT(14))) {
  92. if (timeout && time_before(_timeout, ut_get_jiffies())) {
  93. return 0;
  94. }
  95. if (time_before(_t_sleep, ut_get_jiffies())) {
  96. ut_sleep();
  97. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  98. }
  99. }
  100. *buf = JL_UART0->BUF;
  101. JL_UART0->CON0 |= BIT(12);
  102. __asm__ volatile("csync"); //make RX_PND_CLR taking effect
  103. }
  104. return 1;
  105. }
  106. /**
  107. * @brief ut0中断函数
  108. */
  109. SET_INTERRUPT
  110. static void UT0_isr_fun(void)
  111. {
  112. u32 rx_len = 0;
  113. if ((JL_UART0->CON0 & BIT(2)) && (JL_UART0->CON0 & BIT(15))) {
  114. JL_UART0->CON0 |= BIT(13);
  115. UT_OSSemPost(&uart0.sem_tx);
  116. if (uart0.isr_cbfun) {
  117. uart0.isr_cbfun(&uart0, UT_TX);
  118. }
  119. }
  120. if ((JL_UART0->CON0 & BIT(3)) && (JL_UART0->CON0 & BIT(14))) {
  121. JL_UART0->CON0 |= BIT(7); //DMA模式
  122. JL_UART0->CON0 |= BIT(12); //清RX PND
  123. rx_len = JL_UART0->HRXCNT; //读当前串口接收数据的个数
  124. /* uart0.kfifo.buf_in += uart0.frame_length; //每满frame_length字节则产生一次中断 */
  125. uart0.kfifo.buf_in += rx_len;
  126. UT_OSSemPost(&uart0.sem_rx);
  127. if (uart0.isr_cbfun) {
  128. uart0.isr_cbfun(&uart0, UT_RX);
  129. }
  130. }
  131. if ((JL_UART0->CON0 & BIT(5)) && (JL_UART0->CON0 & BIT(11))) {
  132. //OTCNT PND
  133. JL_UART0->CON0 |= BIT(7); //DMA模式
  134. JL_UART0->CON0 |= BIT(10); //清OTCNT PND
  135. JL_UART0->CON0 |= BIT(12); //清RX PND(这里的顺序不能改变,这里要清一次)
  136. rx_len = JL_UART0->HRXCNT; //读当前串口接收数据的个数
  137. if (rx_len) {
  138. uart0.kfifo.buf_in += rx_len;
  139. /* printf("%s() %d\n", __func__, __LINE__); */
  140. UT_OSSemPost(&uart0.sem_rx);
  141. if (uart0.isr_cbfun) {
  142. uart0.isr_cbfun(&uart0, UT_RX_OT);
  143. }
  144. }
  145. }
  146. }
  147. /**
  148. * @brief ut0接收字符串
  149. *
  150. * @param buf 字符串存放首地址
  151. * @param len 预接收长度
  152. * @param timeout 接收超时时间,单位1ms
  153. * @return 返回实际接收长度
  154. */
  155. static u32 UT0_read_buf(u8 *buf, u32 len, u32 timeout)
  156. {
  157. u32 i;
  158. u32 _timeout, _t_sleep;
  159. if (len == 0) {
  160. return 0;
  161. }
  162. timeout = ut_msecs_to_jiffies(timeout);
  163. if (JL_UART0->CON0 & BIT(6)) {
  164. if (!kfifo_length(&uart0.kfifo)) {
  165. UT_OSSemPend(&uart0.sem_rx, timeout);
  166. }
  167. UT_OSSemSet(&uart0.sem_rx, 0);
  168. return kfifo_get(&uart0.kfifo, buf, len);
  169. } else {
  170. _timeout = timeout + ut_get_jiffies();
  171. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  172. for (i = 0; i < len; i++) {
  173. while (!(JL_UART0->CON0 & BIT(14))) {
  174. if (timeout && time_before(_timeout, ut_get_jiffies())) {
  175. return i;
  176. }
  177. if (time_before(_t_sleep, ut_get_jiffies())) {
  178. ut_sleep();
  179. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  180. }
  181. }
  182. *(buf + i) = JL_UART0->BUF;
  183. JL_UART0->CON0 |= BIT(12);
  184. __asm__ volatile("csync"); //make RX_PND_CLR taking effect
  185. }
  186. }
  187. return len;
  188. }
  189. /**
  190. * @brief ut0发送字符串
  191. *
  192. * @param buf 字符串首地址
  193. * @param len 发送的字符串长度
  194. */
  195. static void UT0_write_buf(const u8 *buf, u32 len)
  196. {
  197. u32 i;
  198. if (len == 0) {
  199. return;
  200. }
  201. if (CONFIG_UART0_ENABLE_TX_DMA) {
  202. UT_OSSemSet(&uart0.sem_tx, 0);
  203. JL_UART0->CON0 |= BIT(13);
  204. JL_UART0->CON0 |= BIT(2);
  205. JL_UART0->TXADR = (u32)buf;
  206. JL_UART0->TXCNT = len;
  207. UT_OSSemPend(&uart0.sem_tx, 0);
  208. JL_UART0->CON0 &= ~BIT(2);
  209. } else {
  210. for (i = 0; i < len; i ++) {
  211. UT0_putbyte(*(buf + i));
  212. }
  213. }
  214. }
  215. /**
  216. * @brief ut0配置波特率
  217. *
  218. * @param baud 波特率值
  219. */
  220. static void UT0_set_baud(u32 baud)
  221. {
  222. JL_UART0->CON0 &= ~(BIT(0) | BIT(1));
  223. JL_UART0->CON0 |= BIT(13) | BIT(12) | BIT(10);
  224. JL_UART0->BAUD = ((UART_CLK + baud / 2) / baud) / 4 - 1;
  225. if (JL_UART0->CON0 & BIT(5)) {
  226. if (uart0.rx_timeout > 10) {
  227. JL_UART0->OTCNT = (uart0.rx_timeout / 10) * (UART_OT_CLK / 10) / 10;
  228. } else {
  229. JL_UART0->OTCNT = uart0.rx_timeout * UART_OT_CLK / 1000;
  230. }
  231. }
  232. JL_UART0->CON0 |= BIT(13) | BIT(12) | BIT(10) | BIT(0) | BIT(1);
  233. }
  234. /**
  235. *获取串口数据长度
  236. */
  237. static u32 uart1_get_data_len()
  238. {
  239. return kfifo_length(&uart1.kfifo);
  240. }
  241. /**
  242. * @brief ut0使能
  243. */
  244. static void UT0_open(u32 baud, u32 is_9bit, void *cbuf, u32 cbuf_size, u32 rx_cnt, u32 ot)
  245. {
  246. JL_UART0->CON0 = BIT(13) | BIT(12) | BIT(10);
  247. UT_OSSemCreate(&uart0.sem_rx, 0);
  248. UT_OSSemCreate(&uart0.sem_tx, 0);
  249. request_irq(IRQ_UART0_IDX, 3, UT0_isr_fun, 0);
  250. if (cbuf) {
  251. uart0.kfifo.buffer = cbuf;
  252. uart0.kfifo.buf_size = cbuf_size;
  253. uart0.kfifo.buf_in = 0;
  254. uart0.kfifo.buf_out = 0;
  255. uart0.frame_length = rx_cnt;
  256. uart0.rx_timeout = ot;
  257. JL_UART0->RXSADR = (u32)uart0.kfifo.buffer;
  258. JL_UART0->RXEADR = (u32)(uart0.kfifo.buffer + uart0.kfifo.buf_size);
  259. JL_UART0->RXCNT = uart0.frame_length;
  260. JL_UART0->CON0 |= BIT(6) | BIT(5) | BIT(3);
  261. }
  262. if (is_9bit) {
  263. JL_UART0->CON2 |= BIT(0);
  264. } else {
  265. JL_UART0->CON2 &= ~BIT(0);
  266. }
  267. UT0_set_baud(baud);
  268. }
  269. /**
  270. * @brief ut0关闭,注销
  271. */
  272. static void UT0_close(void)
  273. {
  274. UT_OSSemClose(&uart0.sem_rx);
  275. UT_OSSemClose(&uart0.sem_tx);
  276. irq_disable(IRQ_UART0_IDX);
  277. JL_UART0->CON0 = BIT(13) | BIT(12) | BIT(10);
  278. }
  279. /**
  280. * @brief ut1发送一个byte
  281. *
  282. * @param a 要发送的字节
  283. */
  284. static void UT1_putbyte(char a)
  285. {
  286. if (JL_UART1->CON0 & BIT(0)) {
  287. JL_UART1->BUF = a;
  288. __asm__ volatile("csync");
  289. while ((JL_UART1->CON0 & BIT(15)) == 0);
  290. JL_UART1->CON0 |= BIT(13);
  291. }
  292. }
  293. /**
  294. * @brief ut1接收一个byte
  295. *
  296. * @param buf 字节存放地址
  297. * @param timeout 接收超时时间,单位1ms
  298. 10ms¥;返回1:接收成功
  299. */
  300. static u8 UT1_getbyte(u8 *buf, u32 timeout)
  301. {
  302. u32 _timeout, _t_sleep;
  303. timeout = ut_msecs_to_jiffies(timeout);
  304. if (JL_UART1->CON0 & BIT(6)) {
  305. if (!kfifo_length(&uart1.kfifo)) {
  306. UT_OSSemPend(&uart1.sem_rx, timeout);
  307. }
  308. UT_OSSemSet(&uart1.sem_rx, 0);
  309. return kfifo_get(&uart1.kfifo, buf, 1);
  310. } else {
  311. _timeout = timeout + ut_get_jiffies();
  312. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  313. while (!(JL_UART1->CON0 & BIT(14))) {
  314. if (timeout && time_before(_timeout, ut_get_jiffies())) {
  315. return 0;
  316. }
  317. if (time_before(_t_sleep, ut_get_jiffies())) {
  318. ut_sleep();
  319. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  320. }
  321. }
  322. *buf = JL_UART1->BUF;
  323. JL_UART1->CON0 |= BIT(12);
  324. __asm__ volatile("csync"); //make RX_PND_CLR taking effect
  325. }
  326. return 1;
  327. }
  328. /**
  329. * @brief ut1中断函数
  330. */
  331. SET_INTERRUPT
  332. static void UT1_isr_fun(void)
  333. {
  334. u32 rx_len = 0;
  335. if ((JL_UART1->CON0 & BIT(2)) && (JL_UART1->CON0 & BIT(15))) {
  336. JL_UART1->CON0 |= BIT(13);
  337. UT_OSSemPost(&uart1.sem_tx);
  338. if (uart1.isr_cbfun) {
  339. uart1.isr_cbfun(&uart1, UT_TX);
  340. }
  341. }
  342. if ((JL_UART1->CON0 & BIT(3)) && (JL_UART1->CON0 & BIT(14))) {
  343. JL_UART1->CON0 |= BIT(7); //DMA模式
  344. JL_UART1->CON0 |= BIT(12); //清RX PND
  345. rx_len = JL_UART1->HRXCNT; //读当前串口接收数据的个数
  346. /* uart1.kfifo.buf_in += uart1.frame_length; //每满32字节则产生一次中断 */
  347. uart1.kfifo.buf_in += rx_len;
  348. UT_OSSemPost(&uart1.sem_rx);
  349. if (uart1.isr_cbfun) {
  350. uart1.isr_cbfun(&uart1, UT_RX);
  351. }
  352. }
  353. if ((JL_UART1->CON0 & BIT(5)) && (JL_UART1->CON0 & BIT(11))) {
  354. //OTCNT PND
  355. JL_UART1->CON0 |= BIT(7); //DMA模式
  356. JL_UART1->CON0 |= BIT(10); //清OTCNT PND
  357. JL_UART1->CON0 |= BIT(12); //清RX PND(这里的顺序不能改变,这里要清一次)
  358. rx_len = JL_UART1->HRXCNT; //读当前串口接收数据的个数
  359. if (rx_len) {
  360. uart1.kfifo.buf_in += rx_len;
  361. /* printf("%s() %d\n", __func__, __LINE__); */
  362. UT_OSSemPost(&uart1.sem_rx);
  363. if (uart1.isr_cbfun) {
  364. uart1.isr_cbfun(&uart1, UT_RX_OT);
  365. }
  366. }
  367. }
  368. }
  369. /**
  370. * @brief ut1接收字符串
  371. *
  372. * @param buf 字符串存放首地址
  373. * @param len 预接收长度
  374. * @param timeout 接收超时时间,单位1ms
  375. * @return 返回实际接收的长度
  376. */
  377. static u32 UT1_read_buf(u8 *buf, u32 len, u32 timeout)
  378. {
  379. u32 i;
  380. u32 _timeout, _t_sleep;
  381. if (len == 0) {
  382. return 0;
  383. }
  384. timeout = ut_msecs_to_jiffies(timeout);
  385. if (JL_UART1->CON0 & BIT(6)) {
  386. if (!kfifo_length(&uart1.kfifo)) {
  387. UT_OSSemPend(&uart1.sem_rx, timeout);
  388. }
  389. UT_OSSemSet(&uart1.sem_rx, 0);
  390. return kfifo_get(&uart1.kfifo, buf, len);
  391. } else {
  392. _timeout = timeout + ut_get_jiffies();
  393. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  394. for (i = 0; i < len; i++) {
  395. while (!(JL_UART1->CON0 & BIT(14))) {
  396. if (timeout && time_before(_timeout, ut_get_jiffies())) {
  397. return i;
  398. }
  399. if (time_before(_t_sleep, ut_get_jiffies())) {
  400. ut_sleep();
  401. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  402. }
  403. }
  404. *(buf + i) = JL_UART1->BUF;
  405. JL_UART1->CON0 |= BIT(12);
  406. __asm__ volatile("csync"); //make RX_PND_CLR taking effect
  407. }
  408. }
  409. return len;
  410. }
  411. /**
  412. * @brief ut1发送字符串
  413. *
  414. * @param buf 字符串首地址
  415. * @param len 发送的字符串长度
  416. * @param timeout 发送超时时间,单位10ms
  417. */
  418. static void UT1_write_buf(const u8 *buf, u32 len)
  419. {
  420. u32 i;
  421. if (len == 0) {
  422. return;
  423. }
  424. if (CONFIG_UART1_ENABLE_TX_DMA) {
  425. UT_OSSemSet(&uart1.sem_tx, 0);
  426. JL_UART1->CON0 |= BIT(13);
  427. JL_UART1->CON0 |= BIT(2);
  428. JL_UART1->TXADR = (u32)buf;
  429. JL_UART1->TXCNT = len;
  430. UT_OSSemPend(&uart1.sem_tx, 0);
  431. JL_UART1->CON0 &= ~BIT(2);
  432. } else {
  433. for (i = 0; i < len; i ++) {
  434. UT1_putbyte(*(buf + i));
  435. }
  436. }
  437. }
  438. /**
  439. * @brief ut1配置波特率
  440. *
  441. * @param baud 波特率值
  442. */
  443. static void UT1_set_baud(u32 baud)
  444. {
  445. JL_UART1->CON0 &= ~(BIT(0) | BIT(1));
  446. JL_UART1->CON0 |= BIT(13) | BIT(12) | BIT(10);
  447. JL_UART1->BAUD = ((UART_CLK + baud / 2) / baud) / 4 - 1;
  448. if (JL_UART1->CON0 & BIT(5)) {
  449. if (uart1.rx_timeout > 10) {
  450. JL_UART1->OTCNT = (uart1.rx_timeout / 10) * (UART_OT_CLK / 10) / 10;
  451. } else {
  452. JL_UART1->OTCNT = uart1.rx_timeout * UART_OT_CLK / 1000;
  453. }
  454. }
  455. JL_UART1->CON0 |= BIT(13) | BIT(12) | BIT(10) | BIT(0) | BIT(1);
  456. }
  457. /**
  458. * @brief ut1使能
  459. */
  460. static void UT1_open(u32 baud, u32 is_9bit, void *cbuf, u32 cbuf_size, u32 rx_cnt, u32 ot)
  461. {
  462. JL_UART1->CON0 = BIT(13) | BIT(12) | BIT(10);
  463. UT_OSSemCreate(&uart1.sem_rx, 0);
  464. UT_OSSemCreate(&uart1.sem_tx, 0);
  465. request_irq(IRQ_UART1_IDX, 3, UT1_isr_fun, 0);
  466. if (cbuf) {
  467. uart1.kfifo.buffer = cbuf;
  468. uart1.kfifo.buf_size = cbuf_size;
  469. uart1.kfifo.buf_in = 0;
  470. uart1.kfifo.buf_out = 0;
  471. uart1.frame_length = rx_cnt;
  472. uart1.rx_timeout = ot;
  473. JL_UART1->RXSADR = (u32)uart1.kfifo.buffer;
  474. JL_UART1->RXEADR = (u32)(uart1.kfifo.buffer + uart1.kfifo.buf_size);
  475. JL_UART1->RXCNT = uart1.frame_length;
  476. JL_UART1->CON0 |= BIT(6) | BIT(5) | BIT(3);
  477. }
  478. if (is_9bit) {
  479. JL_UART1->CON2 |= BIT(0);
  480. } else {
  481. JL_UART1->CON2 &= ~BIT(0);
  482. }
  483. UT1_set_baud(baud);
  484. }
  485. /**
  486. * @brief ut1关闭,注销
  487. */
  488. static void UT1_close(void)
  489. {
  490. UT_OSSemClose(&uart1.sem_rx);
  491. UT_OSSemClose(&uart1.sem_tx);
  492. irq_disable(IRQ_UART1_IDX);
  493. JL_UART1->CON0 = BIT(13) | BIT(12) | BIT(10);
  494. }
  495. /**
  496. * @brief ut2发送一个byte
  497. *
  498. * @param a 要发送的字节
  499. */
  500. static void UT2_putbyte(char a)
  501. {
  502. if (JL_UART2->CON0 & BIT(0)) {
  503. JL_UART2->BUF = a;
  504. __asm__ volatile("csync");
  505. while ((JL_UART2->CON0 & BIT(15)) == 0);
  506. JL_UART2->CON0 |= BIT(13);
  507. }
  508. }
  509. /**
  510. * @brief ut2接收一个byte
  511. *
  512. * @param buf 字节存放地址
  513. * @param timeout 接收超时时间,单位1ms
  514. * @return 返回0:接收失败;返回1:接收成功
  515. */
  516. static u8 UT2_getbyte(u8 *buf, u32 timeout)
  517. {
  518. u32 _timeout, _t_sleep;
  519. timeout = ut_msecs_to_jiffies(timeout);
  520. if (JL_UART2->CON0 & BIT(6)) {
  521. if (!kfifo_length(&uart2.kfifo)) {
  522. UT_OSSemPend(&uart2.sem_rx, timeout);
  523. }
  524. UT_OSSemSet(&uart2.sem_rx, 0);
  525. return kfifo_get(&uart2.kfifo, buf, 1);
  526. } else {
  527. _timeout = timeout + ut_get_jiffies();
  528. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  529. while (!(JL_UART2->CON0 & BIT(14))) {
  530. if (timeout && time_before(_timeout, ut_get_jiffies())) {
  531. return 0;
  532. }
  533. if (time_before(_t_sleep, ut_get_jiffies())) {
  534. ut_sleep();
  535. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  536. }
  537. }
  538. *buf = JL_UART2->BUF;
  539. JL_UART2->CON0 |= BIT(12);
  540. __asm__ volatile("csync"); //make RX_PND_CLR taking effect
  541. }
  542. return 1;
  543. }
  544. /**
  545. * @brief ut2中断函数
  546. */
  547. SET_INTERRUPT
  548. static void UT2_isr_fun(void)
  549. {
  550. //JL_UART2->CON0 |= (BIT(13) | BIT(12) | BIT(10));
  551. u32 rx_len = 0;
  552. if ((JL_UART2->CON0 & BIT(2)) && (JL_UART2->CON0 & BIT(15))) {
  553. JL_UART2->CON0 |= BIT(13);
  554. UT_OSSemPost(&uart2.sem_tx);
  555. if (uart2.isr_cbfun) {
  556. uart2.isr_cbfun(&uart2, UT_TX);
  557. }
  558. }
  559. if ((JL_UART2->CON0 & BIT(3)) && (JL_UART2->CON0 & BIT(14))) {
  560. JL_UART2->CON0 |= BIT(7); //DMA模式
  561. JL_UART2->CON0 |= BIT(12); //清RX PND
  562. rx_len = JL_UART2->HRXCNT; //读当前串口接收数据的个数
  563. /* uart2.kfifo.buf_in += uart2.frame_length; //每满32字节则产生一次中断 */
  564. uart2.kfifo.buf_in += rx_len;
  565. UT_OSSemPost(&uart2.sem_rx);
  566. if (uart2.isr_cbfun) {
  567. uart2.isr_cbfun(&uart2, UT_RX);
  568. }
  569. }
  570. if ((JL_UART2->CON0 & BIT(5)) && (JL_UART2->CON0 & BIT(11))) {
  571. //OTCNT PND
  572. JL_UART2->CON0 |= BIT(7); //DMA模式
  573. JL_UART2->CON0 |= BIT(10); //清OTCNT PND
  574. JL_UART2->CON0 |= BIT(12); //清RX PND(这里的顺序不能改变,这里要清一次)
  575. rx_len = JL_UART2->HRXCNT; //读当前串口接收数据的个数
  576. if (rx_len) {
  577. uart2.kfifo.buf_in += rx_len;
  578. /* printf("%s() %d\n", __func__, __LINE__); */
  579. UT_OSSemPost(&uart2.sem_rx);
  580. if (uart2.isr_cbfun) {
  581. uart2.isr_cbfun(&uart2, UT_RX_OT);
  582. }
  583. }
  584. }
  585. }
  586. /**
  587. * @brief ut1接收字符串
  588. *
  589. * @param buf 字符串存放首地址
  590. * @param len 预接收长度
  591. * @param timeout 接收超时时间,单位1ms
  592. * @return 返回实际接收的长度
  593. */
  594. static u32 UT2_read_buf(u8 *buf, u32 len, u32 timeout)
  595. {
  596. u32 i;
  597. u32 _timeout, _t_sleep;
  598. if (len == 0) {
  599. return 0;
  600. }
  601. timeout = ut_msecs_to_jiffies(timeout);
  602. if (JL_UART2->CON0 & BIT(6)) {
  603. if (!kfifo_length(&uart2.kfifo)) {
  604. UT_OSSemPend(&uart2.sem_rx, timeout);
  605. }
  606. UT_OSSemSet(&uart2.sem_rx, 0);
  607. return kfifo_get(&uart2.kfifo, buf, len);
  608. } else {
  609. _timeout = timeout + ut_get_jiffies();
  610. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  611. for (i = 0; i < len; i ++) {
  612. while (!(JL_UART2->CON0 & BIT(14))) {
  613. if (timeout && time_before(_timeout, ut_get_jiffies())) {
  614. return i;
  615. }
  616. if (time_before(_t_sleep, ut_get_jiffies())) {
  617. ut_sleep();
  618. _t_sleep = ut_msecs_to_jiffies(10) + ut_get_jiffies();
  619. }
  620. }
  621. *(buf + i) = JL_UART2->BUF;
  622. JL_UART2->CON0 |= BIT(12);
  623. __asm__ volatile("csync"); //make RX_PND_CLR taking effect
  624. }
  625. }
  626. return len;
  627. }
  628. /**
  629. * @brief ut2发送字符串
  630. *
  631. * @param buf 字符串首地址
  632. * @param len 发送的字符串长度
  633. * @param timeout 发送超时时间,单位10ms
  634. */
  635. static void UT2_write_buf(const u8 *buf, u32 len)
  636. {
  637. u32 i;
  638. if (len == 0) {
  639. return;
  640. }
  641. if (CONFIG_UART2_ENABLE_TX_DMA) {
  642. UT_OSSemSet(&uart2.sem_tx, 0);
  643. JL_UART2->CON0 |= BIT(13);
  644. JL_UART2->CON0 |= BIT(2);
  645. JL_UART2->TXADR = (u32)buf;
  646. JL_UART2->TXCNT = len;
  647. UT_OSSemPend(&uart2.sem_tx, 0);
  648. JL_UART2->CON0 &= ~BIT(2);
  649. } else {
  650. for (i = 0; i < len; i++) {
  651. UT2_putbyte(*(buf + i));
  652. }
  653. }
  654. }
  655. /**
  656. * @brief ut2配置波特率
  657. *
  658. * @param baud 波特率值
  659. */
  660. static void UT2_set_baud(u32 baud)
  661. {
  662. JL_UART2->CON0 &= ~(BIT(0) | BIT(1));
  663. JL_UART2->CON0 |= BIT(13) | BIT(12) | BIT(10);
  664. JL_UART2->BAUD = ((UART_CLK + baud / 2) / baud) / 4 - 1;
  665. if (JL_UART2->CON0 & BIT(5)) {
  666. if (uart2.rx_timeout > 10) {
  667. JL_UART2->OTCNT = (uart2.rx_timeout / 10) * (UART_OT_CLK / 10) / 10;
  668. } else {
  669. JL_UART2->OTCNT = uart2.rx_timeout * UART_OT_CLK / 1000;
  670. }
  671. }
  672. JL_UART2->CON0 |= BIT(13) | BIT(12) | BIT(10) | BIT(0) | BIT(1);
  673. }
  674. /**
  675. * @brief ut2使能
  676. */
  677. static void UT2_open(u32 baud, u32 is_9bit, void *cbuf, u32 cbuf_size, u32 rx_cnt, u32 ot)
  678. {
  679. JL_UART2->CON0 = BIT(13) | BIT(12) | BIT(10);
  680. UT_OSSemCreate(&uart2.sem_rx, 0);
  681. UT_OSSemCreate(&uart2.sem_tx, 0);
  682. request_irq(IRQ_UART2_IDX, 3, UT2_isr_fun, 0);
  683. if (cbuf) {
  684. uart2.kfifo.buffer = cbuf;
  685. uart2.kfifo.buf_size = cbuf_size;
  686. uart2.kfifo.buf_in = 0;
  687. uart2.kfifo.buf_out = 0;
  688. uart2.frame_length = rx_cnt;
  689. uart2.rx_timeout = ot;
  690. JL_UART2->RXSADR = (u32)uart2.kfifo.buffer;
  691. JL_UART2->RXEADR = (u32)(uart2.kfifo.buffer + uart2.kfifo.buf_size);
  692. JL_UART2->RXCNT = uart2.frame_length;
  693. JL_UART2->CON0 |= BIT(6) | BIT(5) | BIT(3);
  694. }
  695. if (is_9bit) {
  696. JL_UART2->CON2 |= BIT(0);
  697. } else {
  698. JL_UART2->CON2 &= ~BIT(0);
  699. }
  700. UT2_set_baud(baud);
  701. }
  702. /**
  703. * @brief ut2关闭,注销
  704. */
  705. static void UT2_close(void)
  706. {
  707. UT_OSSemClose(&uart2.sem_rx);
  708. UT_OSSemClose(&uart2.sem_tx);
  709. irq_disable(IRQ_UART2_IDX);
  710. JL_UART2->CON0 = BIT(13) | BIT(12) | BIT(10);
  711. }
  712. static u32 uart_is_idle(u32 ut_num)
  713. {
  714. switch (ut_num) {
  715. case 0 :
  716. return !(JL_UART0->CON0 & BIT(0));
  717. case 1 :
  718. return !(JL_UART1->CON0 & BIT(0));
  719. case 2:
  720. return !(JL_UART2->CON0 & BIT(0));
  721. default :
  722. break;
  723. }
  724. return 0;
  725. }
  726. static u8 uart_config(const struct uart_platform_data_t *arg, u8 tx_ch, enum PFI_TABLE rx_pfun)
  727. {
  728. if (!(arg->tx_pin < IO_PORT_MAX || arg->rx_pin < IO_PORT_MAX)) {
  729. return -1;
  730. }
  731. if (arg->tx_pin < IO_PORT_MAX) {
  732. gpio_direction_output(arg->tx_pin, 1);
  733. gpio_set_fun_output_port(arg->tx_pin, tx_ch, 1, 1);
  734. }
  735. if (arg->rx_pin < IO_PORT_MAX) {
  736. gpio_direction_input(arg->rx_pin);
  737. gpio_set_pull_up(arg->rx_pin, 1);
  738. gpio_set_die(arg->rx_pin, 1);
  739. gpio_set_fun_input_port(arg->rx_pin, rx_pfun);
  740. }
  741. return 0;
  742. }
  743. /**
  744. * @brief ut模块初始const struct uart_platform_data_t *arg化函数,供外部调用
  745. *
  746. * @param arg 传入uartconst struct uart_platform_data_t *arg_argment型结构体指针
  747. * @return 返回uart_buconst struct uart_platform_data_t *args_t型结构体指针
  748. */
  749. __attribute__((noinline))
  750. const uart_bus_t *uart_dev_open(const struct uart_platform_data_t *arg)
  751. {
  752. u8 ut_num;
  753. uart_bus_t *ut = NULL;
  754. u8 gpio_input_channle_flag = 0;
  755. if (uart_is_idle(0)) {
  756. ut_num = 0;
  757. } else if (uart_is_idle(1)) {
  758. ut_num = 1;
  759. } else if ((uart_is_idle(2))) {
  760. ut_num = 2;
  761. } else {
  762. return NULL;
  763. }
  764. if (arg->rx_cbuf) {
  765. if ((arg->rx_cbuf_size == 0) || (arg->rx_cbuf_size & (arg->rx_cbuf_size - 1))) {
  766. return NULL;
  767. }
  768. }
  769. if (CONFIG_UART0_ENABLE && ut_num == 0) {
  770. //gpio_set_uart0(ut_ch);
  771. if (uart_config(arg, FO_UART0_TX, PFI_UART0_RX)) {
  772. return NULL;
  773. }
  774. uart0.argv = arg->argv;
  775. uart0.isr_cbfun = arg->isr_cbfun;
  776. uart0.putbyte = UT0_putbyte;
  777. uart0.getbyte = UT0_getbyte;
  778. uart0.read = UT0_read_buf;
  779. uart0.write = UT0_write_buf;
  780. uart0.set_baud = UT0_set_baud;
  781. UT0_open(arg->baud, arg->is_9bit,
  782. arg->rx_cbuf, arg->rx_cbuf_size,
  783. arg->frame_length, arg->rx_timeout);
  784. ut = &uart0;
  785. } else if (CONFIG_UART1_ENABLE && ut_num == 1) {
  786. //gpio_set_uart1(ut_ch);
  787. if (uart_config(arg, FO_UART1_TX, PFI_UART1_RX)) {
  788. return NULL;
  789. }
  790. uart1.argv = arg->argv;
  791. uart1.isr_cbfun = arg->isr_cbfun;
  792. uart1.putbyte = UT1_putbyte;
  793. uart1.getbyte = UT1_getbyte;
  794. uart1.read = UT1_read_buf;
  795. uart1.write = UT1_write_buf;
  796. uart1.set_baud = UT1_set_baud;
  797. uart1.get_data_len = uart1_get_data_len;
  798. UT1_open(arg->baud, arg->is_9bit,
  799. arg->rx_cbuf, arg->rx_cbuf_size,
  800. arg->frame_length, arg->rx_timeout);
  801. ut = &uart1;
  802. } else if (CONFIG_UART2_ENABLE && ut_num == 2) {
  803. //gpio_set_uart2(ut_ch);
  804. if (uart_config(arg, FO_UART2_TX, PFI_UART2_RX)) {
  805. return NULL;
  806. }
  807. uart2.argv = arg->argv;
  808. uart2.isr_cbfun = arg->isr_cbfun;
  809. uart2.putbyte = UT2_putbyte;
  810. uart2.getbyte = UT2_getbyte;
  811. uart2.read = UT2_read_buf;
  812. uart2.write = UT2_write_buf;
  813. uart2.set_baud = UT2_set_baud;
  814. UT2_open(arg->baud, arg->is_9bit,
  815. arg->rx_cbuf, arg->rx_cbuf_size,
  816. arg->frame_length, arg->rx_timeout);
  817. ut = &uart2;
  818. } else {
  819. return NULL;
  820. }
  821. return ut;
  822. }
  823. u32 uart_dev_close(uart_bus_t *ut)
  824. {
  825. UT_OSSemClose(&ut->sem_rx);
  826. UT_OSSemClose(&ut->sem_tx);
  827. if (&uart0 == ut) {
  828. UT0_close();
  829. return gpio_close_uart0();
  830. } else if (&uart1 == ut) {
  831. UT1_close();
  832. return gpio_close_uart1();
  833. } else {
  834. UT2_close();
  835. return gpio_close_uart2();
  836. }
  837. return 0;
  838. }
  839. void uart_disable_for_ota()
  840. {
  841. JL_UART0->CON0 = BIT(13) | BIT(12) | BIT(10);
  842. JL_UART1->CON0 = BIT(13) | BIT(12) | BIT(10);
  843. JL_UART2->CON0 = BIT(13) | BIT(12) | BIT(10);
  844. }
  845. static u8 _rts_io = -1;
  846. static u8 _cts_io = -1;
  847. void uart1_flow_ctl_init(u8 rts_io, u8 cts_io)
  848. {
  849. JL_UART1->CON1 = 0;
  850. //RTS
  851. if (rts_io < IO_PORT_MAX) {
  852. _rts_io = rts_io;
  853. gpio_set_die(rts_io, 1);
  854. gpio_set_direction(rts_io, 0);
  855. gpio_set_pull_up(rts_io, 0);
  856. gpio_set_pull_down(rts_io, 0);
  857. gpio_write(rts_io, 0);
  858. gpio_set_fun_output_port(rts_io, FO_UART1_RTS, 1, 1);
  859. JL_UART1->CON1 |= BIT(13) | BIT(0);
  860. }
  861. //CTS
  862. if (cts_io < IO_PORT_MAX) {
  863. _cts_io = cts_io;
  864. gpio_set_die(cts_io, 1);
  865. gpio_set_direction(cts_io, 1);
  866. gpio_set_pull_up(cts_io, 0);
  867. gpio_set_pull_down(cts_io, 1);
  868. gpio_set_fun_input_port(cts_io, PFI_UART1_CTS);
  869. JL_UART1->CON1 |= BIT(14) | BIT(2);
  870. }
  871. }
  872. void uart1_flow_ctl_rts_suspend(void) //忙碌,硬件停止接收
  873. {
  874. if (JL_UART1->CON1 & BIT(0)) {
  875. JL_UART1->CON1 |= BIT(4); //RX_disable
  876. JL_UART1->CON1 |= BIT(1); //RTS_DMAEN ///强制本地端RTS为高
  877. }
  878. /* if (!(JL_UART1->CON1 & BIT(0))) { */
  879. /* gpio_write(_rts_io, 1); //告诉对方,自己忙碌 */
  880. /* } */
  881. /* JL_UART1->CON1 |= BIT(4); //硬件停止接收 */
  882. }
  883. void uart1_flow_ctl_rts_resume(void) //空闲,表示可以继续接收数据
  884. {
  885. if (JL_UART1->CON1 & BIT(0)) {
  886. JL_UART1->CON1 &= ~BIT(4); //RX_enable
  887. JL_UART1->CON1 &= ~BIT(1); //RTS_DMAEN ///RTS可以硬件拉低
  888. }
  889. /* JL_UART1->CON1 &= ~BIT(4); //硬件可以接收 */
  890. /* if (JL_UART1->CON1 & BIT(0)) { */
  891. /* JL_UART1->CON1 |= BIT(13); */
  892. /* } else { */
  893. /* gpio_write(_rts_io, 0); //表示可以继续接收数据 */
  894. /* } */
  895. }