usb_dc_aic.c 53 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661
  1. /*
  2. * Copyright (c) 2023-2024, ArtInChip Technology Co., Ltd
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. */
  6. #include <rtconfig.h>
  7. #include "usbd_core.h"
  8. #include "usb_dc_aic_reg.h"
  9. // clang-format off
  10. #ifndef __UNALIGNED_UINT32_WRITE
  11. #pragma GCC diagnostic push
  12. #pragma GCC diagnostic ignored "-Wpacked"
  13. #pragma GCC diagnostic ignored "-Wattributes"
  14. __PACKED_STRUCT T_UINT32_WRITE { uint32_t v; };
  15. #pragma GCC diagnostic pop
  16. #define __UNALIGNED_UINT32_WRITE(addr, val) (void)((((struct T_UINT32_WRITE *)(void *)(addr))->v) = (val))
  17. #endif
  18. #ifndef __UNALIGNED_UINT32_READ
  19. #pragma GCC diagnostic push
  20. #pragma GCC diagnostic ignored "-Wpacked"
  21. #pragma GCC diagnostic ignored "-Wattributes"
  22. __PACKED_STRUCT T_UINT32_READ { uint32_t v; };
  23. #pragma GCC diagnostic pop
  24. #define __UNALIGNED_UINT32_READ(addr) (((const struct T_UINT32_READ *)(const void *)(addr))->v)
  25. #endif
  26. // clang-format on
  27. #define FS_PORT 0
  28. #define HS_PORT 1
  29. #ifndef CONFIG_USB_AIC_DC_PORT
  30. #error "please select CONFIG_USB_AIC_DC_PORT with FS_PORT or HS_PORT"
  31. #endif
  32. #ifndef USB_BASE
  33. #define USB_BASE CONFIG_USB_AIC_DC_BASE
  34. #endif
  35. #ifdef LPKG_CHERRYUSB_DEVICE_HID_IO_TEMPLATE
  36. #define USB_RAM_SIZE 1024 /* define with maximum value*/
  37. #else
  38. #define USB_RAM_SIZE 512 /* define with maximum value*/
  39. #endif
  40. #ifndef USB_NUM_BIDIR_ENDPOINTS
  41. #define USB_NUM_BIDIR_ENDPOINTS 5 /* define with minimum value*/
  42. #endif
  43. /* USB_P_TXFIFO_NUM:
  44. * There are only 2 Periodic_TXFIFO, and each Interrupt/Isochronous In ep
  45. * needs to request one P_TXFIFO. So, only two Interrupt/Isochronous In ep
  46. * can be requested for at most.
  47. */
  48. #define USB_P_TXFIFO_NUM 2
  49. #define AIC_UDC_REG ((AIC_UDC_RegDef *)(USB_BASE))
  50. #define AIC_EP_FIFO(i) *(__IO uint32_t *)(USB_BASE + AIC_EP_FIFO_BASE + ((i)*AIC_EP_FIFO_SIZE))
  51. /* Endpoint state */
  52. struct aic_ep_state {
  53. uint16_t ep_mps; /* Endpoint max packet size */
  54. uint8_t ep_type; /* Endpoint type */
  55. uint8_t ep_stalled; /* Endpoint stall flag */
  56. uint8_t *xfer_buf;
  57. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  58. uint8_t *xfer_align_buf;
  59. uint32_t xfer_align_len;
  60. #endif
  61. uint32_t xfer_len;
  62. uint32_t actual_xfer_len;
  63. };
  64. extern uint32_t usbd_clk;
  65. /* Driver state */
  66. /*USB_NOCACHE_RAM_SECTION*/ struct aic_udc {
  67. USB_MEM_ALIGNX struct usb_setup_packet setup;
  68. USB_MEM_ALIGNX struct aic_ep_state in_ep[USB_NUM_BIDIR_ENDPOINTS]; /*!< IN endpoint parameters*/
  69. struct aic_ep_state out_ep[USB_NUM_BIDIR_ENDPOINTS]; /*!< OUT endpoint parameters */
  70. struct usb_endpoint_descriptor in_ep_desc[USB_NUM_BIDIR_ENDPOINTS];
  71. uint32_t p_txfifo_map; /* map which periodic_txfifo is used */
  72. uint32_t np_txfifo_map; /* map no-periodic_txfifo is used */
  73. } g_aic_udc;
  74. #define AIC_EP0_SETUP 1
  75. #define AIC_EP0_DATA_IN 2
  76. #define AIC_EP0_STATUS_OUT 3
  77. #define AIC_EP0_DATA_OUT 12
  78. #define AIC_EP0_STATUS_IN 13
  79. uint8_t ep0_ctrl_stage = 0; /* 1 = setup stage, 2 = data stage, 3 = status stage */
  80. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  81. static uint8_t g_aic_udc_ibuf[USB_RAM_SIZE] __ALIGNED(CACHE_LINE_SIZE);
  82. static uint8_t g_aic_udc_obuf[USB_RAM_SIZE] __ALIGNED(CACHE_LINE_SIZE);
  83. void aic_udc_dcache_clean(uintptr_t addr, uint32_t len)
  84. {
  85. aicos_dcache_clean_range((size_t *)addr, len);
  86. }
  87. void aic_udc_dcache_invalidate(uintptr_t addr, uint32_t len)
  88. {
  89. aicos_dcache_invalid_range((size_t *)addr, len);
  90. }
  91. void aic_udc_dcache_clean_invalidate(uintptr_t addr, uint32_t len)
  92. {
  93. aicos_dcache_clean_invalid_range((size_t *)addr, len);
  94. }
  95. static int aic_udc_ep_buf_alloc(struct aic_ep_state *ep, uint32_t len,
  96. uint8_t *sbuf)
  97. {
  98. ep->xfer_len = len;
  99. if (len % CACHE_LINE_SIZE)
  100. ep->xfer_align_len = ALIGN_UP(len, CACHE_LINE_SIZE);
  101. else
  102. ep->xfer_align_len = len;
  103. if (ep->xfer_align_len > USB_RAM_SIZE) {
  104. ep->xfer_align_buf = aicos_malloc_align(0, ep->xfer_align_len,
  105. CACHE_LINE_SIZE);
  106. USB_LOG_DBG("aicos_malloc_align %d bytes.", ep->xfer_align_len);
  107. if (!ep->xfer_align_buf) {
  108. USB_LOG_ERR("alloc error.\r\n");
  109. return -5;
  110. }
  111. } else {
  112. ep->xfer_align_buf = sbuf;
  113. }
  114. return 0;
  115. }
  116. static void aic_udc_ep_buf_free(struct aic_ep_state *ep, uint8_t *sbuf)
  117. {
  118. if (!ep->xfer_align_buf)
  119. return;
  120. /* Whether the buf is allocated dynamically */
  121. if (ep->xfer_align_buf != sbuf) {
  122. USB_LOG_DBG("aicos_free_align %d bytes.", ep->xfer_align_len);
  123. aicos_free_align(0, ep->xfer_align_buf);
  124. }
  125. ep->xfer_align_buf = NULL;
  126. ep->xfer_align_len = 0;
  127. }
  128. static int aic_udc_ibuf_alloc(struct aic_ep_state *ep, uint32_t len)
  129. {
  130. return aic_udc_ep_buf_alloc(ep, len, g_aic_udc_ibuf);
  131. }
  132. static int aic_udc_obuf_alloc(struct aic_ep_state *ep, uint32_t len)
  133. {
  134. return aic_udc_ep_buf_alloc(ep, len, g_aic_udc_obuf);
  135. }
  136. static void aic_udc_ibuf_free(struct aic_ep_state *ep)
  137. {
  138. aic_udc_ep_buf_free(ep, g_aic_udc_ibuf);
  139. }
  140. static void aic_udc_obuf_free(struct aic_ep_state *ep)
  141. {
  142. aic_udc_ep_buf_free(ep, g_aic_udc_obuf);
  143. }
  144. #else
  145. #define aic_udc_dcache_clean(addr, len)
  146. #define aic_udc_dcache_invalidate(addr, len)
  147. #define aic_udc_dcache_clean_invalidate(addr, len)
  148. #endif
  149. static void aic_set_dma_nextep(void)
  150. {
  151. uint32_t i;
  152. uint32_t inepcfg = 0;
  153. /* dma to set the next-endpoint pointer. */
  154. for (i = 0; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  155. uint32_t next = ((i + 1) % USB_NUM_BIDIR_ENDPOINTS) << DEPCTL_NEXT_EP_BIT;
  156. inepcfg = readl(&AIC_UDC_REG->inepcfg[i]);
  157. inepcfg &= ~DEPCTL_NEXT_EP_MASK;
  158. inepcfg |= next;
  159. writel(inepcfg, &AIC_UDC_REG->inepcfg[i]);
  160. }
  161. }
  162. static inline int aic_reset(void)
  163. {
  164. uint32_t count = 0U;
  165. uint32_t tmpreg = 0;
  166. /* Wait for AHB master IDLE state. */
  167. do {
  168. if (++count > 200000U) {
  169. return -1;
  170. }
  171. tmpreg = readl(&AIC_UDC_REG->ahbbasic);
  172. } while ((tmpreg & AHBBASIC_AHBIDLE) == 0U);
  173. /* Core Soft Reset */
  174. count = 0U;
  175. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  176. tmpreg |= USBDEVINIT_CSFTRST;
  177. writel(tmpreg, &AIC_UDC_REG->usbdevinit);
  178. do {
  179. if (++count > 200000U) {
  180. return -1;
  181. }
  182. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  183. } while ((tmpreg & USBDEVINIT_CSFTRST) == USBDEVINIT_CSFTRST);
  184. return 0;
  185. }
  186. static inline int aic_core_init(void)
  187. {
  188. int ret;
  189. uint32_t usb_gusbcfg =
  190. 0 << 19 /* ULPI Clock SuspendM */
  191. | 0 << 18 /* ULPI Phy Auto Resume */
  192. | 0 << 15 /* PHY Low Power Clock sel */
  193. | 0x5 << 10 /* USB Turnaround time (0x5 for HS phy) */
  194. | 0 << 7 /* ULPI DDR sel 0:single 8bit, 1:double 4bit */
  195. /*| 0 << 6 0: high speed utmi+, 1: full speed serial*/
  196. #ifdef FPGA_BOARD_ARTINCHIP
  197. | 1 << 4 /* 0: utmi+, 1:ulpi*/
  198. #else
  199. | 0 << 4 /* 0: utmi+, 1:ulpi*/
  200. #endif
  201. | 0 << 3 /* UTMI+ PHY 0:8bit, 1:16bit (ULPI PHY set 8bit) */
  202. | 0x7 << 0; /* HS/FS timeout calibration**/
  203. /* Activate the USB Transceiver */
  204. writel(usb_gusbcfg, &AIC_UDC_REG->usbphyif);
  205. /* Reset after a PHY select */
  206. ret = aic_reset();
  207. aic_set_dma_nextep();
  208. return ret;
  209. }
  210. static inline int aic_flush_rxfifo(void)
  211. {
  212. uint32_t count = 0;
  213. uint32_t tmpreg = 0;
  214. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  215. tmpreg |= USBDEVINIT_RXFFLSH;
  216. writel(tmpreg, &AIC_UDC_REG->usbdevinit);
  217. do {
  218. if (++count > 200000U) {
  219. return -1;
  220. }
  221. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  222. } while ((tmpreg & USBDEVINIT_RXFFLSH) == USBDEVINIT_RXFFLSH);
  223. return 0;
  224. }
  225. static inline int aic_flush_txfifo(uint32_t num)
  226. {
  227. uint32_t count = 0U;
  228. uint32_t tmpreg = 0;
  229. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  230. tmpreg &= ~ USBDEVINIT_TXFNUM(USBDEVINIT_TXFNUM_LIMIT);
  231. tmpreg |= USBDEVINIT_TXFNUM(num & USBDEVINIT_TXFNUM_LIMIT)
  232. | USBDEVINIT_TXFFLSH;
  233. writel(tmpreg, &AIC_UDC_REG->usbdevinit);
  234. do {
  235. if (++count > 200000U) {
  236. return -1;
  237. }
  238. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  239. } while ((tmpreg & USBDEVINIT_TXFFLSH) == USBDEVINIT_TXFFLSH);
  240. return 0;
  241. }
  242. static void aic_set_turnaroundtime(uint32_t hclk, uint8_t speed)
  243. {
  244. uint32_t UsbTrd;
  245. uint32_t tmpreg = 0;
  246. /* The USBTRD is configured according to the tables below, depending on AHB frequency
  247. used by application. In the low AHB frequency range it is used to stretch enough the USB response
  248. time to IN tokens, the USB turnaround time, so to compensate for the longer AHB read access
  249. latency to the Data FIFO */
  250. if (speed == USB_ENUM_SPEED_FULL) {
  251. if ((hclk >= 14200000U) && (hclk < 15000000U)) {
  252. /* hclk Clock Range between 14.2-15 MHz */
  253. UsbTrd = 0xFU;
  254. } else if ((hclk >= 15000000U) && (hclk < 16000000U)) {
  255. /* hclk Clock Range between 15-16 MHz */
  256. UsbTrd = 0xEU;
  257. } else if ((hclk >= 16000000U) && (hclk < 17200000U)) {
  258. /* hclk Clock Range between 16-17.2 MHz */
  259. UsbTrd = 0xDU;
  260. } else if ((hclk >= 17200000U) && (hclk < 18500000U)) {
  261. /* hclk Clock Range between 17.2-18.5 MHz */
  262. UsbTrd = 0xCU;
  263. } else if ((hclk >= 18500000U) && (hclk < 20000000U)) {
  264. /* hclk Clock Range between 18.5-20 MHz */
  265. UsbTrd = 0xBU;
  266. } else if ((hclk >= 20000000U) && (hclk < 21800000U)) {
  267. /* hclk Clock Range between 20-21.8 MHz */
  268. UsbTrd = 0xAU;
  269. } else if ((hclk >= 21800000U) && (hclk < 24000000U)) {
  270. /* hclk Clock Range between 21.8-24 MHz */
  271. UsbTrd = 0x9U;
  272. } else if ((hclk >= 24000000U) && (hclk < 27700000U)) {
  273. /* hclk Clock Range between 24-27.7 MHz */
  274. UsbTrd = 0x8U;
  275. } else if ((hclk >= 27700000U) && (hclk < 32000000U)) {
  276. /* hclk Clock Range between 27.7-32 MHz */
  277. UsbTrd = 0x7U;
  278. } else {/* if(hclk >= 32000000) */
  279. /* hclk Clock Range between 32-200 MHz */
  280. UsbTrd = 0x6U;
  281. }
  282. } else if (speed == USB_ENUM_SPEED_HIGH) {
  283. UsbTrd = USBPHYIF_HS_TRDT_VALUE;
  284. } else {
  285. UsbTrd = USBPHYIF_DEFAULT_TRDT_VALUE;
  286. }
  287. tmpreg = readl(&AIC_UDC_REG->usbphyif);
  288. tmpreg |= USBPHYIF_TOUTCAL_LIMIT;
  289. tmpreg &= ~USBPHYIF_USBTRDTIM_MASK;
  290. tmpreg |= (uint32_t)((UsbTrd << USBPHYIF_USBTRDTIM_SHIFT)
  291. & USBPHYIF_USBTRDTIM_MASK);
  292. writel(tmpreg, &AIC_UDC_REG->usbphyif);
  293. }
  294. #if 0
  295. static void aic_set_txfifo(uint8_t fifo, uint16_t size)
  296. {
  297. uint8_t i;
  298. uint32_t Tx_Offset;
  299. /* TXn min size = 16 words. (n : Transmit FIFO index)
  300. When a TxFIFO is not used, the Configuration should be as follows:
  301. case 1 : n > m and Txn is not used (n,m : Transmit FIFO indexes)
  302. --> Txm can use the space allocated for Txn.
  303. case2 : n < m and Txn is not used (n,m : Transmit FIFO indexes)
  304. --> Txn should be configured with the minimum space of 16 words
  305. The FIFO is used optimally when used TxFIFOs are allocated in the top
  306. of the FIFO.Ex: use EP1 and EP2 as IN instead of EP1 and EP3 as IN ones.
  307. When DMA is used 3n * FIFO locations should be reserved for internal DMA registers */
  308. Tx_Offset = AIC_UDC_REG->rxfifosiz;
  309. if (fifo == 0U) {
  310. AIC_UDC_REG->nptxfifosiz = ((uint32_t)size << 16) | Tx_Offset;
  311. } else {
  312. Tx_Offset += (AIC_UDC_REG->nptxfifosiz) >> 16;
  313. for (i = 0U; i < (fifo - 1U); i++) {
  314. Tx_Offset += (AIC_UDC_REG->txfifosiz[i] >> 16);
  315. }
  316. /* Multiply Tx_Size by 2 to get higher performance */
  317. AIC_UDC_REG->txfifosiz[fifo - 1U] = ((uint32_t)size << 16) | Tx_Offset;
  318. }
  319. }
  320. #endif
  321. static uint8_t aic_get_devspeed(void)
  322. {
  323. uint8_t speed;
  324. uint32_t DevEnumSpeed = readl(&AIC_UDC_REG->usblinests);
  325. DevEnumSpeed &= USB_ENUM_SPEED_MASK;
  326. if (DevEnumSpeed == USB_HIGH_30_60MHZ) {
  327. speed = USB_ENUM_SPEED_HIGH;
  328. } else if (DevEnumSpeed == USB_FULL_30_60MHZ) {
  329. speed = USB_ENUM_SPEED_FULL;
  330. } else {
  331. speed = 0xFU;
  332. }
  333. return speed;
  334. }
  335. static void aic_ep0_start_read_setup(uint8_t *psetup)
  336. {
  337. uint32_t outepcfg = 0;
  338. g_aic_udc.out_ep[0].xfer_buf = psetup;
  339. g_aic_udc.out_ep[0].xfer_len = 8;
  340. ep0_ctrl_stage = AIC_EP0_SETUP;
  341. USB_LOG_DBG("\r\n");
  342. USB_LOG_DBG("[1]: Control transfer start read setup.");
  343. aic_udc_dcache_invalidate((uintptr_t)psetup, CACHE_LINE_SIZE);
  344. writel((1<<29) | (DXEPTSIZ_PKT_CNT_MASK & (1U << 19)) | (8U), &AIC_UDC_REG->outeptsfsiz[0]);
  345. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  346. writel((uint32_t)(uintptr_t)psetup, &AIC_UDC_REG->outepdmaaddr[0]);
  347. #endif
  348. writel(0xFFFFFFFFU, &AIC_UDC_REG->outepint[0]);
  349. /* EP enable */
  350. outepcfg = readl(&AIC_UDC_REG->outepcfg[0]);
  351. outepcfg |= DEPCTL_CNAK | DEPCTL_EPENA | DEPCTL_USBACTEP;
  352. writel(outepcfg, &AIC_UDC_REG->outepcfg[0]);
  353. }
  354. void aic_ep_write(uint8_t ep_idx, uint8_t *src, uint16_t len)
  355. {
  356. uint32_t *pSrc = (uint32_t *)src;
  357. uint32_t count32b, i;
  358. count32b = ((uint32_t)len + 3U) / 4U;
  359. for (i = 0U; i < count32b; i++) {
  360. AIC_EP_FIFO(ep_idx) = __UNALIGNED_UINT32_READ(pSrc);
  361. pSrc++;
  362. }
  363. }
  364. void aic_ep_read(uint8_t *dest, uint16_t len)
  365. {
  366. uint32_t *pDest = (uint32_t *)dest;
  367. uint32_t i;
  368. uint32_t count32b = ((uint32_t)len + 3U) / 4U;
  369. for (i = 0U; i < count32b; i++) {
  370. __UNALIGNED_UINT32_WRITE(pDest, AIC_EP_FIFO(0U));
  371. pDest++;
  372. }
  373. }
  374. #ifndef CONFIG_USB_AIC_DMA_ENABLE
  375. static void aic_tx_fifo_empty_procecss(uint8_t ep_idx)
  376. {
  377. uint32_t len;
  378. //uint32_t len32b;
  379. len = g_aic_udc.in_ep[ep_idx].xfer_len - g_aic_udc.in_ep[ep_idx].actual_xfer_len;
  380. if (len > g_aic_udc.in_ep[ep_idx].ep_mps) {
  381. len = g_aic_udc.in_ep[ep_idx].ep_mps;
  382. }
  383. //len32b = (len + 3U) / 4U;
  384. while (/*((AIC_UDC_REG->ineptxsts[ep_idx] & INEPTXSTS_IN_EP_TXFIFO_STS) >= len32b) &&*/
  385. (g_aic_udc.in_ep[ep_idx].actual_xfer_len < g_aic_udc.in_ep[ep_idx].xfer_len) && (g_aic_udc.in_ep[ep_idx].xfer_len != 0U)) {
  386. /* Write the FIFO */
  387. len = g_aic_udc.in_ep[ep_idx].xfer_len - g_aic_udc.in_ep[ep_idx].actual_xfer_len;
  388. if (len > g_aic_udc.in_ep[ep_idx].ep_mps) {
  389. len = g_aic_udc.in_ep[ep_idx].ep_mps;
  390. }
  391. aic_ep_write(ep_idx, g_aic_udc.in_ep[ep_idx].xfer_buf, len);
  392. g_aic_udc.in_ep[ep_idx].xfer_buf += len;
  393. g_aic_udc.in_ep[ep_idx].actual_xfer_len += len;
  394. }
  395. }
  396. #endif
  397. /**
  398. * @brief aic_get_glb_intstatus: return the global USB interrupt status
  399. * @retval status
  400. */
  401. static inline uint32_t aic_get_glb_intstatus(void)
  402. {
  403. uint32_t tmpreg;
  404. uint32_t mask;
  405. tmpreg = readl(&AIC_UDC_REG->usbintsts);
  406. mask = readl(&AIC_UDC_REG->usbintmsk);
  407. return tmpreg & mask;
  408. }
  409. /**
  410. * @brief aic_get_outeps_intstatus: return the USB device OUT endpoints interrupt status
  411. * @retval status
  412. */
  413. static inline uint32_t aic_get_outeps_intstatus(void)
  414. {
  415. uint32_t tmpreg;
  416. uint32_t mask;
  417. tmpreg = readl(&AIC_UDC_REG->usbepint);
  418. mask = readl(&AIC_UDC_REG->usbepintmsk);
  419. return (((tmpreg & mask) & 0xffff0000U) >> 16);
  420. }
  421. /**
  422. * @brief aic_get_ineps_intstatus: return the USB device IN endpoints interrupt status
  423. * @retval status
  424. */
  425. static inline uint32_t aic_get_ineps_intstatus(void)
  426. {
  427. uint32_t tmpreg;
  428. uint32_t mask;
  429. tmpreg = readl(&AIC_UDC_REG->usbepint);
  430. mask = readl(&AIC_UDC_REG->usbepintmsk);
  431. return ((tmpreg & mask) & 0xFFFFU);
  432. }
  433. /**
  434. * @brief Returns Device OUT EP Interrupt register
  435. * @param epnum endpoint number
  436. * This parameter can be a value from 0 to 15
  437. * @retval Device OUT EP Interrupt register
  438. */
  439. static inline uint32_t aic_get_outep_intstatus(uint8_t epnum)
  440. {
  441. uint32_t tmpreg;
  442. uint32_t mask;
  443. tmpreg = readl(&AIC_UDC_REG->outepint[epnum]);
  444. USB_LOG_DBG("[int]: Out ep%d outepint = 0x%x [%d].", epnum, tmpreg, ep0_ctrl_stage);
  445. mask = readl(&AIC_UDC_REG->outepintmsk);
  446. return tmpreg & mask;
  447. }
  448. /**
  449. * @brief Returns Device IN EP Interrupt register
  450. * @param epnum endpoint number
  451. * This parameter can be a value from 0 to 15
  452. * @retval Device IN EP Interrupt register
  453. */
  454. static inline uint32_t aic_get_inep_intstatus(uint8_t epnum)
  455. {
  456. uint32_t tmpreg;
  457. uint32_t mask;
  458. tmpreg = readl(&AIC_UDC_REG->inepint[epnum]);
  459. USB_LOG_DBG("[int]: In ep%d inepint = 0x%x [%d].", epnum, tmpreg, ep0_ctrl_stage);
  460. mask = readl(&AIC_UDC_REG->inepintmsk);
  461. return tmpreg & mask;
  462. }
  463. __WEAK void usb_dc_low_level_init(void)
  464. {
  465. }
  466. __WEAK void usb_dc_low_level_deinit(void)
  467. {
  468. }
  469. int usb_dc_rst(void)
  470. {
  471. uint32_t outepintmsk = 0;
  472. uint32_t inepintmsk = 0;
  473. USB_LOG_DBG("usb_dc_rst.\n");
  474. usbd_set_address(0);
  475. aic_flush_txfifo(0x10U);
  476. aic_flush_rxfifo();
  477. for (uint8_t i = 0U; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  478. if (i == 0U) {
  479. writel(DEPCTL_SNAK, &AIC_UDC_REG->inepcfg[i]);
  480. writel(DEPCTL_SNAK, &AIC_UDC_REG->outepcfg[i]);
  481. } else {
  482. usbd_ep_close(i);
  483. usbd_ep_close(i | 0x80);
  484. }
  485. writel(0U, &AIC_UDC_REG->ineptsfsiz[i]);
  486. writel(0xFFFFFFFFU, &AIC_UDC_REG->inepint[i]);
  487. writel(0U, &AIC_UDC_REG->outeptsfsiz[i]);
  488. writel(0xFFFFFFFFU, &AIC_UDC_REG->outepint[i]);
  489. }
  490. writel(0, &AIC_UDC_REG->usbepintmsk);
  491. outepintmsk = TRANSFER_DONE | CTRL_OUT_EP_SETUP_PHASE_DONE | CTRL_OUT_EP_STATUS_PHASE_RCVD;
  492. inepintmsk = TRANSFER_DONE | NON_ISO_IN_EP_TIMEOUT | INTKNEPMIS;
  493. #ifndef CONFIG_USB_AIC_DMA_ENABLE
  494. outepintmsk |= CTRL_OUT_EP_SETUP_PHASE_DONE;
  495. inepintmsk |= INTKN_TXFEMP;
  496. #endif
  497. writel(outepintmsk, &AIC_UDC_REG->outepintmsk);
  498. writel(inepintmsk, &AIC_UDC_REG->inepintmsk);
  499. aic_set_dma_nextep();
  500. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  501. for (uint8_t i = 0U; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  502. aic_udc_obuf_free(&g_aic_udc.out_ep[i]);
  503. aic_udc_ibuf_free(&g_aic_udc.in_ep[i]);
  504. }
  505. #endif
  506. memset(&g_aic_udc, 0, sizeof(struct aic_udc));
  507. usbd_event_reset_handler(0);
  508. /* Start reading setup */
  509. aic_ep0_start_read_setup((uint8_t *)&g_aic_udc.setup);
  510. return 0;
  511. }
  512. int usb_dc_init(uint8_t busid)
  513. {
  514. int ret;
  515. uint32_t base = 0;
  516. uint32_t tmpreg = 0;
  517. memset(&g_aic_udc, 0, sizeof(struct aic_udc));
  518. usb_dc_low_level_init();
  519. /* Disconnect */
  520. tmpreg = readl(&AIC_UDC_REG->usbdevfunc);
  521. tmpreg |= USBDEVFUNC_SFTDISCON;
  522. writel(tmpreg, &AIC_UDC_REG->usbdevfunc);
  523. /* Disable Interrupt */
  524. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  525. tmpreg &= ~USBDEVINIT_GLBL_INTR_EN;
  526. writel(tmpreg, &AIC_UDC_REG->usbdevinit);
  527. ret = aic_core_init();
  528. for (uint8_t i = 0U; i < 2U; i++) {
  529. writel(0, &AIC_UDC_REG->txfifosiz[i]);
  530. }
  531. /* Device mode configuration */
  532. tmpreg = readl(&AIC_UDC_REG->usbdevconf);
  533. tmpreg |= PERIOD_FRAME_INTERVAL_80;
  534. #if defined(CONFIG_USB_HS)
  535. /* Set Core speed to High speed mode */
  536. tmpreg |= DEV_SPEED_HIGH_SPEED_20;
  537. #else
  538. tmpreg |= DEV_SPEED_FULL_SPEED_20;
  539. #endif
  540. writel(tmpreg, &AIC_UDC_REG->usbdevconf);
  541. ret = aic_flush_txfifo(0x10U);
  542. ret = aic_flush_rxfifo();
  543. /* Clear all pending Device Interrupts */
  544. writel(0, &AIC_UDC_REG->inepintmsk);
  545. writel(0, &AIC_UDC_REG->outepintmsk);
  546. writel(0, &AIC_UDC_REG->usbepintmsk);
  547. /* Disable all interrupts. */
  548. writel(0, &AIC_UDC_REG->usbintmsk);
  549. /* Clear any pending interrupts */
  550. writel(0xBFFFFFFFU, &AIC_UDC_REG->usbintsts);
  551. /* Enable interrupts matching to the Device mode ONLY */
  552. tmpreg = INT_RESET | INT_ENUMDONE |
  553. INT_OUT_EP | INT_IN_EP |
  554. INT_INCOMP_ISO_IN_INT | INT_INCOMP_ISO_OUT_INT | INT_SUSPEND;
  555. writel(tmpreg, &AIC_UDC_REG->usbintmsk);
  556. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  557. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  558. tmpreg |= (USBDEVINIT_HBSTLEN_INCR4 << USBDEVINIT_HBSTLEN_SHIFT);
  559. tmpreg |= USBDEVINIT_DMA_EN;
  560. writel(tmpreg, &AIC_UDC_REG->usbdevinit);
  561. #else
  562. tmpreg = readl(&AIC_UDC_REG->usbintmsk);
  563. tmpreg |= INT_RX_FIFO_NOT_EMPTY;
  564. writel(tmpreg, &AIC_UDC_REG->usbintmsk);
  565. #endif
  566. /* Assign FIFO */
  567. base = 0;
  568. writel(AIC_RX_FIFO_SIZE, &AIC_UDC_REG->rxfifosiz);
  569. base += AIC_RX_FIFO_SIZE;
  570. writel((AIC_NP_TX_FIFO_SIZE << 16) | base, &AIC_UDC_REG->nptxfifosiz);
  571. base += AIC_NP_TX_FIFO_SIZE;
  572. writel((AIC_PERIOD_TX_FIFO1_SIZE << 16) | base, &AIC_UDC_REG->txfifosiz[0]);
  573. base += AIC_PERIOD_TX_FIFO1_SIZE;
  574. writel((AIC_PERIOD_TX_FIFO2_SIZE << 16) | base, &AIC_UDC_REG->txfifosiz[1]);
  575. usb_dc_rst();
  576. /* Enable Interrupt */
  577. tmpreg = readl(&AIC_UDC_REG->usbdevinit);
  578. tmpreg |= USBDEVINIT_GLBL_INTR_EN;
  579. writel(tmpreg, &AIC_UDC_REG->usbdevinit);
  580. /* Connect */
  581. tmpreg = readl(&AIC_UDC_REG->usbdevfunc);
  582. tmpreg &= ~USBDEVFUNC_SFTDISCON;
  583. writel(tmpreg, &AIC_UDC_REG->usbdevfunc);
  584. return ret;
  585. }
  586. int usb_dc_deinit(uint8_t busid)
  587. {
  588. uint32_t tmpreg = 0;
  589. usbd_event_suspend_handler();
  590. /* Clear Pending interrupt */
  591. for (uint8_t i = 0U; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  592. writel(0xFB7FU, &AIC_UDC_REG->outepint[i]);
  593. writel(0xFB7FU, &AIC_UDC_REG->inepint[i]);
  594. }
  595. /* Clear interrupt masks */
  596. writel(0, &AIC_UDC_REG->inepintmsk);
  597. writel(0, &AIC_UDC_REG->outepintmsk);
  598. writel(0, &AIC_UDC_REG->usbepintmsk);
  599. /* Flush the FIFO */
  600. aic_flush_txfifo(0x10U);
  601. aic_flush_rxfifo();
  602. tmpreg = readl(&AIC_UDC_REG->usbdevfunc);
  603. tmpreg |= USBDEVFUNC_SFTDISCON;
  604. writel(tmpreg, &AIC_UDC_REG->usbdevfunc);
  605. usb_dc_low_level_deinit();
  606. return 0;
  607. }
  608. int usbd_set_address(uint8_t busid, const uint8_t addr)
  609. {
  610. uint32_t tmpreg = 0;
  611. tmpreg = readl(&AIC_UDC_REG->usbdevconf);
  612. tmpreg &= ~(DEVICE_ADDRESS_MASK);
  613. tmpreg |= ((uint32_t)addr << 4) & DEVICE_ADDRESS_MASK;
  614. writel(tmpreg, &AIC_UDC_REG->usbdevconf);
  615. return 0;
  616. }
  617. uint8_t usbd_get_port_speed(uint8_t busid, const uint8_t port)
  618. {
  619. uint8_t speed;
  620. uint32_t DevEnumSpeed = readl(&AIC_UDC_REG->usblinests);
  621. DevEnumSpeed &= USB_ENUM_SPEED_MASK;
  622. if (DevEnumSpeed == USB_HIGH_30_60MHZ) {
  623. speed = USB_SPEED_HIGH;
  624. } else if (DevEnumSpeed == USB_FULL_30_60MHZ) {
  625. speed = USB_SPEED_FULL;
  626. } else {
  627. speed = USB_SPEED_FULL;
  628. }
  629. return speed;
  630. }
  631. int usbd_ep_open(uint8_t busid, const struct usb_endpoint_descriptor *ep)
  632. {
  633. uint8_t ep_idx = USB_EP_GET_IDX(ep->bEndpointAddress);
  634. uint16_t ep_mps;
  635. uint8_t tx_fifo_num = 0;
  636. uint32_t i;
  637. uint32_t usbepintmsk = 0;
  638. uint32_t epcfg = 0;
  639. if (ep_idx > (USB_NUM_BIDIR_ENDPOINTS - 1)) {
  640. USB_LOG_ERR("Ep addr %d overflow\r\n", ep->bEndpointAddress);
  641. return -1;
  642. }
  643. ep_mps = USB_GET_MAXPACKETSIZE(ep->wMaxPacketSize);
  644. if (ep_idx == 0) {
  645. switch (ep_mps) {
  646. case 8:
  647. ep_mps = DEPCTL0_MPS_8;
  648. break;
  649. case 16:
  650. ep_mps = DEPCTL0_MPS_16;
  651. break;
  652. case 32:
  653. ep_mps = DEPCTL0_MPS_32;
  654. break;
  655. case 64:
  656. ep_mps = DEPCTL0_MPS_64;
  657. break;
  658. }
  659. }
  660. usbepintmsk = readl(&AIC_UDC_REG->usbepintmsk);
  661. if (USB_EP_DIR_IS_OUT(ep->bEndpointAddress)) {
  662. g_aic_udc.out_ep[ep_idx].ep_mps = USB_GET_MAXPACKETSIZE(ep->wMaxPacketSize);
  663. g_aic_udc.out_ep[ep_idx].ep_type = USB_GET_ENDPOINT_TYPE(ep->bmAttributes);
  664. usbepintmsk |= DAINT_OUT_MASK & (uint32_t)(1UL << (16 + ep_idx));
  665. writel(usbepintmsk, &AIC_UDC_REG->usbepintmsk);
  666. epcfg = readl(&AIC_UDC_REG->outepcfg[ep_idx]);
  667. epcfg |= (ep_mps & DEPCTL_MPS_MASK) |
  668. ((uint32_t)USB_GET_ENDPOINT_TYPE(ep->bmAttributes) << 18) |
  669. DEPCTL_SETD0PID |
  670. DEPCTL_USBACTEP;
  671. writel(epcfg, &AIC_UDC_REG->outepcfg[ep_idx]);
  672. } else {
  673. g_aic_udc.in_ep_desc[ep_idx] = *ep;
  674. g_aic_udc.in_ep[ep_idx].ep_mps = USB_GET_MAXPACKETSIZE(ep->wMaxPacketSize);
  675. g_aic_udc.in_ep[ep_idx].ep_type = USB_GET_ENDPOINT_TYPE(ep->bmAttributes);
  676. usbepintmsk |= DAINT_IN_MASK & (uint32_t)(1UL << ep_idx);
  677. writel(usbepintmsk, &AIC_UDC_REG->usbepintmsk);
  678. /* Period IN EP alloc fifo num */
  679. if ((USB_GET_ENDPOINT_TYPE(ep->bmAttributes) == USB_ENDPOINT_TYPE_INTERRUPT) ||
  680. (USB_GET_ENDPOINT_TYPE(ep->bmAttributes) == USB_ENDPOINT_TYPE_ISOCHRONOUS)) {
  681. for (i = 1; i <= USB_P_TXFIFO_NUM; i++) {
  682. if (g_aic_udc.p_txfifo_map & (1 << i))
  683. continue;
  684. g_aic_udc.p_txfifo_map |= (1 << i);
  685. tx_fifo_num = i;
  686. break;
  687. }
  688. if (tx_fifo_num == 0)
  689. return -1;
  690. aic_flush_txfifo(tx_fifo_num);
  691. } else {
  692. g_aic_udc.np_txfifo_map |= (1 << ep_idx);
  693. }
  694. epcfg = readl(&AIC_UDC_REG->inepcfg[ep_idx]);
  695. epcfg |= (ep_mps & DEPCTL_MPS_MASK) |
  696. ((uint32_t)USB_GET_ENDPOINT_TYPE(ep->bmAttributes) << 18) |
  697. (tx_fifo_num << 22) |
  698. DEPCTL_SETD0PID |
  699. DEPCTL_USBACTEP;
  700. writel(epcfg, &AIC_UDC_REG->inepcfg[ep_idx]);
  701. }
  702. return 0;
  703. }
  704. int usbd_ep_close(uint8_t busid, const uint8_t ep)
  705. {
  706. uint8_t ep_idx = USB_EP_GET_IDX(ep);
  707. uint8_t tx_fifo_num = 0;
  708. int i = 0;
  709. uint32_t outepcfg = 0;
  710. uint32_t outepint = 0;
  711. uint32_t inepcfg = 0;
  712. uint32_t inepint = 0;
  713. uint32_t usbintsts = 0;
  714. uint32_t usbdevfunc = 0;
  715. uint32_t usbepintmsk = 0;
  716. #define DIS_EP_TIMOUT 100
  717. if (USB_EP_DIR_IS_OUT(ep)) {
  718. outepcfg = readl(&AIC_UDC_REG->outepcfg[ep_idx]);
  719. if (outepcfg & DEPCTL_EPENA) {
  720. /* (1) Wait for global nak to take effect */
  721. usbintsts = readl(&AIC_UDC_REG->usbintsts);
  722. if (!(usbintsts & INT_GOUTNAKEFF)) {
  723. usbdevfunc = readl(&AIC_UDC_REG->usbdevfunc);
  724. usbdevfunc |= USBDEVFUNC_SGOUTNAK;
  725. writel(usbdevfunc, &AIC_UDC_REG->usbdevfunc);
  726. }
  727. for (i = 0; i < DIS_EP_TIMOUT; i++) {
  728. usbintsts = readl(&AIC_UDC_REG->usbintsts);
  729. if (usbintsts & INT_GOUTNAKEFF)
  730. break;
  731. aic_udelay(1);
  732. }
  733. if (i == DIS_EP_TIMOUT)
  734. USB_LOG_ERR("%s: timeout USBINTSTS.GOUTNAKEFF\n", __func__);
  735. /* (2) Disable ep */
  736. outepcfg = readl(&AIC_UDC_REG->outepcfg[ep_idx]);
  737. outepcfg |= DEPCTL_SNAK;
  738. outepcfg |= DEPCTL_EPDIS;
  739. writel(outepcfg, &AIC_UDC_REG->outepcfg[ep_idx]);
  740. for (i = 0; i < DIS_EP_TIMOUT*10; i++) {
  741. outepint = readl(&AIC_UDC_REG->outepint[ep_idx]);
  742. if (outepint & EPDISBLD)
  743. break;
  744. aic_udelay(1);
  745. }
  746. if (i == DIS_EP_TIMOUT)
  747. USB_LOG_ERR("%s: timeout OUTEPCFG.EPDisable\n", __func__);
  748. /* Clear EPDISBLD interrupt */
  749. outepint = readl(&AIC_UDC_REG->outepint[ep_idx]);
  750. outepint |= EPDISBLD;
  751. writel(outepint, &AIC_UDC_REG->outepint[ep_idx]);
  752. /* (3) Remove global NAKs */
  753. usbdevfunc = readl(&AIC_UDC_REG->usbdevfunc);
  754. usbdevfunc |= USBDEVFUNC_CGOUTNAK;
  755. writel(usbdevfunc, &AIC_UDC_REG->usbdevfunc);
  756. }
  757. usbepintmsk = readl(&AIC_UDC_REG->usbepintmsk);
  758. usbepintmsk &= ~(DAINT_OUT_MASK & (uint32_t)(1UL << (16 + ep_idx)));
  759. writel(usbepintmsk, &AIC_UDC_REG->usbepintmsk);
  760. writel(0, &AIC_UDC_REG->outepcfg[ep_idx]);
  761. } else {
  762. inepcfg = readl(&AIC_UDC_REG->inepcfg[ep_idx]);
  763. tx_fifo_num = (inepcfg & DEPCTL_TXFIFONUM_MASK) >> DEPCTL_TXFIFONUM_SHIFT;
  764. inepcfg = readl(&AIC_UDC_REG->inepcfg[ep_idx]);
  765. if (inepcfg & DEPCTL_EPENA) {
  766. if (tx_fifo_num) {
  767. /* (1) Wait for Nak effect */
  768. inepcfg |= DEPCTL_SNAK;
  769. writel(inepcfg, &AIC_UDC_REG->inepcfg[ep_idx]);
  770. for (i = 0; i < DIS_EP_TIMOUT; i++) {
  771. inepint = readl(&AIC_UDC_REG->inepint[ep_idx]);
  772. if (inepint & INEP_NAKEFF)
  773. break;
  774. aic_udelay(1);
  775. }
  776. if (i == DIS_EP_TIMOUT)
  777. USB_LOG_ERR("%s: timeout INEPINT.NAKEFF\n", __func__);
  778. } else {
  779. /* (1) Wait for Nak effect */
  780. usbdevfunc = readl(&AIC_UDC_REG->usbdevfunc);
  781. usbdevfunc |= USBDEVFUNC_SGNPINNAK;
  782. writel(usbdevfunc, &AIC_UDC_REG->usbdevfunc);
  783. for (i = 0; i < DIS_EP_TIMOUT; i++) {
  784. usbintsts = readl(&AIC_UDC_REG->usbintsts);
  785. if (usbintsts & INT_GINNAKEFF)
  786. break;
  787. aic_udelay(1);
  788. }
  789. if (i == DIS_EP_TIMOUT)
  790. USB_LOG_ERR("%s: timeout USBINTSTS.GOUTNAKEFF\n", __func__);
  791. }
  792. /* (2) Disable ep */
  793. inepcfg = readl(&AIC_UDC_REG->inepcfg[ep_idx]);
  794. inepcfg |= DEPCTL_SNAK;
  795. inepcfg |= DEPCTL_EPDIS;
  796. writel(inepcfg, &AIC_UDC_REG->inepcfg[ep_idx]);
  797. for (i = 0; i < DIS_EP_TIMOUT; i++) {
  798. inepint = readl(&AIC_UDC_REG->inepint[ep_idx]);
  799. if (inepint & EPDISBLD)
  800. break;
  801. aic_udelay(1);
  802. }
  803. if (i == DIS_EP_TIMOUT)
  804. USB_LOG_ERR("%s: timeout OUTEPCFG.EPDisable\n", __func__);
  805. /* Clear EPDISBLD interrupt */
  806. inepint = readl(&AIC_UDC_REG->inepint[ep_idx]);
  807. inepint |= EPDISBLD;
  808. writel(inepint, &AIC_UDC_REG->inepint[ep_idx]);
  809. /* (3) Flush TX FIFO */
  810. aic_flush_txfifo(tx_fifo_num);
  811. /* Period IN EP free fifo num */
  812. if (tx_fifo_num > 0)
  813. g_aic_udc.p_txfifo_map &= ~(1 << tx_fifo_num);
  814. else
  815. g_aic_udc.np_txfifo_map &= ~(1 << ep_idx);
  816. /* (4) Clear Global In NP NAK in Shared FIFO for non periodic ep */
  817. if (!tx_fifo_num) {
  818. usbdevfunc = readl(&AIC_UDC_REG->usbdevfunc);
  819. usbdevfunc |= USBDEVFUNC_CGNPINNAK;
  820. writel(usbdevfunc, &AIC_UDC_REG->usbdevfunc);
  821. }
  822. }
  823. usbepintmsk = readl(&AIC_UDC_REG->usbepintmsk);
  824. usbepintmsk &= ~(DAINT_OUT_MASK & (uint32_t)(1UL << ep_idx));
  825. writel(usbepintmsk, &AIC_UDC_REG->usbepintmsk);
  826. writel(0, &AIC_UDC_REG->inepcfg[ep_idx]);
  827. }
  828. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  829. if (USB_EP_DIR_IS_OUT(ep)) {
  830. aic_udc_obuf_free(&g_aic_udc.out_ep[ep_idx]);
  831. } else {
  832. aic_udc_ibuf_free(&g_aic_udc.in_ep[ep_idx]);
  833. }
  834. #endif
  835. return 0;
  836. }
  837. int usbd_npinep_rewrite(const uint8_t ep)
  838. {
  839. int i = 0;
  840. int j = 0;
  841. int fail = 0;
  842. unsigned int pending_map = 0;
  843. //int data_len = 0;
  844. uint32_t tmpreg = 0;
  845. for (i = 0U, j = 0; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  846. tmpreg = readl(&AIC_UDC_REG->inepcfg[i]);
  847. if (!((g_aic_udc.np_txfifo_map & (1 << i)) &&
  848. (tmpreg & DEPCTL_EPENA)))
  849. continue;
  850. j++;
  851. pending_map |= (1 << i);
  852. }
  853. if (j <= 1)
  854. return 0;
  855. /* (1) close all no-periodic ep */
  856. /* (1.1) Set Global In NP NAK in Shared FIFO for non periodic ep */
  857. tmpreg = readl(&AIC_UDC_REG->usbdevfunc);
  858. tmpreg |= USBDEVFUNC_SGNPINNAK;
  859. writel(tmpreg, &AIC_UDC_REG->usbdevfunc);
  860. for (i = 0; i < DIS_EP_TIMOUT; i++) {
  861. tmpreg = readl(&AIC_UDC_REG->usbintsts);
  862. if (tmpreg & INT_GINNAKEFF)
  863. break;
  864. aic_udelay(1);
  865. }
  866. if (i == DIS_EP_TIMOUT)
  867. USB_LOG_ERR("%s: timeout USBINTSTS.GOUTNAKEFF\n", __func__);
  868. /* (1.2) Disable ep */
  869. for (i = 0U; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  870. tmpreg = readl(&AIC_UDC_REG->inepcfg[i]);
  871. if (!((g_aic_udc.np_txfifo_map & (1 << i)) &&
  872. (tmpreg & DEPCTL_EPENA)))
  873. continue;
  874. tmpreg |= DEPCTL_SNAK;
  875. tmpreg |= DEPCTL_EPDIS;
  876. writel(tmpreg, &AIC_UDC_REG->inepcfg[i]);
  877. /* remain data */
  878. #if 0
  879. tmpreg = readl(&AIC_UDC_REG->ineptsfsiz[i]);
  880. data_len = tmpreg & DXEPTSIZ_XFER_SIZE_MASK;
  881. g_aic_udc.in_ep[ep].xfer_buf += g_aic_udc.in_ep[ep].xfer_len - data_len;
  882. g_aic_udc.in_ep[ep].xfer_len = data_len;
  883. #endif
  884. //pending_map |= (1 << i);
  885. }
  886. for (j = 0; j < DIS_EP_TIMOUT; j++) {
  887. fail = 0;
  888. for (i = 0U; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  889. if (!(pending_map & (1 << i)))
  890. continue;
  891. tmpreg = readl(&AIC_UDC_REG->inepint[i]);
  892. if (!(tmpreg & EPDISBLD)) {
  893. fail = i+1;
  894. break;
  895. }
  896. }
  897. if (!fail)
  898. break;
  899. aic_udelay(1);
  900. }
  901. if (j == DIS_EP_TIMOUT)
  902. USB_LOG_ERR("%s: ep%d timeout OUTEPCFG.EPDisable\n", __func__, fail-1);
  903. /* Clear EPDISBLD interrupt */
  904. for (i = 0U; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  905. if (!(pending_map & (1 << i)))
  906. continue;
  907. tmpreg = readl(&AIC_UDC_REG->inepint[i]);
  908. tmpreg |= EPDISBLD;
  909. writel(tmpreg, &AIC_UDC_REG->inepint[i]);
  910. }
  911. /* (1.3) Flush TX FIFO0 */
  912. aic_flush_txfifo(0);
  913. /* (1.4) Clear Global In NP NAK in Shared FIFO for non periodic ep */
  914. tmpreg = readl(&AIC_UDC_REG->usbdevfunc);
  915. tmpreg |= USBDEVFUNC_CGNPINNAK;
  916. writel(tmpreg, &AIC_UDC_REG->usbdevfunc);
  917. /* (2) reopen current ep */
  918. usbd_ep_open(&g_aic_udc.in_ep_desc[ep]);
  919. /* (3) rewrite current ep */
  920. if (pending_map & (1 << ep)) {
  921. usbd_ep_start_write(ep, g_aic_udc.in_ep[ep].xfer_buf,
  922. g_aic_udc.in_ep[ep].xfer_len);
  923. }
  924. /* (4) reopen & rewrite other ep, let's receive ep mismtach interrupt */
  925. for (i = 0U; i < USB_NUM_BIDIR_ENDPOINTS; i++) {
  926. if (!(pending_map & (1 << i)) ||
  927. (i == ep))
  928. continue;
  929. usbd_ep_open(&g_aic_udc.in_ep_desc[i]);
  930. usbd_ep_start_write(i, g_aic_udc.in_ep[i].xfer_buf,
  931. g_aic_udc.in_ep[i].xfer_len);
  932. }
  933. return 0;
  934. }
  935. int usbd_ep_set_stall(uint8_t busid, const uint8_t ep)
  936. {
  937. uint8_t ep_idx = USB_EP_GET_IDX(ep);
  938. uint32_t tmpreg = 0;
  939. if (USB_EP_DIR_IS_OUT(ep)) {
  940. tmpreg = readl(&AIC_UDC_REG->outepcfg[ep_idx]);
  941. if (((tmpreg & DEPCTL_EPENA) == 0U) && (ep_idx != 0U)) {
  942. tmpreg &= ~(DEPCTL_EPDIS);
  943. }
  944. tmpreg |= DEPCTL_STALL;
  945. writel(tmpreg, &AIC_UDC_REG->outepcfg[ep_idx]);
  946. } else {
  947. tmpreg = readl(&AIC_UDC_REG->inepcfg[ep_idx]);
  948. if (((tmpreg & DEPCTL_EPENA) == 0U) && (ep_idx != 0U)) {
  949. tmpreg &= ~(DEPCTL_EPDIS);
  950. }
  951. tmpreg |= DEPCTL_STALL;
  952. writel(tmpreg, &AIC_UDC_REG->inepcfg[ep_idx]);
  953. }
  954. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  955. if (ep_idx == 0) {
  956. aic_ep0_start_read_setup((uint8_t *)&g_aic_udc.setup);
  957. }
  958. #endif
  959. return 0;
  960. }
  961. int usbd_ep_clear_stall(uint8_t busid, const uint8_t ep)
  962. {
  963. uint8_t ep_idx = USB_EP_GET_IDX(ep);
  964. uint32_t tmpreg = 0;
  965. if (USB_EP_DIR_IS_OUT(ep)) {
  966. tmpreg = readl(&AIC_UDC_REG->outepcfg[ep_idx]);
  967. tmpreg &= ~DEPCTL_STALL;
  968. if ((g_aic_udc.out_ep[ep_idx].ep_type == USB_ENDPOINT_TYPE_INTERRUPT) ||
  969. (g_aic_udc.out_ep[ep_idx].ep_type == USB_ENDPOINT_TYPE_BULK)) {
  970. tmpreg |= DEPCTL_SETD0PID; /* DATA0 */
  971. }
  972. writel(tmpreg, &AIC_UDC_REG->outepcfg[ep_idx]);
  973. } else {
  974. tmpreg = readl(&AIC_UDC_REG->inepcfg[ep_idx]);
  975. tmpreg &= ~DEPCTL_STALL;
  976. if ((g_aic_udc.in_ep[ep_idx].ep_type == USB_ENDPOINT_TYPE_INTERRUPT) ||
  977. (g_aic_udc.in_ep[ep_idx].ep_type == USB_ENDPOINT_TYPE_BULK)) {
  978. tmpreg |= DEPCTL_SETD0PID; /* DATA0 */
  979. }
  980. writel(tmpreg, &AIC_UDC_REG->inepcfg[ep_idx]);
  981. }
  982. return 0;
  983. }
  984. int usbd_ep_is_stalled(uint8_t busid, const uint8_t ep, uint8_t *stalled)
  985. {
  986. if (USB_EP_DIR_IS_OUT(ep)) {
  987. } else {
  988. }
  989. return 0;
  990. }
  991. int usbd_ep_start_write_raw(const uint8_t ep, const uint8_t *data, uint32_t data_len, uint8_t cache_align)
  992. {
  993. uint8_t ep_idx = USB_EP_GET_IDX(ep);
  994. uint32_t pktcnt = 0;
  995. uint32_t inepcfg = 0;
  996. uint32_t ineptsfsiz = 0;
  997. uint32_t usblinests = 0;
  998. if (!data && data_len) {
  999. return -1;
  1000. }
  1001. inepcfg = readl(&AIC_UDC_REG->inepcfg[ep_idx]);
  1002. if (inepcfg & DEPCTL_EPENA) {
  1003. return -2;
  1004. }
  1005. if (ep_idx && !(inepcfg & DEPCTL_MPS_MASK)) {
  1006. return -3;
  1007. }
  1008. if ((uint32_t)(uintptr_t)data & 0x03) {
  1009. return -4;
  1010. }
  1011. g_aic_udc.in_ep[ep_idx].xfer_buf = (uint8_t *)data;
  1012. g_aic_udc.in_ep[ep_idx].xfer_len = data_len;
  1013. g_aic_udc.in_ep[ep_idx].actual_xfer_len = 0;
  1014. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  1015. if (cache_align && (ep_idx != 0) && (data_len > 0) &&
  1016. ((((uint32_t)(uintptr_t)data % CACHE_LINE_SIZE) != 0) ||
  1017. (((uint32_t)(uintptr_t)(data + data_len) % CACHE_LINE_SIZE) != 0))) {
  1018. if (g_aic_udc.in_ep[ep_idx].xfer_align_len != data_len) {
  1019. int ret = 0;
  1020. aic_udc_ibuf_free(&g_aic_udc.in_ep[ep_idx]);
  1021. ret = aic_udc_ibuf_alloc(&g_aic_udc.in_ep[ep_idx], data_len);
  1022. if (ret)
  1023. return ret;
  1024. }
  1025. memcpy(g_aic_udc.in_ep[ep_idx].xfer_align_buf, data, data_len);
  1026. data = g_aic_udc.in_ep[ep_idx].xfer_align_buf;
  1027. } else {
  1028. aic_udc_ibuf_free(&g_aic_udc.in_ep[ep_idx]);
  1029. }
  1030. if (data_len>0)
  1031. aic_udc_dcache_clean((uintptr_t)data, ALIGN_UP(data_len, CACHE_LINE_SIZE));
  1032. #endif
  1033. ineptsfsiz = readl(&AIC_UDC_REG->ineptsfsiz[ep_idx]);
  1034. ineptsfsiz &= ~(DXEPTSIZ_PKT_CNT_MASK);
  1035. ineptsfsiz &= ~(DXEPTSIZ_XFER_SIZE_MASK);
  1036. if (data_len == 0) {
  1037. ineptsfsiz |= (DXEPTSIZ_PKT_CNT_MASK & (1U << 19));
  1038. writel(ineptsfsiz, &AIC_UDC_REG->ineptsfsiz[ep_idx]);
  1039. inepcfg |= (DEPCTL_CNAK | DEPCTL_EPENA);
  1040. writel(inepcfg, &AIC_UDC_REG->inepcfg[ep_idx]);
  1041. return 0;
  1042. }
  1043. if (ep_idx == 0) {
  1044. if (data_len > g_aic_udc.in_ep[ep_idx].ep_mps) {
  1045. data_len = g_aic_udc.in_ep[ep_idx].ep_mps;
  1046. }
  1047. g_aic_udc.in_ep[ep_idx].xfer_len = data_len;
  1048. ineptsfsiz |= (DXEPTSIZ_PKT_CNT_MASK & (1U << 19));
  1049. ineptsfsiz |= (DXEPTSIZ_XFER_SIZE_MASK & data_len);
  1050. } else {
  1051. pktcnt = (uint16_t)((data_len + g_aic_udc.in_ep[ep_idx].ep_mps - 1U) / g_aic_udc.in_ep[ep_idx].ep_mps);
  1052. ineptsfsiz |= (DXEPTSIZ_PKT_CNT_MASK & (pktcnt << 19));
  1053. ineptsfsiz |= (DXEPTSIZ_XFER_SIZE_MASK & data_len);
  1054. }
  1055. if (g_aic_udc.in_ep[ep_idx].ep_type == USB_ENDPOINT_TYPE_ISOCHRONOUS) {
  1056. usblinests = readl(&AIC_UDC_REG->usblinests);
  1057. if ((usblinests & (1U << 8)) == 0U) {
  1058. inepcfg &= ~DEPCTL_SETD0PID;
  1059. inepcfg |= DEPCTL_SETD1PID;
  1060. } else {
  1061. inepcfg &= ~DEPCTL_SETD1PID;
  1062. inepcfg |= DEPCTL_SETD0PID;
  1063. }
  1064. ineptsfsiz &= ~(DXEPTSIZ_MULCNT_MASK);
  1065. ineptsfsiz |= ((pktcnt << DXEPTSIZ_MULCNT_SHIFT) & DXEPTSIZ_MULCNT_MASK);
  1066. } else if (g_aic_udc.in_ep[ep_idx].ep_type == USB_ENDPOINT_TYPE_INTERRUPT) {
  1067. ineptsfsiz &= ~(DXEPTSIZ_MULCNT_MASK);
  1068. ineptsfsiz |= (1U << DXEPTSIZ_MULCNT_SHIFT);
  1069. }
  1070. writel(ineptsfsiz, &AIC_UDC_REG->ineptsfsiz[ep_idx]);
  1071. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  1072. writel((uint32_t)(uintptr_t)data, &AIC_UDC_REG->inepdmaaddr[ep_idx]);
  1073. #endif
  1074. writel(0xFFFFFFFFU, &AIC_UDC_REG->inepint[ep_idx]);
  1075. inepcfg |= (DEPCTL_CNAK | DEPCTL_EPENA);
  1076. writel(inepcfg, &AIC_UDC_REG->inepcfg[ep_idx]);
  1077. return 0;
  1078. }
  1079. int usbd_ep_start_write(uint8_t busid, const uint8_t ep, const uint8_t *data, uint32_t data_len)
  1080. {
  1081. return usbd_ep_start_write_raw(ep, data, data_len, 1);
  1082. }
  1083. int usbd_ep_start_read_raw(const uint8_t ep, uint8_t *data, uint32_t data_len, uint8_t cache_align)
  1084. {
  1085. uint8_t ep_idx = USB_EP_GET_IDX(ep);
  1086. uint32_t pktcnt = 0;
  1087. uint32_t i = 0;
  1088. uint32_t outepcfg = 0;
  1089. uint32_t outeptsfsiz = 0;
  1090. uint32_t usblinests = 0;
  1091. if (!data && data_len) {
  1092. return -1;
  1093. }
  1094. outepcfg = readl(&AIC_UDC_REG->outepcfg[ep_idx]);
  1095. if (outepcfg & DEPCTL_EPENA) {
  1096. for (i = 0; i < 100000; i++) {
  1097. outepcfg = readl(&AIC_UDC_REG->outepcfg[ep_idx]);
  1098. if (!(outepcfg & DEPCTL_EPENA))
  1099. break;
  1100. }
  1101. if (i == 1000000) {
  1102. g_aic_udc.out_ep[ep_idx].xfer_len = data_len;
  1103. USB_LOG_ERR("ep%d AIC_UDC_REG->outepcfg[ep_idx] = 0x%x.\n",
  1104. (unsigned int)ep_idx, (unsigned int)outepcfg);
  1105. return -2;
  1106. }
  1107. }
  1108. if (ep_idx && !(outepcfg & DEPCTL_MPS_MASK)) {
  1109. return -3;
  1110. }
  1111. if (((uint32_t)(uintptr_t)data) & 0x03) {
  1112. return -4;
  1113. }
  1114. g_aic_udc.out_ep[ep_idx].xfer_buf = (uint8_t *)data;
  1115. g_aic_udc.out_ep[ep_idx].xfer_len = data_len;
  1116. g_aic_udc.out_ep[ep_idx].actual_xfer_len = 0;
  1117. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  1118. if (cache_align && (ep_idx != 0) && (data_len > 0) &&
  1119. ((((uint32_t)(uintptr_t)data % CACHE_LINE_SIZE) != 0) ||
  1120. (((uint32_t)(uintptr_t)(data + data_len) % CACHE_LINE_SIZE) != 0))) {
  1121. if (g_aic_udc.out_ep[ep_idx].xfer_align_len != data_len) {
  1122. int ret = 0;
  1123. aic_udc_obuf_free(&g_aic_udc.out_ep[ep_idx]);
  1124. ret = aic_udc_obuf_alloc(&g_aic_udc.out_ep[ep_idx], data_len);
  1125. if (ret)
  1126. return ret;
  1127. }
  1128. data = g_aic_udc.out_ep[ep_idx].xfer_align_buf;
  1129. } else {
  1130. aic_udc_obuf_free(&g_aic_udc.out_ep[ep_idx]);
  1131. }
  1132. if (data_len > 0)
  1133. aic_udc_dcache_invalidate((uintptr_t)data, ALIGN_UP(data_len, CACHE_LINE_SIZE));
  1134. #endif
  1135. outeptsfsiz = readl(&AIC_UDC_REG->outeptsfsiz[ep_idx]);
  1136. outeptsfsiz &= ~(DXEPTSIZ_PKT_CNT_MASK);
  1137. outeptsfsiz &= ~(DXEPTSIZ_XFER_SIZE_MASK);
  1138. outeptsfsiz &= ~(DXEPTSIZ_MULCNT_MASK);
  1139. if (data_len == 0) {
  1140. outeptsfsiz |= (DXEPTSIZ_PKT_CNT_MASK & (1 << 19));
  1141. outeptsfsiz |= (DXEPTSIZ_XFER_SIZE_MASK & g_aic_udc.out_ep[ep_idx].ep_mps);
  1142. writel(outeptsfsiz, &AIC_UDC_REG->outeptsfsiz[ep_idx]);
  1143. outepcfg |= (DEPCTL_CNAK | DEPCTL_EPENA);
  1144. writel(outepcfg, &AIC_UDC_REG->outepcfg[ep_idx]);
  1145. return 0;
  1146. }
  1147. if (ep_idx == 0) {
  1148. if (data_len > g_aic_udc.out_ep[ep_idx].ep_mps) {
  1149. data_len = g_aic_udc.out_ep[ep_idx].ep_mps;
  1150. }
  1151. g_aic_udc.out_ep[ep_idx].xfer_len = data_len;
  1152. outeptsfsiz |= (DXEPTSIZ_PKT_CNT_MASK & (1U << 19));
  1153. outeptsfsiz |= (DXEPTSIZ_XFER_SIZE_MASK & data_len);
  1154. writel(outeptsfsiz, &AIC_UDC_REG->outeptsfsiz[ep_idx]);
  1155. } else {
  1156. pktcnt = (uint16_t)((data_len + g_aic_udc.out_ep[ep_idx].ep_mps - 1U) / g_aic_udc.out_ep[ep_idx].ep_mps);
  1157. outeptsfsiz |= (DXEPTSIZ_PKT_CNT_MASK & (pktcnt << 19));
  1158. outeptsfsiz |= (DXEPTSIZ_XFER_SIZE_MASK & data_len);
  1159. writel(outeptsfsiz, &AIC_UDC_REG->outeptsfsiz[ep_idx]);
  1160. }
  1161. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  1162. writel((uint32_t)(uintptr_t)data, &AIC_UDC_REG->outepdmaaddr[ep_idx]);
  1163. #endif
  1164. if (g_aic_udc.out_ep[ep_idx].ep_type == USB_ENDPOINT_TYPE_ISOCHRONOUS) {
  1165. usblinests = readl(&AIC_UDC_REG->usblinests);
  1166. if ((usblinests & (1U << 8)) == 0U) {
  1167. outepcfg &= ~DEPCTL_SETD0PID;
  1168. outepcfg |= DEPCTL_SETD1PID;
  1169. } else {
  1170. outepcfg &= ~DEPCTL_SETD1PID;
  1171. outepcfg |= DEPCTL_SETD0PID;
  1172. }
  1173. }
  1174. writel(0xFFFFFFFFU, &AIC_UDC_REG->outepint[ep_idx]);
  1175. outepcfg |= (DEPCTL_CNAK | DEPCTL_EPENA);
  1176. writel(outepcfg, &AIC_UDC_REG->outepcfg[ep_idx]);
  1177. return 0;
  1178. }
  1179. int usbd_ep_start_read(uint8_t busid, const uint8_t ep, uint8_t *data, uint32_t data_len)
  1180. {
  1181. return usbd_ep_start_read_raw(ep, data, data_len, 1);
  1182. }
  1183. void USBD_IRQHandler(void)
  1184. {
  1185. uint32_t gint_status, ep_idx, ep_intr, epint, daintmask, tmpreg, tmpreg01;
  1186. gint_status = aic_get_glb_intstatus();
  1187. /* Avoid spurious interrupt */
  1188. if (gint_status == 0) {
  1189. return;
  1190. }
  1191. #ifndef CONFIG_USB_AIC_DMA_ENABLE
  1192. uint32_t temp;
  1193. uint32_t read_count;
  1194. /* Handle RxQLevel Interrupt */
  1195. if (gint_status & INT_RX_FIFO_NOT_EMPTY) {
  1196. tmpreg = readl(&AIC_UDC_REG->usbintmsk);
  1197. tmpreg &= ~(INT_RX_FIFO_NOT_EMPTY);
  1198. writel(tmpreg, &AIC_UDC_REG->usbintmsk);
  1199. temp = readl(&AIC_UDC_REG->rxfifosts_pop);
  1200. ep_idx = temp & RXFIFOSTS_EPNUM_MASK;
  1201. if ((temp & RXFIFOSTS_PKTSTS_MASK) == PKTSTS_OUT_DATA_PKT_REC) {
  1202. read_count = (temp & RXFIFOSTS_BCNT_MASK) >> 4;
  1203. if (read_count != 0) {
  1204. aic_ep_read(g_aic_udc.out_ep[ep_idx].xfer_buf, read_count);
  1205. g_aic_udc.out_ep[ep_idx].xfer_buf += read_count;
  1206. }
  1207. } else if ((temp & RXFIFOSTS_PKTSTS_MASK) == PKTSTS_SETUP_DATA_PKT_REC) {
  1208. read_count = (temp & RXFIFOSTS_BCNT_MASK) >> 4;
  1209. aic_ep_read((uint8_t *)&g_aic_udc.setup, read_count);
  1210. } else {
  1211. /* ... */
  1212. }
  1213. tmpreg = readl(&AIC_UDC_REG->usbintmsk);
  1214. tmpreg |= INT_RX_FIFO_NOT_EMPTY;
  1215. writel(tmpreg, &AIC_UDC_REG->usbintmsk);
  1216. }
  1217. #endif
  1218. if (gint_status & INT_OUT_EP) {
  1219. ep_idx = 0;
  1220. ep_intr = aic_get_outeps_intstatus();
  1221. while (ep_intr != 0U) {
  1222. if ((ep_intr & 0x1U) != 0U) {
  1223. epint = aic_get_outep_intstatus(ep_idx);
  1224. writel(epint, &AIC_UDC_REG->outepint[ep_idx]);
  1225. struct aic_ep_state *ep = &g_aic_udc.out_ep[ep_idx];
  1226. if ((ep_idx == 0)) {
  1227. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  1228. extern void usb_dc_sync_dma(void);
  1229. usb_dc_sync_dma();
  1230. if (ep->xfer_align_buf)
  1231. memcpy(ep->xfer_buf, ep->xfer_align_buf, ep->xfer_len);
  1232. #endif
  1233. if (ep0_ctrl_stage == AIC_EP0_SETUP) {
  1234. /* Setup data-out will send STATUS_PHASE_RCVD interrupt when next setup.
  1235. Attemp to re-read setup data. */
  1236. if (epint & CTRL_OUT_EP_STATUS_PHASE_RCVD) {
  1237. aic_ep0_start_read_setup((uint8_t *)&g_aic_udc.setup);
  1238. }
  1239. /* Normal setup handle */
  1240. if (epint & CTRL_OUT_EP_SETUP_PHASE_DONE) {
  1241. if (g_aic_udc.setup.wLength)
  1242. if ((g_aic_udc.setup.bmRequestType & USB_REQUEST_DIR_MASK) == USB_REQUEST_DIR_OUT)
  1243. ep0_ctrl_stage = AIC_EP0_DATA_OUT;
  1244. else
  1245. ep0_ctrl_stage = AIC_EP0_DATA_IN;
  1246. else
  1247. ep0_ctrl_stage = AIC_EP0_STATUS_IN;
  1248. usbd_event_ep0_setup_complete_handler(0, (uint8_t *)&g_aic_udc.setup);
  1249. }
  1250. } else {
  1251. if ((epint & TRANSFER_DONE) == TRANSFER_DONE) {
  1252. if (ep->xfer_len == 0) {
  1253. /* Out status, start reading setup */
  1254. aic_ep0_start_read_setup((uint8_t *)&g_aic_udc.setup);
  1255. } else {
  1256. //ep->actual_xfer_len = ep->xfer_len - ((AIC_UDC_REG->outeptsfsiz[ep_idx]) & DXEPTSIZ_XFER_SIZE_MASK);
  1257. ep->actual_xfer_len = ep->xfer_len;
  1258. ep->xfer_len = 0;
  1259. usbd_event_ep_out_complete_handler(0, 0x00, ep->actual_xfer_len);
  1260. }
  1261. }
  1262. }
  1263. } else {
  1264. #ifdef CONFIG_USB_AIC_DMA_ENABLE
  1265. extern void usb_dc_sync_dma(void);
  1266. usb_dc_sync_dma();
  1267. if (ep->xfer_align_buf)
  1268. memcpy(ep->xfer_buf, ep->xfer_align_buf, ep->xfer_len);
  1269. #endif
  1270. tmpreg = readl(&AIC_UDC_REG->outeptsfsiz[ep_idx]);
  1271. ep->actual_xfer_len = ep->xfer_len - (tmpreg & DXEPTSIZ_XFER_SIZE_MASK);
  1272. ep->xfer_len = 0;
  1273. usbd_event_ep_out_complete_handler(0, ep_idx, ep->actual_xfer_len);
  1274. }
  1275. #ifndef CONFIG_USB_AIC_DMA_ENABLE
  1276. if ((epint & CTRL_OUT_EP_SETUP_PHASE_DONE) == CTRL_OUT_EP_SETUP_PHASE_DONE) {
  1277. if (ep0_ctrl_stage == 1) {
  1278. ep0_ctrl_stage = 2;
  1279. usbd_event_ep0_setup_complete_handler(0, (uint8_t *)&g_aic_udc.setup);
  1280. }
  1281. }
  1282. #endif
  1283. }
  1284. ep_intr >>= 1U;
  1285. ep_idx++;
  1286. }
  1287. }
  1288. #ifndef CONFIG_USB_AIC_DMA_ENABLE
  1289. if (gint_status & INT_NP_TX_FIFO_EMPTY) {
  1290. tmpreg = readl(&AIC_UDC_REG->usbintmsk);
  1291. tmpreg &= ~(INT_NP_TX_FIFO_EMPTY);
  1292. writel(tmpreg, &AIC_UDC_REG->usbintmsk);
  1293. aic_tx_fifo_empty_procecss(0);
  1294. }
  1295. #endif
  1296. if (gint_status & INT_IN_EP) {
  1297. ep_idx = 0U;
  1298. ep_intr = aic_get_ineps_intstatus();
  1299. while (ep_intr != 0U) {
  1300. if ((ep_intr & 0x1U) != 0U) {
  1301. epint = aic_get_inep_intstatus(ep_idx);
  1302. writel(epint, &AIC_UDC_REG->inepint[ep_idx]);
  1303. if (epint & INTKNEPMIS) {
  1304. aic_udelay(100);
  1305. usbd_npinep_rewrite(ep_idx);
  1306. }
  1307. if ((epint & TRANSFER_DONE) == TRANSFER_DONE) {
  1308. if (ep_idx == 0) {
  1309. if (g_aic_udc.setup.wLength && ((g_aic_udc.setup.bmRequestType & USB_REQUEST_DIR_MASK) == USB_REQUEST_DIR_OUT)) {
  1310. /* In status, start reading setup */
  1311. aic_ep0_start_read_setup((uint8_t *)&g_aic_udc.setup);
  1312. } else if (g_aic_udc.setup.wLength == 0) {
  1313. /* In status, start reading setup */
  1314. aic_ep0_start_read_setup((uint8_t *)&g_aic_udc.setup);
  1315. } else {
  1316. g_aic_udc.in_ep[ep_idx].actual_xfer_len = g_aic_udc.in_ep[ep_idx].xfer_len - ((AIC_UDC_REG->ineptsfsiz[ep_idx]) & DXEPTSIZ_XFER_SIZE_MASK);
  1317. g_aic_udc.in_ep[ep_idx].xfer_len = 0;
  1318. usbd_event_ep_in_complete_handler(0, 0x80, g_aic_udc.in_ep[ep_idx].actual_xfer_len);
  1319. }
  1320. } else {
  1321. tmpreg = readl(&AIC_UDC_REG->ineptsfsiz[ep_idx]);
  1322. g_aic_udc.in_ep[ep_idx].actual_xfer_len = g_aic_udc.in_ep[ep_idx].xfer_len - (tmpreg & DXEPTSIZ_XFER_SIZE_MASK);
  1323. g_aic_udc.in_ep[ep_idx].xfer_len = 0;
  1324. usbd_event_ep_in_complete_handler(0, ep_idx | 0x80, g_aic_udc.in_ep[ep_idx].actual_xfer_len);
  1325. }
  1326. }
  1327. #ifndef CONFIG_USB_AIC_DMA_ENABLE
  1328. if ((epint & INTKN_TXFEMP) == INTKN_TXFEMP) {
  1329. aic_tx_fifo_empty_procecss(ep_idx);
  1330. }
  1331. #endif
  1332. }
  1333. ep_intr >>= 1U;
  1334. ep_idx++;
  1335. }
  1336. }
  1337. if (gint_status & INT_RESET) {
  1338. writel(INT_RESET, &AIC_UDC_REG->usbintsts);
  1339. tmpreg = readl(&AIC_UDC_REG->usbdevfunc);
  1340. tmpreg &= ~USBDEVFUNC_RMTWKUPSIG;
  1341. writel(tmpreg, &AIC_UDC_REG->usbdevfunc);
  1342. usb_dc_rst();
  1343. }
  1344. if (gint_status & INT_ENUMDONE) {
  1345. writel(INT_ENUMDONE, &AIC_UDC_REG->usbintsts);
  1346. aic_set_turnaroundtime(usbd_clk, aic_get_devspeed());
  1347. tmpreg = readl(&AIC_UDC_REG->usbdevfunc);
  1348. tmpreg |= USBDEVFUNC_CGNPINNAK;
  1349. writel(tmpreg, &AIC_UDC_REG->usbdevfunc);
  1350. }
  1351. if (gint_status & INT_INCOMP_ISO_OUT_INT) {
  1352. daintmask = readl(&AIC_UDC_REG->usbepintmsk);
  1353. daintmask >>= 16;
  1354. for (ep_idx = 1; ep_idx < USB_NUM_BIDIR_ENDPOINTS; ep_idx++) {
  1355. if ((BIT(ep_idx) & ~daintmask) || (g_aic_udc.out_ep[ep_idx].ep_type != USB_ENDPOINT_TYPE_ISOCHRONOUS))
  1356. continue;
  1357. tmpreg = readl(&AIC_UDC_REG->outepcfg[ep_idx]);
  1358. if (!(tmpreg & DEPCTL_USBACTEP))
  1359. continue;
  1360. tmpreg01 = readl(&AIC_UDC_REG->usblinests);
  1361. if ((tmpreg01 & (1U << 8)) != 0U) {
  1362. tmpreg |= DEPCTL_SETD0PID;
  1363. tmpreg &= ~DEPCTL_SETD1PID;
  1364. } else {
  1365. tmpreg &= ~DEPCTL_SETD0PID;
  1366. tmpreg |= DEPCTL_SETD1PID;
  1367. }
  1368. writel(tmpreg, &AIC_UDC_REG->outepcfg[ep_idx]);
  1369. }
  1370. writel(INT_INCOMP_ISO_OUT_INT, &AIC_UDC_REG->usbintsts);
  1371. }
  1372. if (gint_status & INT_INCOMP_ISO_IN_INT) {
  1373. daintmask = readl(&AIC_UDC_REG->usbepintmsk);
  1374. daintmask &= 0xFFFF;
  1375. for (ep_idx = 1; ep_idx < USB_NUM_BIDIR_ENDPOINTS; ep_idx++) {
  1376. if (((BIT(ep_idx) & ~daintmask)) || (g_aic_udc.in_ep[ep_idx].ep_type != USB_ENDPOINT_TYPE_ISOCHRONOUS))
  1377. continue;
  1378. tmpreg = readl(&AIC_UDC_REG->inepcfg[ep_idx]);
  1379. if (!(tmpreg & DEPCTL_USBACTEP))
  1380. continue;
  1381. tmpreg01 = readl(&AIC_UDC_REG->usblinests);
  1382. if ((tmpreg01 & (1U << 8)) != 0U) {
  1383. tmpreg |= DEPCTL_SETD0PID;
  1384. tmpreg &= ~DEPCTL_SETD1PID;
  1385. } else {
  1386. tmpreg &= ~DEPCTL_SETD0PID;
  1387. tmpreg |= DEPCTL_SETD1PID;
  1388. }
  1389. writel(tmpreg, &AIC_UDC_REG->inepcfg[ep_idx]);
  1390. }
  1391. writel(INT_INCOMP_ISO_IN_INT, &AIC_UDC_REG->usbintsts);
  1392. }
  1393. if (gint_status & INT_SOF) {
  1394. writel(INT_SOF, &AIC_UDC_REG->usbintsts);
  1395. }
  1396. if (gint_status & INT_SUSPEND) {
  1397. writel(INT_SUSPEND, &AIC_UDC_REG->usbintsts);
  1398. usbd_event_suspend_handler(0);
  1399. }
  1400. if (gint_status & INT_RESUME) {
  1401. writel(INT_RESUME, &AIC_UDC_REG->usbintsts);
  1402. }
  1403. }