You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
This repo is archived. You can view files and clone it, but cannot push or open issues/pull-requests.

cdc_XR21B1411.h 13KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272
  1. /* Copyright (C) 2015 Andrew J. Kroll
  2. and
  3. Circuits At Home, LTD. All rights reserved.
  4. This software may be distributed and modified under the terms of the GNU
  5. General Public License version 2 (GPL2) as published by the Free Software
  6. Foundation and appearing in the file GPL2.TXT included in the packaging of
  7. this file. Please note that GPL2 Section 2[b] requires that all works based
  8. on this software must also be made publicly available under the terms of
  9. the GPL2 ("Copyleft").
  10. Contact information
  11. -------------------
  12. Circuits At Home, LTD
  13. Web : http://www.circuitsathome.com
  14. e-mail : [email protected]
  15. */
  16. #if !defined(__CDC_XR21B1411_H__)
  17. #define __CDC_XR21B1411_H__
  18. #include "cdcacm.h"
  19. #define XR_REG_CUSTOM_DRIVER (0x020DU) // DRIVER SELECT
  20. #define XR_REG_CUSTOM_DRIVER_ACTIVE (0x0001U) // 0: CDC 1: CUSTOM
  21. #define XR_REG_ACM_FLOW_CTL (0x0216U) // FLOW CONTROL REGISTER CDCACM MODE
  22. #define XR_REG_FLOW_CTL (0x0C06U) // FLOW CONTROL REGISTER CUSTOM MODE
  23. #define XR_REG_FLOW_CTL_HALF_DPLX (0x0008U) // 0:FULL DUPLEX 1:HALF DUPLEX
  24. #define XR_REG_FLOW_CTL_MODE_MASK (0x0007U) // MODE BITMASK
  25. #define XR_REG_FLOW_CTL_NONE (0x0000U) // NO FLOW CONTROL
  26. #define XR_REG_FLOW_CTL_HW (0x0001U) // HARDWARE FLOW CONTROL
  27. #define XR_REG_FLOW_CTL_SW (0x0002U) // SOFTWARE FLOW CONTROL
  28. #define XR_REG_FLOW_CTL_MMMRX (0x0003U) // MULTIDROP RX UPON ADDRESS MATCH
  29. #define XR_REG_FLOW_CTL_MMMRXTX (0x0004U) // MULTIDROP RX/TX UPON ADDRESS MATCH
  30. #define XR_REG_ACM_GPIO_MODE (0x0217U) // GPIO MODE REGISTER IN CDCACM MODE
  31. #define XR_REG_GPIO_MODE (0x0C0CU) // GPIO MODE REGISTER IN CUSTOM MODE
  32. #define XR_REG_GPIO_MODE_GPIO (0x0000U) // ALL GPIO PINS ACM PROGRAMMABLE
  33. #define XR_REG_GPIO_MODE_FC_RTSCTS (0x0001U) // AUTO RTSCTS HW FC (GPIO 4/5)
  34. #define XR_REG_GPIO_MODE_FC_DTRDSR (0x0002U) // AUTO DTRDSR HW FC (GPIO 2/3)
  35. #define XR_REG_GPIO_MODE_ATE (0x0003U) // AUTO TRANSCEIVER ENABLE DURING TX (GPIO 5)
  36. #define XR_REG_GPIO_MODE_ATE_ADDRESS (0x0004U) // AUTO TRANSCEIVER ENABLE ON ADDRESS MATCH (GPIO 5)
  37. #define XR_REG_ACM_GPIO_DIR (0x0218U) // GPIO DIRECTION REGISTER CDCACM MODE, 0:IN 1:OUT
  38. #define XR_REG_GPIO_DIR (0x0C0DU) // GPIO DIRECTION REGISTER CUSTOM MODE, 0:IN 1:OUT
  39. #define XR_REG_ACM_GPIO_INT (0x0219U) // GPIO PIN CHANGE INTERRUPT ENABLE CDCACM MODE, 0: ENABLED 1: DISABLED
  40. #define XR_REG_GPIO_INT (0x0C11U) // GPIO PIN CHANGE INTERRUPT ENABLE CUSTOM MODE, 0: ENABLED 1: DISABLED
  41. #define XR_REG_GPIO_MASK (0x001FU) // GPIO REGISTERS BITMASK
  42. #define XR_REG_UART_ENABLE (0x0C00U) // UART I/O ENABLE REGISTER
  43. #define XR_REG_UART_ENABLE_RX (0x0002U) // 0:DISABLED 1:ENABLED
  44. #define XR_REG_UART_ENABLE_TX (0x0001U) // 0:DISABLED 1:ENABLED
  45. #define XR_REG_ERROR_STATUS (0x0C09U) // ERROR STATUS REGISTER
  46. #define XR_REG_ERROR_STATUS_MASK (0x00F8U) // ERROR STATUS BITMASK
  47. #define XR_REG_ERROR_STATUS_ERROR (0x0078U) // ERROR STATUS ERROR BITMASK
  48. #define XR_REG_ERROR_STATUS_BREAK (0x0008U) // BREAK ERROR HAS BEEN DETECTED
  49. #define XR_REG_ERROR_STATUS_FRAME (0x0010U) // FRAMING ERROR HAS BEEN DETECTED
  50. #define XR_REG_ERROR_STATUS_PARITY (0x0020U) // PARITY ERROR HAS BEEN DETECTED
  51. #define XR_REG_ERROR_STATUS_OVERRUN (0x0040U) // RX OVERRUN ERROR HAS BEEN DETECTED
  52. #define XR_REG_ERROR_STATUS_BREAK_STATUS (0x0080U) // BREAK CONDITION IS CURRENTLY BEING DETECTED
  53. #define XR_REG_TX_BREAK (0x0C0AU) // TRANSMIT BREAK. 0X0001-0XFFE TIME IN MS, 0X0000 STOP, 0X0FFF BREAK ON
  54. #define XR_REG_XCVR_EN_DELAY (0x0C0BU) // TURN-ARROUND DELAY IN BIT-TIMES 0X0000-0X000F
  55. #define XR_REG_GPIO_SET (0x0C0EU) // 1:SET GPIO PIN
  56. #define XR_REG_GPIO_CLR (0x0C0FU) // 1:CLEAR GPIO PIN
  57. #define XR_REG_GPIO_STATUS (0x0C10U) // READ GPIO PINS
  58. #define XR_REG_CUSTOMISED_INT (0x0C12U) // 0:STANDARD 1:CUSTOM SEE DATA SHEET
  59. #define XR_REG_PIN_PULLUP_ENABLE (0x0C14U) // 0:DISABLE 1:ENABLE, BITS 0-5:GPIO, 6:RX 7:TX
  60. #define XR_REG_PIN_PULLDOWN_ENABLE (0x0C15U) // 0:DISABLE 1:ENABLE, BITS 0-5:GPIO, 6:RX 7:TX
  61. #define XR_REG_LOOPBACK (0x0C16U) // 0:DISABLE 1:ENABLE, SEE DATA SHEET
  62. #define XR_REG_RX_FIFO_LATENCY (0x0CC2U) // FIFO LATENCY REGISTER
  63. #define XR_REG_RX_FIFO_LATENCY_ENABLE (0x0001U) //
  64. #define XR_REG_WIDE_MODE (0x0D02U)
  65. #define XR_REG_WIDE_MODE_ENABLE (0x0001U)
  66. #define XR_REG_XON_CHAR (0x0C07U)
  67. #define XR_REG_XOFF_CHAR (0x0C08U)
  68. #define XR_REG_TX_FIFO_RESET (0x0C80U) // 1: RESET, SELF-CLEARING
  69. #define XR_REG_TX_FIFO_COUNT (0x0C81U) // READ-ONLY
  70. #define XR_REG_RX_FIFO_RESET (0x0CC0U) // 1: RESET, SELF-CLEARING
  71. #define XR_REG_RX_FIFO_COUNT (0x0CC1U) // READ-ONLY
  72. #define XR_WRITE_REQUEST_TYPE (0x40U)
  73. #define XR_READ_REQUEST_TYPE (0xC0U)
  74. #define XR_MAX_ENDPOINTS 4
  75. class XR21B1411 : public ACM {
  76. protected:
  77. public:
  78. XR21B1411(USB *pusb, CDCAsyncOper *pasync);
  79. /**
  80. * Used by the USB core to check what this driver support.
  81. * @param vid The device's VID.
  82. * @param pid The device's PID.
  83. * @return Returns true if the device's VID and PID matches this driver.
  84. */
  85. virtual bool VIDPIDOK(uint16_t vid, uint16_t pid) {
  86. return (((vid == 0x2890U) && (pid == 0x0201U)) || ((vid == 0x04e2U) && (pid == 0x1411U)));
  87. };
  88. uint8_t Init(uint8_t parent, uint8_t port, bool lowspeed);
  89. virtual tty_features enhanced_features(void) {
  90. tty_features rv;
  91. rv.enhanced = true;
  92. rv.autoflow_RTS = true;
  93. rv.autoflow_DSR = true;
  94. rv.autoflow_XON = true;
  95. rv.half_duplex = true;
  96. rv.wide = true;
  97. return rv;
  98. };
  99. uint8_t read_register(uint16_t reg, uint16_t *val) {
  100. return (pUsb->ctrlReq(bAddress, 0, XR_READ_REQUEST_TYPE, 1, 0, 0, reg, 2, 2, (uint8_t *)val, NULL));
  101. }
  102. uint8_t write_register(uint16_t reg, uint16_t val) {
  103. return (pUsb->ctrlReq(bAddress, 0, XR_WRITE_REQUEST_TYPE, 0, BGRAB0(val), BGRAB1(val), reg, 0, 0, NULL, NULL));
  104. }
  105. ////////////////////////////////////////////////////////////////////////
  106. // The following methods set the CDC-ACM defaults.
  107. ////////////////////////////////////////////////////////////////////////
  108. virtual void autoflowRTS(bool s) {
  109. uint16_t val;
  110. uint8_t rval;
  111. rval = read_register(XR_REG_ACM_FLOW_CTL, &val);
  112. if(!rval) {
  113. if(s) {
  114. val &= XR_REG_FLOW_CTL_HALF_DPLX;
  115. val |= XR_REG_FLOW_CTL_HW;
  116. } else {
  117. val &= XR_REG_FLOW_CTL_HALF_DPLX;
  118. }
  119. rval = write_register(XR_REG_ACM_FLOW_CTL, val);
  120. if(!rval) {
  121. rval = write_register(XR_REG_ACM_GPIO_MODE, XR_REG_GPIO_MODE_GPIO);
  122. if(!rval) {
  123. // ACM commands apply the new settings.
  124. LINE_CODING LCT;
  125. rval = GetLineCoding(&LCT);
  126. if(!rval) {
  127. rval = SetLineCoding(&LCT);
  128. if(!rval) {
  129. _enhanced_status.autoflow_XON = false;
  130. _enhanced_status.autoflow_DSR = false;
  131. _enhanced_status.autoflow_RTS = s;
  132. }
  133. }
  134. }
  135. }
  136. }
  137. };
  138. virtual void autoflowDSR(bool s) {
  139. uint16_t val;
  140. uint8_t rval;
  141. rval = read_register(XR_REG_ACM_FLOW_CTL, &val);
  142. if(!rval) {
  143. if(s) {
  144. val &= XR_REG_FLOW_CTL_HALF_DPLX;
  145. val |= XR_REG_FLOW_CTL_HW;
  146. } else {
  147. val &= XR_REG_FLOW_CTL_HALF_DPLX;
  148. }
  149. rval = write_register(XR_REG_ACM_FLOW_CTL, val);
  150. if(!rval) {
  151. if(s) {
  152. rval = write_register(XR_REG_ACM_GPIO_MODE, XR_REG_GPIO_MODE_FC_DTRDSR);
  153. } else {
  154. rval = write_register(XR_REG_ACM_GPIO_MODE, XR_REG_GPIO_MODE_GPIO);
  155. }
  156. if(!rval) {
  157. // ACM commands apply the new settings.
  158. LINE_CODING LCT;
  159. rval = GetLineCoding(&LCT);
  160. if(!rval) {
  161. rval = SetLineCoding(&LCT);
  162. if(!rval) {
  163. _enhanced_status.autoflow_XON = false;
  164. _enhanced_status.autoflow_RTS = false;
  165. _enhanced_status.autoflow_DSR = s;
  166. }
  167. }
  168. }
  169. }
  170. }
  171. };
  172. virtual void autoflowXON(bool s) {
  173. // NOTE: hardware defaults to the normal XON/XOFF
  174. uint16_t val;
  175. uint8_t rval;
  176. rval = read_register(XR_REG_ACM_FLOW_CTL, &val);
  177. if(!rval) {
  178. if(s) {
  179. val &= XR_REG_FLOW_CTL_HALF_DPLX;
  180. val |= XR_REG_FLOW_CTL_SW;
  181. } else {
  182. val &= XR_REG_FLOW_CTL_HALF_DPLX;
  183. }
  184. rval = write_register(XR_REG_ACM_FLOW_CTL, val);
  185. if(!rval) {
  186. rval = write_register(XR_REG_ACM_GPIO_MODE, XR_REG_GPIO_MODE_GPIO);
  187. if(!rval) {
  188. // ACM commands apply the new settings.
  189. LINE_CODING LCT;
  190. rval = GetLineCoding(&LCT);
  191. if(!rval) {
  192. rval = SetLineCoding(&LCT);
  193. if(!rval) {
  194. _enhanced_status.autoflow_RTS = false;
  195. _enhanced_status.autoflow_DSR = false;
  196. _enhanced_status.autoflow_XON = s;
  197. }
  198. }
  199. }
  200. }
  201. }
  202. };
  203. virtual void half_duplex(bool s) {
  204. uint16_t val;
  205. uint8_t rval;
  206. rval = read_register(XR_REG_ACM_FLOW_CTL, &val);
  207. if(!rval) {
  208. if(s) {
  209. val |= XR_REG_FLOW_CTL_HALF_DPLX;
  210. } else {
  211. val &= XR_REG_FLOW_CTL_MODE_MASK;
  212. }
  213. rval = write_register(XR_REG_ACM_FLOW_CTL, val);
  214. if(!rval) {
  215. // ACM commands apply the new settings.
  216. LINE_CODING LCT;
  217. rval = GetLineCoding(&LCT);
  218. if(!rval) {
  219. rval = SetLineCoding(&LCT);
  220. if(!rval) {
  221. _enhanced_status.half_duplex = s;
  222. }
  223. }
  224. }
  225. }
  226. };
  227. };
  228. #endif // __CDCPROLIFIC_H__