usb_hid.c 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455
  1. // Copyright 2021 IOsetting <iosetting(at)outlook.com>
  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. //
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. //
  9. // Unless required by applicable law or agreed to in writing, software
  10. // distributed under the License is distributed on an "AS IS" BASIS,
  11. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. // See the License for the specific language governing permissions and
  13. // limitations under the License.
  14. #include "fw_hal.h"
  15. #include <string.h>
  16. __CODE uint8_t DEVICEDESC[18];
  17. __CODE uint8_t CONFIGDESC[41];
  18. __CODE uint8_t HIDREPORTDESC[27];
  19. __CODE uint8_t LANGIDDESC[4];
  20. __CODE uint8_t MANUFACTDESC[8];
  21. __CODE uint8_t PRODUCTDESC[30];
  22. __XDATA uint8_t HidFreature[64];
  23. __XDATA uint8_t HidInput[64];
  24. __XDATA uint8_t HidOutput[64];
  25. USB_Request_t usb_request;
  26. USB_EP0_Stage_t usb_ep0_stag;
  27. void USB_Init();
  28. uint8_t CalCheckSum(uint8_t *buf, uint8_t len);
  29. void main()
  30. {
  31. GPIO_P3_SetMode(GPIO_Pin_0|GPIO_Pin_1, GPIO_Mode_Input_HIP);
  32. USB_Init();
  33. EXTI_Global_SetIntState(HAL_State_ON);
  34. memset(HidOutput, 0x00, sizeof(HidOutput));
  35. HidOutput[0] = 0xaa;
  36. HidOutput[1] = 0x55;
  37. HidOutput[2] = 0x02;
  38. HidOutput[3] = 0x01;
  39. HidOutput[4] = 0x02;
  40. HidOutput[5] = 0x01;
  41. HidOutput[6] = 0x02;
  42. HidOutput[7] = CalCheckSum(HidOutput,7);
  43. while (1);
  44. }
  45. void USB_Init()
  46. {
  47. SYS_EnableOscillator48M();
  48. USB_SetClockSource(USB_ClockSource_6M);
  49. USB_SetEnabled(HAL_State_ON);
  50. USB_SetDpDmPullUp(HAL_State_ON);
  51. EXTI_USB_SetIntPriority(EXTI_IntPriority_Highest);
  52. USB_WriteReg(FADDR, 0x00);
  53. USB_WriteReg(POWER, 0x08);
  54. USB_WriteReg(INTRIN1E, 0x3f);
  55. USB_WriteReg(INTROUT1E, 0x3f);
  56. USB_WriteReg(INTRUSBE, 0x00);
  57. USB_WriteReg(POWER, 0x01);
  58. usb_ep0_stag.bStage = USB_CtrlState_Idle;
  59. EXTI_USB_SetIntState(HAL_State_ON);
  60. }
  61. INTERRUPT(USB_Routine, EXTI_VectUSB)
  62. {
  63. uint8_t intrusb;
  64. uint8_t intrin;
  65. uint8_t introut;
  66. uint8_t csr;
  67. uint8_t cnt;
  68. uint16_t len = 0;
  69. intrusb = USB_ReadReg(INTRUSB);
  70. intrin = USB_ReadReg(INTRIN1);
  71. introut = USB_ReadReg(INTROUT1);
  72. /**
  73. * Reset Interrupt
  74. */
  75. if (intrusb & RSTIF)
  76. {
  77. USB_SelectEndPoint(1);
  78. USB_WriteReg(INCSR1, INCLRDT);
  79. USB_SelectEndPoint(1);
  80. USB_WriteReg(OUTCSR1, OUTCLRDT);
  81. usb_ep0_stag.bStage = USB_CtrlState_Idle;
  82. }
  83. /**
  84. * Endpoint-0 Interrupt
  85. */
  86. if (intrin & EP0IF)
  87. {
  88. USB_SelectEndPoint(0);
  89. csr = USB_ReadReg(CSR0);
  90. if (csr & STSTL) // Sent Stall
  91. {
  92. USB_WriteReg(CSR0, csr & ~STSTL);
  93. usb_ep0_stag.bStage = USB_CtrlState_Idle;
  94. }
  95. if (csr & SUEND) // Setup End
  96. {
  97. USB_WriteReg(CSR0, csr | SSUEND);
  98. }
  99. switch (usb_ep0_stag.bStage)
  100. {
  101. case USB_CtrlState_Idle:
  102. if (csr & OPRDY) // Out Packet Ready
  103. {
  104. usb_ep0_stag.bStage = USB_CtrlState_SettingUp;
  105. USB_ReadFIFO(FIFO0, (uint8_t *)&usb_request);
  106. ((uint8_t *)&usb_ep0_stag.wResidue)[0] = usb_request.wLength.bb.bh;
  107. ((uint8_t *)&usb_ep0_stag.wResidue)[1] = usb_request.wLength.bb.bl;
  108. switch (usb_request.bmRequestType & REQUEST_TYPE_MASK)
  109. {
  110. case USB_RequestType_Standard:
  111. switch (usb_request.bRequest)
  112. {
  113. case USB_StdReq_SetAddress:
  114. USB_WriteReg(FADDR, usb_request.wValue.bb.bl);
  115. break;
  116. case USB_StdReq_SetConfiguration:
  117. USB_SelectEndPoint(1);
  118. USB_WriteReg(INCSR2, INMODEIN);
  119. USB_WriteReg(INMAXP, 8);
  120. USB_SelectEndPoint(1);
  121. USB_WriteReg(INCSR2, INMODEOUT);
  122. USB_WriteReg(OUTMAXP, 8);
  123. USB_SelectEndPoint(0);
  124. break;
  125. case USB_StdReq_GetDescriptor:
  126. usb_ep0_stag.bStage = USB_CtrlState_DataIn;
  127. switch (usb_request.wValue.bb.bh)
  128. {
  129. case USB_DescriptorType_Device:
  130. usb_ep0_stag.pData = (uint8_t *)DEVICEDESC;
  131. len = sizeof(DEVICEDESC);
  132. break;
  133. case USB_DescriptorType_Configuration:
  134. usb_ep0_stag.pData = (uint8_t *)CONFIGDESC;
  135. len = sizeof(CONFIGDESC);
  136. break;
  137. case USB_DescriptorType_String:
  138. switch (usb_request.wValue.bb.bl)
  139. {
  140. case 0:
  141. usb_ep0_stag.pData = (uint8_t *)LANGIDDESC;
  142. len = sizeof(LANGIDDESC);
  143. break;
  144. case 1:
  145. usb_ep0_stag.pData = (uint8_t *)MANUFACTDESC;
  146. len = sizeof(MANUFACTDESC);
  147. break;
  148. case 2:
  149. usb_ep0_stag.pData = (uint8_t *)PRODUCTDESC;
  150. len = sizeof(PRODUCTDESC);
  151. break;
  152. default:
  153. usb_ep0_stag.bStage = USB_CtrlState_Stalled;
  154. break;
  155. }
  156. break;
  157. case USB_DescriptorType_Report:
  158. usb_ep0_stag.pData = (uint8_t *)HIDREPORTDESC;
  159. len = sizeof(HIDREPORTDESC);
  160. break;
  161. default:
  162. usb_ep0_stag.bStage = USB_CtrlState_Stalled;
  163. break;
  164. }
  165. if (len < usb_ep0_stag.wResidue)
  166. {
  167. usb_ep0_stag.wResidue = len;
  168. }
  169. break;
  170. default:
  171. usb_ep0_stag.bStage = USB_CtrlState_Stalled;
  172. break;
  173. }
  174. break;
  175. case USB_RequestType_Class:
  176. switch (usb_request.bRequest)
  177. {
  178. case USB_HidReq_GetReport:
  179. usb_ep0_stag.pData = HidFreature;
  180. usb_ep0_stag.bStage = USB_CtrlState_DataIn;
  181. break;
  182. case USB_HidReq_SetReport:
  183. usb_ep0_stag.pData = HidFreature;
  184. usb_ep0_stag.bStage = USB_CtrlState_DataOut;
  185. break;
  186. case USB_HidReq_SetIdle:
  187. break;
  188. // case USB_HidReq_GetIdle:
  189. // case USB_HidReq_GetProtocol:
  190. // case USB_HidReq_SetProtocol:
  191. default:
  192. usb_ep0_stag.bStage = USB_CtrlState_Stalled;
  193. break;
  194. }
  195. break;
  196. default:
  197. usb_ep0_stag.bStage = USB_CtrlState_Stalled;
  198. break;
  199. }
  200. switch (usb_ep0_stag.bStage)
  201. {
  202. case USB_CtrlState_DataIn:
  203. USB_WriteReg(CSR0, SOPRDY);
  204. goto L_Ep0SendData;
  205. break;
  206. case USB_CtrlState_DataOut:
  207. USB_WriteReg(CSR0, SOPRDY);
  208. break;
  209. case USB_CtrlState_SettingUp:
  210. USB_WriteReg(CSR0, SOPRDY | DATEND);
  211. usb_ep0_stag.bStage = USB_CtrlState_Idle;
  212. break;
  213. case USB_CtrlState_Stalled:
  214. USB_WriteReg(CSR0, SOPRDY | SDSTL);
  215. usb_ep0_stag.bStage = USB_CtrlState_Idle;
  216. break;
  217. }
  218. }
  219. break;
  220. case USB_CtrlState_DataIn:
  221. if (!(csr & IPRDY))
  222. {
  223. L_Ep0SendData:
  224. cnt = usb_ep0_stag.wResidue > 64 ? 64 : usb_ep0_stag.wResidue;
  225. USB_WriteFIFO(FIFO0, usb_ep0_stag.pData, cnt);
  226. usb_ep0_stag.wResidue -= cnt;
  227. usb_ep0_stag.pData += cnt;
  228. if (usb_ep0_stag.wResidue == 0)
  229. {
  230. USB_WriteReg(CSR0, IPRDY | DATEND);
  231. usb_ep0_stag.bStage = USB_CtrlState_Idle;
  232. }
  233. else
  234. {
  235. USB_WriteReg(CSR0, IPRDY);
  236. }
  237. }
  238. break;
  239. case USB_CtrlState_DataOut:
  240. if (csr & OPRDY)
  241. {
  242. cnt = USB_ReadFIFO(FIFO0, usb_ep0_stag.pData);
  243. usb_ep0_stag.wResidue -= cnt;
  244. usb_ep0_stag.pData += cnt;
  245. if (usb_ep0_stag.wResidue == 0)
  246. {
  247. USB_WriteReg(CSR0, SOPRDY | DATEND);
  248. usb_ep0_stag.bStage = USB_CtrlState_Idle;
  249. }
  250. else
  251. {
  252. USB_WriteReg(CSR0, SOPRDY);
  253. }
  254. }
  255. break;
  256. }
  257. }
  258. /**
  259. * Endpoint-1 In Interrupt
  260. */
  261. if (intrin & EP1INIF)
  262. {
  263. USB_SelectEndPoint(1);
  264. csr = USB_ReadReg(INCSR1);
  265. if (csr & INSTSTL)
  266. {
  267. USB_WriteReg(INCSR1, INCLRDT);
  268. }
  269. if (csr & INUNDRUN)
  270. {
  271. USB_WriteReg(INCSR1, 0);
  272. }
  273. }
  274. /**
  275. * Endpoint-1 Out Interrupt
  276. */
  277. if (introut & EP1OUTIF)
  278. {
  279. USB_SelectEndPoint(1);
  280. csr = USB_ReadReg(OUTCSR1);
  281. if (csr & OUTSTSTL)
  282. {
  283. USB_WriteReg(OUTCSR1, OUTCLRDT);
  284. }
  285. if (csr & OUTOPRDY)
  286. {
  287. USB_ReadFIFO(FIFO1, HidInput);
  288. USB_WriteReg(OUTCSR1, 0);
  289. /** Write response */
  290. if((HidInput[0] == 0xaa) && (HidInput[1] == 0x55) && (HidInput[2] == 0x01))
  291. {
  292. USB_SelectEndPoint(1);
  293. USB_WriteFIFO(FIFO1, HidOutput, 64);
  294. USB_WriteReg(INCSR1, INIPRDY);
  295. }
  296. }
  297. }
  298. }
  299. __CODE uint8_t DEVICEDESC[18] =
  300. {
  301. 0x12, //bLength(18);
  302. 0x01, //bDescriptorType(Device);
  303. 0x00,0x02, //bcdUSB(2.00);
  304. 0x00, //bDeviceClass(0);
  305. 0x00, //bDeviceSubClass0);
  306. 0x00, //bDeviceProtocol(0);
  307. 0x40, //bMaxPacketSize0(64);
  308. 0x54,0x53, //idVendor(5354);
  309. 0x80,0x43, //idProduct(4380);
  310. 0x00,0x01, //bcdDevice(1.00);
  311. 0x01, //iManufacturer(1);
  312. 0x02, //iProduct(2);
  313. 0x00, //iSerialNumber(0);
  314. 0x01, //bNumConfigurations(1);
  315. };
  316. __CODE uint8_t CONFIGDESC[41] =
  317. {
  318. 0x09, //bLength(9);
  319. 0x02, //bDescriptorType(Configuration);
  320. 0x29,0x00, //wTotalLength(41);
  321. 0x01, //bNumInterfaces(1);
  322. 0x01, //bConfigurationValue(1);
  323. 0x00, //iConfiguration(0);
  324. 0x80, //bmAttributes(BUSPower);
  325. 0x32, //MaxPower(100mA);
  326. 0x09, //bLength(9);
  327. 0x04, //bDescriptorType(Interface);
  328. 0x00, //bInterfaceNumber(0);
  329. 0x00, //bAlternateSetting(0);
  330. 0x02, //bNumEndpoints(2);
  331. 0x03, //bInterfaceClass(HID);
  332. 0x00, //bInterfaceSubClass(0);
  333. 0x00, //bInterfaceProtocol(0);
  334. 0x00, //iInterface(0);
  335. 0x09, //bLength(9);
  336. 0x21, //bDescriptorType(HID);
  337. 0x01,0x01, //bcdHID(1.01);
  338. 0x00, //bCountryCode(0);
  339. 0x01, //bNumDescriptors(1);
  340. 0x22, //bDescriptorType(HID Report);
  341. 0x1b,0x00, //wDescriptorLength(27);
  342. 0x07, //bLength(7);
  343. 0x05, //bDescriptorType(Endpoint);
  344. 0x81, //bEndpointAddress(EndPoint1 as IN);
  345. 0x03, //bmAttributes(Interrupt);
  346. 0x40,0x00, //wMaxPacketSize(64);
  347. 0x01, //bInterval(10ms);
  348. 0x07, //bLength(7);
  349. 0x05, //bDescriptorType(Endpoint);
  350. 0x01, //bEndpointAddress(EndPoint1 as OUT);
  351. 0x03, //bmAttributes(Interrupt);
  352. 0x40,0x00, //wMaxPacketSize(64);
  353. 0x01, //bInterval(10ms);
  354. };
  355. __CODE uint8_t HIDREPORTDESC[27] =
  356. {
  357. 0x05,0x0c, //USAGE_PAGE(Consumer);
  358. 0x09,0x01, //USAGE(Consumer Control);
  359. 0xa1,0x01, //COLLECTION(Application);
  360. 0x15,0x00, // LOGICAL_MINIMUM(0);
  361. 0x25,0xff, // LOGICAL_MAXIMUM(255);
  362. 0x75,0x08, // REPORT_SIZE(8);
  363. 0x95,0x40, // REPORT_COUNT(64);
  364. 0x09,0x01, // USAGE(Consumer Control);
  365. 0xb1,0x02, // FEATURE(Data,Variable);
  366. 0x09,0x01, // USAGE(Consumer Control);
  367. 0x81,0x02, // INPUT(Data,Variable);
  368. 0x09,0x01, // USAGE(Consumer Control);
  369. 0x91,0x02, // OUTPUT(Data,Variable);
  370. 0xc0, //END_COLLECTION;
  371. };
  372. __CODE uint8_t LANGIDDESC[4] =
  373. {
  374. 0x04,0x03,
  375. 0x09,0x04,
  376. };
  377. __CODE uint8_t MANUFACTDESC[8] =
  378. {
  379. 0x08,0x03,
  380. 'S',0,
  381. 'T',0,
  382. 'C',0,
  383. };
  384. __CODE uint8_t PRODUCTDESC[30] =
  385. {
  386. 0x1e,0x03,
  387. 'S',0,
  388. 'T',0,
  389. 'C',0,
  390. '8',0,
  391. ' ',0,
  392. 'F',0,
  393. 'w',0,
  394. 'L',0,
  395. 'i',0,
  396. 'b',0,
  397. ' ',0,
  398. 'H',0,
  399. 'I',0,
  400. 'D',0,
  401. };
  402. uint8_t CalCheckSum(uint8_t *buf, uint8_t len)
  403. {
  404. uint8_t i;
  405. uint8_t cs=0;
  406. for (i = 0; i < len; i++)
  407. {
  408. cs += buf[i];
  409. }
  410. return cs;
  411. }