1
0

usbd_stm32l100_devfs.c 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461
  1. /* This file is the part of the Lightweight USB device Stack for STM32 microcontrollers
  2. *
  3. * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
  4. *
  5. * Licensed under the Apache License, Version 2.0 (the "License");
  6. * you may not use this file except in compliance with the License.
  7. * You may obtain a copy of the License at
  8. * http://www.apache.org/licenses/LICENSE-2.0
  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. */
  15. #include <stdint.h>
  16. #include <stdbool.h>
  17. #include "stm32.h"
  18. #include "usb.h"
  19. #if defined(USBD_STM32L100)
  20. #ifndef USB_PMASIZE
  21. #warning PMA memory size is not defined. Use 512 bytes by default
  22. #define USB_PMASIZE 0x200
  23. #endif
  24. #define USB_EP_SWBUF_TX USB_EP_DTOG_RX
  25. #define USB_EP_SWBUF_RX USB_EP_DTOG_TX
  26. #define EP_TOGGLE_SET(epr, bits, mask) *(epr) = (*(epr) ^ (bits)) & (USB_EPREG_MASK | (mask))
  27. #define EP_TX_STALL(epr) EP_TOGGLE_SET((epr), USB_EP_TX_STALL, USB_EPTX_STAT)
  28. #define EP_RX_STALL(epr) EP_TOGGLE_SET((epr), USB_EP_RX_STALL, USB_EPRX_STAT)
  29. #define EP_TX_UNSTALL(epr) EP_TOGGLE_SET((epr), USB_EP_TX_NAK, USB_EPTX_STAT | USB_EP_DTOG_TX)
  30. #define EP_RX_UNSTALL(epr) EP_TOGGLE_SET((epr), USB_EP_RX_VALID, USB_EPRX_STAT | USB_EP_DTOG_RX)
  31. #define EP_DTX_UNSTALL(epr) EP_TOGGLE_SET((epr), USB_EP_TX_VALID, USB_EPTX_STAT | USB_EP_DTOG_TX | USB_EP_SWBUF_TX)
  32. #define EP_DRX_UNSTALL(epr) EP_TOGGLE_SET((epr), USB_EP_RX_VALID | USB_EP_SWBUF_RX, USB_EPRX_STAT | USB_EP_DTOG_RX | USB_EP_SWBUF_RX)
  33. #define EP_TX_VALID(epr) EP_TOGGLE_SET((epr), USB_EP_TX_VALID, USB_EPTX_STAT)
  34. #define EP_RX_VALID(epr) EP_TOGGLE_SET((epr), USB_EP_RX_VALID, USB_EPRX_STAT)
  35. #define STATUS_VAL(x) (x)
  36. typedef struct {
  37. uint16_t addr;
  38. uint16_t :16;
  39. uint16_t cnt;
  40. uint16_t :16;
  41. } pma_rec;
  42. typedef union pma_table {
  43. struct {
  44. pma_rec tx;
  45. pma_rec rx;
  46. };
  47. struct {
  48. pma_rec tx0;
  49. pma_rec tx1;
  50. };
  51. struct {
  52. pma_rec rx0;
  53. pma_rec rx1;
  54. };
  55. } pma_table;
  56. /** \brief Helper function. Returns pointer to the buffer descriptor table.
  57. */
  58. inline static pma_table *EPT(uint8_t ep) {
  59. return (pma_table*)((ep & 0x07) * 16 + USB_PMAADDR);
  60. }
  61. /** \brief Helper function. Returns pointer to the endpoint control register.
  62. */
  63. inline static volatile uint16_t *EPR(uint8_t ep) {
  64. return (uint16_t*)((ep & 0x07) * 4 + USB_BASE);
  65. }
  66. /** \brief Helper function. Returns next available PMA buffer.
  67. *
  68. * \param sz uint16_t Requested buffer size.
  69. * \return uint16_t Buffer address for PMA table.
  70. * \note PMA buffers grown from top to bottom like stack.
  71. */
  72. static uint16_t get_next_pma(uint16_t sz) {
  73. unsigned _result = USB_PMASIZE;
  74. for (int i = 0; i < 8; i++) {
  75. pma_table *tbl = EPT(i);
  76. if ((tbl->tx.addr) && (tbl->tx.addr < _result)) _result = tbl->tx.addr;
  77. if ((tbl->rx.addr) && (tbl->rx.addr < _result)) _result = tbl->rx.addr;
  78. }
  79. return (_result < (0x020 + sz)) ? 0 : (_result - sz);
  80. }
  81. uint32_t getinfo(void) {
  82. if (!(RCC->APB1ENR & RCC_APB1ENR_USBEN)) return STATUS_VAL(0);
  83. if (SYSCFG->PMC & SYSCFG_PMC_USB_PU) return STATUS_VAL(USBD_HW_ENABLED | USBD_HW_SPEED_FS);
  84. return STATUS_VAL(USBD_HW_ENABLED);
  85. }
  86. void ep_setstall(uint8_t ep, bool stall) {
  87. volatile uint16_t *reg = EPR(ep);
  88. /* ISOCHRONOUS endpoint can't be stalled or unstalled */
  89. if (USB_EP_ISOCHRONOUS == (*reg & USB_EP_T_FIELD)) return;
  90. /* If it's an IN endpoint */
  91. if (ep & 0x80) {
  92. /* DISABLED endpoint can't be stalled or unstalled */
  93. if (USB_EP_TX_DIS == (*reg & USB_EPTX_STAT)) return;
  94. if (stall) {
  95. EP_TX_STALL(reg);
  96. } else {
  97. /* if it's a doublebuffered endpoint */
  98. if ((USB_EP_KIND | USB_EP_BULK) == (*reg & (USB_EP_T_FIELD | USB_EP_KIND))) {
  99. /* set endpoint to VALID and clear DTOG_TX & SWBUF_TX */
  100. EP_DTX_UNSTALL(reg);
  101. } else {
  102. /* set endpoint to NAKED and clear DTOG_TX */
  103. EP_TX_UNSTALL(reg);
  104. }
  105. }
  106. } else {
  107. if (USB_EP_RX_DIS == (*reg & USB_EPRX_STAT)) return;
  108. if (stall) {
  109. EP_RX_STALL(reg);
  110. } else {
  111. /* if it's a doublebuffered endpoint */
  112. if ((USB_EP_KIND | USB_EP_BULK) == (*reg & (USB_EP_T_FIELD | USB_EP_KIND))) {
  113. /* set endpoint to VALID, clear DTOG_RX, set SWBUF_RX */
  114. EP_DRX_UNSTALL(reg);
  115. } else {
  116. /* set endpoint to VALID and clear DTOG_RX */
  117. EP_RX_UNSTALL(reg);
  118. }
  119. }
  120. }
  121. }
  122. bool ep_isstalled(uint8_t ep) {
  123. if (ep & 0x80) {
  124. return (USB_EP_TX_STALL == (USB_EPTX_STAT & *EPR(ep)));
  125. } else {
  126. return (USB_EP_RX_STALL == (USB_EPRX_STAT & *EPR(ep)));
  127. }
  128. }
  129. void enable(bool enable) {
  130. if (enable) {
  131. RCC->APB1ENR |= RCC_APB1ENR_USBEN;
  132. RCC->APB2ENR |= RCC_APB2ENR_SYSCFGEN;
  133. RCC->APB1RSTR |= RCC_APB1RSTR_USBRST;
  134. RCC->APB1RSTR &= ~RCC_APB1RSTR_USBRST;
  135. USB->CNTR = USB_CNTR_CTRM | USB_CNTR_RESETM | USB_CNTR_ERRM |
  136. #if !defined(USBD_SOF_DISABLED)
  137. USB_CNTR_SOFM |
  138. #endif
  139. USB_CNTR_SUSPM | USB_CNTR_WKUPM;
  140. } else if (RCC->APB1ENR & RCC_APB1ENR_USBEN) {
  141. SYSCFG->PMC &= ~SYSCFG_PMC_USB_PU;
  142. RCC->APB1RSTR |= RCC_APB1RSTR_USBRST;
  143. RCC->APB1ENR &= ~RCC_APB1ENR_USBEN;
  144. }
  145. }
  146. uint8_t connect(bool connect) {
  147. if (connect) {
  148. SYSCFG->PMC |= SYSCFG_PMC_USB_PU;
  149. } else {
  150. SYSCFG->PMC &= ~SYSCFG_PMC_USB_PU;
  151. }
  152. return usbd_lane_unk;
  153. }
  154. void setaddr (uint8_t addr) {
  155. USB->DADDR = USB_DADDR_EF | addr;
  156. }
  157. bool ep_config(uint8_t ep, uint8_t eptype, uint16_t epsize) {
  158. volatile uint16_t *reg = EPR(ep);
  159. pma_table *tbl = EPT(ep);
  160. /* epsize should be 16-bit aligned */
  161. if (epsize & 0x01) epsize++;
  162. switch (eptype) {
  163. case USB_EPTYPE_CONTROL:
  164. *reg = USB_EP_CONTROL | (ep & 0x07);
  165. break;
  166. case USB_EPTYPE_ISOCHRONUS:
  167. *reg = USB_EP_ISOCHRONOUS | (ep & 0x07);
  168. break;
  169. case USB_EPTYPE_BULK:
  170. *reg = USB_EP_BULK | (ep & 0x07);
  171. break;
  172. case USB_EPTYPE_BULK | USB_EPTYPE_DBLBUF:
  173. *reg = USB_EP_BULK | USB_EP_KIND | (ep & 0x07);
  174. break;
  175. default:
  176. *reg = USB_EP_INTERRUPT | (ep & 0x07);
  177. break;
  178. }
  179. /* if it TX or CONTROL endpoint */
  180. if ((ep & 0x80) || (eptype == USB_EPTYPE_CONTROL)) {
  181. uint16_t _pma;
  182. _pma = get_next_pma(epsize);
  183. if (_pma == 0) return false;
  184. tbl->tx.addr = _pma;
  185. tbl->tx.cnt = 0;
  186. if ((eptype == USB_EPTYPE_ISOCHRONUS) ||
  187. (eptype == (USB_EPTYPE_BULK | USB_EPTYPE_DBLBUF))) {
  188. _pma = get_next_pma(epsize);
  189. if (_pma == 0) return false;
  190. tbl->tx1.addr = _pma;
  191. tbl->tx1.cnt = 0;
  192. EP_DTX_UNSTALL(reg);
  193. } else {
  194. EP_TX_UNSTALL(reg);
  195. }
  196. }
  197. if (!(ep & 0x80)) {
  198. uint16_t _rxcnt;
  199. uint16_t _pma;
  200. if (epsize > 62) {
  201. if (epsize & 0x1F) {
  202. epsize &= 0x1F;
  203. } else {
  204. epsize -= 0x20;
  205. }
  206. _rxcnt = 0x8000 | (epsize << 5);
  207. epsize += 0x20;
  208. } else {
  209. _rxcnt = epsize << 9;
  210. }
  211. _pma = get_next_pma(epsize);
  212. if (_pma == 0) return false;
  213. tbl->rx.addr = _pma;
  214. tbl->rx.cnt = _rxcnt;
  215. if ((eptype == USB_EPTYPE_ISOCHRONUS) ||
  216. (eptype == (USB_EPTYPE_BULK | USB_EPTYPE_DBLBUF))) {
  217. _pma = get_next_pma(epsize);
  218. if (_pma == 0) return false;
  219. tbl->rx0.addr = _pma;
  220. tbl->rx0.cnt = _rxcnt;
  221. EP_DRX_UNSTALL(reg);
  222. } else {
  223. EP_RX_UNSTALL(reg);
  224. }
  225. }
  226. return true;
  227. }
  228. void ep_deconfig(uint8_t ep) {
  229. pma_table *ept = EPT(ep);
  230. *EPR(ep) &= ~USB_EPREG_MASK;
  231. ept->rx.addr = 0;
  232. ept->rx.cnt = 0;
  233. ept->tx.addr = 0;
  234. ept->tx.cnt = 0;
  235. }
  236. static uint16_t pma_read (uint8_t *buf, uint16_t blen, pma_rec *rx) {
  237. uint16_t *pma = (void*)(USB_PMAADDR + 2 * rx->addr);
  238. uint16_t rxcnt = rx->cnt & 0x03FF;
  239. rx->cnt &= ~0x3FF;
  240. if (blen > rxcnt) {
  241. blen = rxcnt;
  242. }
  243. rxcnt = blen;
  244. while (blen) {
  245. uint16_t _t = *pma;
  246. *buf++ = _t & 0xFF;
  247. if (--blen) {
  248. *buf++ = _t >> 8;
  249. pma += 2;
  250. blen--;
  251. } else break;
  252. }
  253. return rxcnt;
  254. }
  255. int32_t ep_read(uint8_t ep, void *buf, uint16_t blen) {
  256. pma_table *tbl = EPT(ep);
  257. volatile uint16_t *reg = EPR(ep);
  258. switch (*reg & (USB_EPRX_STAT | USB_EP_T_FIELD | USB_EP_KIND)) {
  259. /* doublebuffered bulk endpoint */
  260. case (USB_EP_RX_VALID | USB_EP_BULK | USB_EP_KIND):
  261. /* switching SWBUF if EP is NAKED */
  262. switch (*reg & (USB_EP_DTOG_RX | USB_EP_SWBUF_RX)) {
  263. case 0:
  264. case (USB_EP_DTOG_RX | USB_EP_SWBUF_RX):
  265. *reg = (*reg & USB_EPREG_MASK) | USB_EP_SWBUF_RX;
  266. break;
  267. default:
  268. break;
  269. }
  270. if (*reg & USB_EP_SWBUF_RX) {
  271. return pma_read(buf, blen, &(tbl->rx1));
  272. } else {
  273. return pma_read(buf, blen, &(tbl->rx0));
  274. }
  275. /* isochronous endpoint */
  276. case (USB_EP_RX_VALID | USB_EP_ISOCHRONOUS):
  277. if (*reg & USB_EP_DTOG_RX) {
  278. return pma_read(buf, blen, &(tbl->rx1));
  279. } else {
  280. return pma_read(buf, blen, &(tbl->rx0));
  281. }
  282. /* regular endpoint */
  283. case (USB_EP_RX_NAK | USB_EP_BULK):
  284. case (USB_EP_RX_NAK | USB_EP_CONTROL):
  285. case (USB_EP_RX_NAK | USB_EP_INTERRUPT):
  286. {
  287. int32_t res = pma_read(buf, blen, &(tbl->rx));
  288. /* setting endpoint to VALID state */
  289. EP_RX_VALID(reg);
  290. return res;
  291. }
  292. /* invalid or not ready */
  293. default:
  294. return -1;
  295. }
  296. }
  297. static void pma_write(const uint8_t *buf, uint16_t blen, pma_rec *tx) {
  298. uint16_t *pma = (void*)(USB_PMAADDR + 2 * (tx->addr));
  299. tx->cnt = blen;
  300. while (blen > 1) {
  301. *pma = buf[1] << 8 | buf[0];
  302. pma += 2;
  303. buf += 2;
  304. blen -= 2;
  305. }
  306. if (blen) *pma = *buf;
  307. }
  308. int32_t ep_write(uint8_t ep, void *buf, uint16_t blen) {
  309. pma_table *tbl = EPT(ep);
  310. volatile uint16_t *reg = EPR(ep);
  311. switch (*reg & (USB_EPTX_STAT | USB_EP_T_FIELD | USB_EP_KIND)) {
  312. /* doublebuffered bulk endpoint */
  313. case (USB_EP_TX_NAK | USB_EP_BULK | USB_EP_KIND):
  314. if (*reg & USB_EP_SWBUF_TX) {
  315. pma_write(buf, blen, &(tbl->tx1));
  316. } else {
  317. pma_write(buf, blen, &(tbl->tx0));
  318. }
  319. *reg = (*reg & USB_EPREG_MASK) | USB_EP_SWBUF_TX;
  320. break;
  321. /* isochronous endpoint */
  322. case (USB_EP_TX_VALID | USB_EP_ISOCHRONOUS):
  323. if (!(*reg & USB_EP_DTOG_TX)) {
  324. pma_write(buf, blen, &(tbl->tx1));
  325. } else {
  326. pma_write(buf, blen, &(tbl->tx0));
  327. }
  328. break;
  329. /* regular endpoint */
  330. case (USB_EP_TX_NAK | USB_EP_BULK):
  331. case (USB_EP_TX_NAK | USB_EP_CONTROL):
  332. case (USB_EP_TX_NAK | USB_EP_INTERRUPT):
  333. pma_write(buf, blen, &(tbl->tx));
  334. EP_TX_VALID(reg);
  335. break;
  336. /* invalid or not ready */
  337. default:
  338. return -1;
  339. }
  340. return blen;
  341. }
  342. uint16_t get_frame (void) {
  343. return USB->FNR & USB_FNR_FN;
  344. }
  345. void evt_poll(usbd_device *dev, usbd_evt_callback callback) {
  346. uint8_t _ev, _ep;
  347. uint16_t _istr = USB->ISTR;
  348. _ep = _istr & USB_ISTR_EP_ID;
  349. if (_istr & USB_ISTR_CTR) {
  350. volatile uint16_t *reg = EPR(_ep);
  351. if (*reg & USB_EP_CTR_TX) {
  352. *reg &= (USB_EPREG_MASK ^ USB_EP_CTR_TX);
  353. _ep |= 0x80;
  354. _ev = usbd_evt_eptx;
  355. } else {
  356. *reg &= (USB_EPREG_MASK ^ USB_EP_CTR_RX);
  357. _ev = (*reg & USB_EP_SETUP) ? usbd_evt_epsetup : usbd_evt_eprx;
  358. }
  359. } else if (_istr & USB_ISTR_RESET) {
  360. USB->ISTR &= ~USB_ISTR_RESET;
  361. USB->BTABLE = 0;
  362. for (int i = 0; i < 8; i++) {
  363. ep_deconfig(i);
  364. }
  365. _ev = usbd_evt_reset;
  366. #if !defined(USBD_SOF_DISABLED)
  367. } else if (_istr & USB_ISTR_SOF) {
  368. _ev = usbd_evt_sof;
  369. USB->ISTR &= ~USB_ISTR_SOF;
  370. #endif
  371. } else if (_istr & USB_ISTR_WKUP) {
  372. _ev = usbd_evt_wkup;
  373. USB->CNTR &= ~USB_CNTR_FSUSP;
  374. USB->ISTR &= ~USB_ISTR_WKUP;
  375. } else if (_istr & USB_ISTR_SUSP) {
  376. _ev = usbd_evt_susp;
  377. USB->CNTR |= USB_CNTR_FSUSP;
  378. USB->ISTR &= ~USB_ISTR_SUSP;
  379. } else if (_istr & USB_ISTR_ERR) {
  380. USB->ISTR &= ~USB_ISTR_ERR;
  381. _ev = usbd_evt_error;
  382. } else {
  383. return;
  384. }
  385. callback(dev, _ev, _ep);
  386. }
  387. static uint32_t fnv1a32_turn (uint32_t fnv, uint32_t data ) {
  388. for (int i = 0; i < 4 ; i++) {
  389. fnv ^= (data & 0xFF);
  390. fnv *= 16777619;
  391. data >>= 8;
  392. }
  393. return fnv;
  394. }
  395. uint16_t get_serialno_desc(void *buffer) {
  396. struct usb_string_descriptor *dsc = buffer;
  397. uint16_t *str = dsc->wString;
  398. uint32_t fnv = 2166136261;
  399. fnv = fnv1a32_turn(fnv, *(uint32_t*)(UID_BASE + 0x00));
  400. fnv = fnv1a32_turn(fnv, *(uint32_t*)(UID_BASE + 0x04));
  401. fnv = fnv1a32_turn(fnv, *(uint32_t*)(UID_BASE + 0x14));
  402. for (int i = 28; i >= 0; i -= 4 ) {
  403. uint16_t c = (fnv >> i) & 0x0F;
  404. c += (c < 10) ? '0' : ('A' - 10);
  405. *str++ = c;
  406. }
  407. dsc->bDescriptorType = USB_DTYPE_STRING;
  408. dsc->bLength = 18;
  409. return 18;
  410. }
  411. __attribute__((externally_visible)) const struct usbd_driver usbd_devfs = {
  412. getinfo,
  413. enable,
  414. connect,
  415. setaddr,
  416. ep_config,
  417. ep_deconfig,
  418. ep_read,
  419. ep_write,
  420. ep_setstall,
  421. ep_isstalled,
  422. evt_poll,
  423. get_frame,
  424. get_serialno_desc,
  425. };
  426. #endif //USBD_STM32L100