cdc_class.c 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414
  1. /**
  2. **************************************************************************
  3. * @file cdc_class.c
  4. * @version v2.0.6
  5. * @date 2021-12-31
  6. * @brief usb cdc class type
  7. **************************************************************************
  8. * Copyright notice & Disclaimer
  9. *
  10. * The software Board Support Package (BSP) that is made available to
  11. * download from Artery official website is the copyrighted work of Artery.
  12. * Artery authorizes customers to use, copy, and distribute the BSP
  13. * software and its related documentation for the purpose of design and
  14. * development in conjunction with Artery microcontrollers. Use of the
  15. * software is governed by this copyright notice and the following disclaimer.
  16. *
  17. * THIS SOFTWARE IS PROVIDED ON "AS IS" BASIS WITHOUT WARRANTIES,
  18. * GUARANTEES OR REPRESENTATIONS OF ANY KIND. ARTERY EXPRESSLY DISCLAIMS,
  19. * TO THE FULLEST EXTENT PERMITTED BY LAW, ALL EXPRESS, IMPLIED OR
  20. * STATUTORY OR OTHER WARRANTIES, GUARANTEES OR REPRESENTATIONS,
  21. * INCLUDING BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY,
  22. * FITNESS FOR A PARTICULAR PURPOSE, OR NON-INFRINGEMENT.
  23. *
  24. **************************************************************************
  25. */
  26. #include "usbd_core.h"
  27. #include "cdc_class.h"
  28. #include "cdc_desc.h"
  29. /** @addtogroup AT32F403A_407_middlewares_usbd_class
  30. * @{
  31. */
  32. /** @defgroup USB_cdc_class
  33. * @brief usb device class cdc demo
  34. * @{
  35. */
  36. /** @defgroup USB_cdc_class_private_functions
  37. * @{
  38. */
  39. usb_sts_type class_init_handler(void *udev);
  40. usb_sts_type class_clear_handler(void *udev);
  41. usb_sts_type class_setup_handler(void *udev, usb_setup_type *setup);
  42. usb_sts_type class_ept0_tx_handler(void *udev);
  43. usb_sts_type class_ept0_rx_handler(void *udev);
  44. usb_sts_type class_in_handler(void *udev, uint8_t ept_num);
  45. usb_sts_type class_out_handler(void *udev, uint8_t ept_num);
  46. usb_sts_type class_sof_handler(void *udev);
  47. usb_sts_type class_event_handler(void *udev, usbd_event_type event);
  48. void usb_vcp_cmd_process(void *udev, uint8_t cmd, uint8_t *buff, uint16_t len);
  49. /* usb rx and tx buffer */
  50. static uint32_t alt_setting = 0;
  51. static uint8_t g_rx_buff[USBD_OUT_MAXPACKET_SIZE];
  52. //static uint8_t g_tx_buff[USBD_IN_MAXPACKET_SIZE];
  53. static uint8_t g_cmd[USBD_CMD_MAXPACKET_SIZE];
  54. static uint8_t g_req;
  55. static uint16_t g_len, g_rxlen;
  56. __IO uint8_t g_tx_completed = 1, g_rx_completed = 0;
  57. linecoding_type linecoding =
  58. {
  59. 115200,
  60. 0x00,
  61. 0x00,
  62. 0x08
  63. };
  64. /* static variable */
  65. /* usb device class handler */
  66. usbd_class_handler class_handler =
  67. {
  68. class_init_handler,
  69. class_clear_handler,
  70. class_setup_handler,
  71. class_ept0_tx_handler,
  72. class_ept0_rx_handler,
  73. class_in_handler,
  74. class_out_handler,
  75. class_sof_handler,
  76. class_event_handler,
  77. };
  78. /**
  79. * @brief initialize usb endpoint
  80. * @param udev: to the structure of usbd_core_type
  81. * @retval status of usb_sts_type
  82. */
  83. usb_sts_type class_init_handler(void *udev)
  84. {
  85. usb_sts_type status = USB_OK;
  86. usbd_core_type *pudev = (usbd_core_type *)udev;
  87. #ifndef USB_EPT_AUTO_MALLOC_BUFFER
  88. /* use user define buffer address */
  89. usbd_ept_buf_custom_define(pudev, USBD_CDC_INT_EPT, EPT2_TX_ADDR);
  90. usbd_ept_buf_custom_define(pudev, USBD_CDC_BULK_IN_EPT, EPT1_TX_ADDR);
  91. usbd_ept_buf_custom_define(pudev, USBD_CDC_BULK_OUT_EPT, EPT1_RX_ADDR);
  92. #endif
  93. /* open in endpoint */
  94. usbd_ept_open(pudev, USBD_CDC_INT_EPT, EPT_INT_TYPE, USBD_CMD_MAXPACKET_SIZE);
  95. /* open in endpoint */
  96. usbd_ept_open(pudev, USBD_CDC_BULK_IN_EPT, EPT_BULK_TYPE, USBD_IN_MAXPACKET_SIZE);
  97. /* open out endpoint */
  98. usbd_ept_open(pudev, USBD_CDC_BULK_OUT_EPT, EPT_BULK_TYPE, USBD_OUT_MAXPACKET_SIZE);
  99. /* set out endpoint to receive status */
  100. usbd_ept_recv(pudev, USBD_CDC_BULK_OUT_EPT, g_rx_buff, USBD_OUT_MAXPACKET_SIZE);
  101. g_tx_completed = 1;
  102. return status;
  103. }
  104. /**
  105. * @brief clear endpoint or other state
  106. * @param udev: to the structure of usbd_core_type
  107. * @retval status of usb_sts_type
  108. */
  109. usb_sts_type class_clear_handler(void *udev)
  110. {
  111. usb_sts_type status = USB_OK;
  112. usbd_core_type *pudev = (usbd_core_type *)udev;
  113. /* close in endpoint */
  114. usbd_ept_close(pudev, USBD_CDC_INT_EPT);
  115. /* close in endpoint */
  116. usbd_ept_close(pudev, USBD_CDC_BULK_IN_EPT);
  117. /* close out endpoint */
  118. usbd_ept_close(pudev, USBD_CDC_BULK_OUT_EPT);
  119. return status;
  120. }
  121. /**
  122. * @brief usb device class setup request handler
  123. * @param udev: to the structure of usbd_core_type
  124. * @param setup: setup packet
  125. * @retval status of usb_sts_type
  126. */
  127. usb_sts_type class_setup_handler(void *udev, usb_setup_type *setup)
  128. {
  129. usb_sts_type status = USB_OK;
  130. usbd_core_type *pudev = (usbd_core_type *)udev;
  131. switch(setup->bmRequestType & USB_REQ_TYPE_RESERVED)
  132. {
  133. /* class request */
  134. case USB_REQ_TYPE_CLASS:
  135. if(setup->wLength)
  136. {
  137. if(setup->bmRequestType & USB_REQ_DIR_DTH)
  138. {
  139. usb_vcp_cmd_process(udev, setup->bRequest, g_cmd, setup->wLength);
  140. usbd_ctrl_send(pudev, g_cmd, setup->wLength);
  141. }
  142. else
  143. {
  144. g_req = setup->bRequest;
  145. g_len = setup->wLength;
  146. usbd_ctrl_recv(pudev, g_cmd, g_len);
  147. }
  148. }
  149. break;
  150. /* standard request */
  151. case USB_REQ_TYPE_STANDARD:
  152. switch(setup->bRequest)
  153. {
  154. case USB_STD_REQ_GET_DESCRIPTOR:
  155. usbd_ctrl_unsupport(pudev);
  156. break;
  157. case USB_STD_REQ_GET_INTERFACE:
  158. usbd_ctrl_send(pudev, (uint8_t *)&alt_setting, 1);
  159. break;
  160. case USB_STD_REQ_SET_INTERFACE:
  161. alt_setting = setup->wValue;
  162. break;
  163. default:
  164. break;
  165. }
  166. break;
  167. default:
  168. usbd_ctrl_unsupport(pudev);
  169. break;
  170. }
  171. return status;
  172. }
  173. /**
  174. * @brief usb device class endpoint 0 in status stage complete
  175. * @param udev: to the structure of usbd_core_type
  176. * @retval status of usb_sts_type
  177. */
  178. usb_sts_type class_ept0_tx_handler(void *udev)
  179. {
  180. usb_sts_type status = USB_OK;
  181. /* ...user code... */
  182. return status;
  183. }
  184. /**
  185. * @brief usb device class endpoint 0 out status stage complete
  186. * @param udev: to the structure of usbd_core_type
  187. * @retval status of usb_sts_type
  188. */
  189. usb_sts_type class_ept0_rx_handler(void *udev)
  190. {
  191. usb_sts_type status = USB_OK;
  192. usbd_core_type *pudev = (usbd_core_type *)udev;
  193. uint32_t recv_len = usbd_get_recv_len(pudev, 0);
  194. /* ...user code... */
  195. if( g_req == SET_LINE_CODING)
  196. {
  197. /* class process */
  198. usb_vcp_cmd_process(udev, g_req, g_cmd, recv_len);
  199. }
  200. return status;
  201. }
  202. /**
  203. * @brief usb device class transmision complete handler
  204. * @param udev: to the structure of usbd_core_type
  205. * @param ept_num: endpoint number
  206. * @retval status of usb_sts_type
  207. */
  208. usb_sts_type class_in_handler(void *udev, uint8_t ept_num)
  209. {
  210. usb_sts_type status = USB_OK;
  211. /* ...user code...
  212. trans next packet data
  213. */
  214. g_tx_completed = 1;
  215. return status;
  216. }
  217. /**
  218. * @brief usb device class endpoint receive data
  219. * @param udev: to the structure of usbd_core_type
  220. * @param ept_num: endpoint number
  221. * @retval status of usb_sts_type
  222. */
  223. usb_sts_type class_out_handler(void *udev, uint8_t ept_num)
  224. {
  225. usb_sts_type status = USB_OK;
  226. usbd_core_type *pudev = (usbd_core_type *)udev;
  227. /* get endpoint receive data length */
  228. g_rxlen = usbd_get_recv_len(pudev, ept_num);
  229. /*set recv flag*/
  230. g_rx_completed = 1;
  231. return status;
  232. }
  233. /**
  234. * @brief usb device class sof handler
  235. * @param udev: to the structure of usbd_core_type
  236. * @retval status of usb_sts_type
  237. */
  238. usb_sts_type class_sof_handler(void *udev)
  239. {
  240. usb_sts_type status = USB_OK;
  241. /* ...user code... */
  242. return status;
  243. }
  244. /**
  245. * @brief usb device class event handler
  246. * @param udev: to the structure of usbd_core_type
  247. * @param event: usb device event
  248. * @retval status of usb_sts_type
  249. */
  250. usb_sts_type class_event_handler(void *udev, usbd_event_type event)
  251. {
  252. usb_sts_type status = USB_OK;
  253. switch(event)
  254. {
  255. case USBD_RESET_EVENT:
  256. /* ...user code... */
  257. break;
  258. case USBD_SUSPEND_EVENT:
  259. /* ...user code... */
  260. break;
  261. case USBD_WAKEUP_EVENT:
  262. /* ...user code... */
  263. break;
  264. default:
  265. break;
  266. }
  267. return status;
  268. }
  269. /**
  270. * @brief usb device class rx data process
  271. * @param udev: to the structure of usbd_core_type
  272. * @param recv_data: receive buffer
  273. * @retval receive data len
  274. */
  275. uint16_t usb_vcp_get_rxdata(void *udev, uint8_t *recv_data)
  276. {
  277. uint16_t i_index = 0;
  278. usbd_core_type *pudev = (usbd_core_type *)udev;
  279. uint16_t tmp_len = g_rxlen;
  280. if(g_rx_completed == 0)
  281. {
  282. return 0;
  283. }
  284. g_rx_completed = 0;
  285. tmp_len = g_rxlen;
  286. for(i_index = 0; i_index < g_rxlen; i_index ++)
  287. {
  288. recv_data[i_index] = g_rx_buff[i_index];
  289. }
  290. usbd_ept_recv(pudev, USBD_CDC_BULK_OUT_EPT, g_rx_buff, USBD_OUT_MAXPACKET_SIZE);
  291. return tmp_len;
  292. }
  293. /**
  294. * @brief usb device class send data
  295. * @param udev: to the structure of usbd_core_type
  296. * @param send_data: send data buffer
  297. * @param len: send length
  298. * @retval error status
  299. */
  300. error_status usb_vcp_send_data(void *udev, uint8_t *send_data, uint16_t len)
  301. {
  302. error_status status = SUCCESS;
  303. usbd_core_type *pudev = (usbd_core_type *)udev;
  304. if(g_tx_completed)
  305. {
  306. g_tx_completed = 0;
  307. usbd_ept_send(pudev, USBD_CDC_BULK_IN_EPT, send_data, len);
  308. }
  309. else
  310. {
  311. status = ERROR;
  312. }
  313. return status;
  314. }
  315. /**
  316. * @brief usb device class request function
  317. * @param udev: to the structure of usbd_core_type
  318. * @param cmd: request number
  319. * @param buff: request buffer
  320. * @param len: buffer length
  321. * @retval none
  322. */
  323. void usb_vcp_cmd_process(void *udev, uint8_t cmd, uint8_t *buff, uint16_t len)
  324. {
  325. switch(cmd)
  326. {
  327. case SET_LINE_CODING:
  328. linecoding.bitrate = (uint32_t)(buff[0] | (buff[1] << 8) | (buff[2] << 16) | (buff[3] <<24));
  329. linecoding.format = buff[4];
  330. linecoding.parity = buff[5];
  331. linecoding.data = buff[6];
  332. break;
  333. case GET_LINE_CODING:
  334. buff[0] = (uint8_t)linecoding.bitrate;
  335. buff[1] = (uint8_t)(linecoding.bitrate >> 8);
  336. buff[2] = (uint8_t)(linecoding.bitrate >> 16);
  337. buff[3] = (uint8_t)(linecoding.bitrate >> 24);
  338. buff[4] = (uint8_t)(linecoding.format);
  339. buff[5] = (uint8_t)(linecoding.parity);
  340. buff[6] = (uint8_t)(linecoding.data);
  341. break;
  342. default:
  343. break;
  344. }
  345. }
  346. /**
  347. * @}
  348. */
  349. /**
  350. * @}
  351. */
  352. /**
  353. * @}
  354. */