Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Fork of USBDevice by
USBHAL_LPC17.cpp
00001 /* Copyright (c) 2010-2011 mbed.org, MIT License 00002 * 00003 * Permission is hereby granted, free of charge, to any person obtaining a copy of this software 00004 * and associated documentation files (the "Software"), to deal in the Software without 00005 * restriction, including without limitation the rights to use, copy, modify, merge, publish, 00006 * distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the 00007 * Software is furnished to do so, subject to the following conditions: 00008 * 00009 * The above copyright notice and this permission notice shall be included in all copies or 00010 * substantial portions of the Software. 00011 * 00012 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING 00013 * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 00014 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, 00015 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 00016 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 00017 */ 00018 00019 #ifdef TARGET_LPC1768 00020 00021 #include "USBHAL.h" 00022 00023 00024 // Get endpoint direction 00025 #define IN_EP(endpoint) ((endpoint) & 1U ? true : false) 00026 #define OUT_EP(endpoint) ((endpoint) & 1U ? false : true) 00027 00028 // Convert physical endpoint number to register bit 00029 #define EP(endpoint) (1UL<<endpoint) 00030 00031 // Power Control for Peripherals register 00032 #define PCUSB (1UL<<31) 00033 00034 // USB Clock Control register 00035 #define DEV_CLK_EN (1UL<<1) 00036 #define AHB_CLK_EN (1UL<<4) 00037 00038 // USB Clock Status register 00039 #define DEV_CLK_ON (1UL<<1) 00040 #define AHB_CLK_ON (1UL<<4) 00041 00042 // USB Device Interupt registers 00043 #define FRAME (1UL<<0) 00044 #define EP_FAST (1UL<<1) 00045 #define EP_SLOW (1UL<<2) 00046 #define DEV_STAT (1UL<<3) 00047 #define CCEMPTY (1UL<<4) 00048 #define CDFULL (1UL<<5) 00049 #define RxENDPKT (1UL<<6) 00050 #define TxENDPKT (1UL<<7) 00051 #define EP_RLZED (1UL<<8) 00052 #define ERR_INT (1UL<<9) 00053 00054 // USB Control register 00055 #define RD_EN (1<<0) 00056 #define WR_EN (1<<1) 00057 #define LOG_ENDPOINT(endpoint) ((endpoint>>1)<<2) 00058 00059 // USB Receive Packet Length register 00060 #define DV (1UL<<10) 00061 #define PKT_RDY (1UL<<11) 00062 #define PKT_LNGTH_MASK (0x3ff) 00063 00064 // Serial Interface Engine (SIE) 00065 #define SIE_WRITE (0x01) 00066 #define SIE_READ (0x02) 00067 #define SIE_COMMAND (0x05) 00068 #define SIE_CMD_CODE(phase, data) ((phase<<8)|(data<<16)) 00069 00070 // SIE Command codes 00071 #define SIE_CMD_SET_ADDRESS (0xD0) 00072 #define SIE_CMD_CONFIGURE_DEVICE (0xD8) 00073 #define SIE_CMD_SET_MODE (0xF3) 00074 #define SIE_CMD_READ_FRAME_NUMBER (0xF5) 00075 #define SIE_CMD_READ_TEST_REGISTER (0xFD) 00076 #define SIE_CMD_SET_DEVICE_STATUS (0xFE) 00077 #define SIE_CMD_GET_DEVICE_STATUS (0xFE) 00078 #define SIE_CMD_GET_ERROR_CODE (0xFF) 00079 #define SIE_CMD_READ_ERROR_STATUS (0xFB) 00080 00081 #define SIE_CMD_SELECT_ENDPOINT(endpoint) (0x00+endpoint) 00082 #define SIE_CMD_SELECT_ENDPOINT_CLEAR_INTERRUPT(endpoint) (0x40+endpoint) 00083 #define SIE_CMD_SET_ENDPOINT_STATUS(endpoint) (0x40+endpoint) 00084 00085 #define SIE_CMD_CLEAR_BUFFER (0xF2) 00086 #define SIE_CMD_VALIDATE_BUFFER (0xFA) 00087 00088 // SIE Device Status register 00089 #define SIE_DS_CON (1<<0) 00090 #define SIE_DS_CON_CH (1<<1) 00091 #define SIE_DS_SUS (1<<2) 00092 #define SIE_DS_SUS_CH (1<<3) 00093 #define SIE_DS_RST (1<<4) 00094 00095 // SIE Device Set Address register 00096 #define SIE_DSA_DEV_EN (1<<7) 00097 00098 // SIE Configue Device register 00099 #define SIE_CONF_DEVICE (1<<0) 00100 00101 // Select Endpoint register 00102 #define SIE_SE_FE (1<<0) 00103 #define SIE_SE_ST (1<<1) 00104 #define SIE_SE_STP (1<<2) 00105 #define SIE_SE_PO (1<<3) 00106 #define SIE_SE_EPN (1<<4) 00107 #define SIE_SE_B_1_FULL (1<<5) 00108 #define SIE_SE_B_2_FULL (1<<6) 00109 00110 // Set Endpoint Status command 00111 #define SIE_SES_ST (1<<0) 00112 #define SIE_SES_DA (1<<5) 00113 #define SIE_SES_RF_MO (1<<6) 00114 #define SIE_SES_CND_ST (1<<7) 00115 00116 00117 USBHAL * USBHAL::instance; 00118 00119 volatile int epComplete; 00120 uint32_t endpointStallState; 00121 00122 static void SIECommand(uint32_t command) { 00123 // The command phase of a SIE transaction 00124 LPC_USB->USBDevIntClr = CCEMPTY; 00125 LPC_USB->USBCmdCode = SIE_CMD_CODE(SIE_COMMAND, command); 00126 while (!(LPC_USB->USBDevIntSt & CCEMPTY)); 00127 } 00128 00129 static void SIEWriteData(uint8_t data) { 00130 // The data write phase of a SIE transaction 00131 LPC_USB->USBDevIntClr = CCEMPTY; 00132 LPC_USB->USBCmdCode = SIE_CMD_CODE(SIE_WRITE, data); 00133 while (!(LPC_USB->USBDevIntSt & CCEMPTY)); 00134 } 00135 00136 static uint8_t SIEReadData(uint32_t command) { 00137 // The data read phase of a SIE transaction 00138 LPC_USB->USBDevIntClr = CDFULL; 00139 LPC_USB->USBCmdCode = SIE_CMD_CODE(SIE_READ, command); 00140 while (!(LPC_USB->USBDevIntSt & CDFULL)); 00141 return (uint8_t)LPC_USB->USBCmdData; 00142 } 00143 00144 static void SIEsetDeviceStatus(uint8_t status) { 00145 // Write SIE device status register 00146 SIECommand(SIE_CMD_SET_DEVICE_STATUS); 00147 SIEWriteData(status); 00148 } 00149 00150 static uint8_t SIEgetDeviceStatus(void) { 00151 // Read SIE device status register 00152 SIECommand(SIE_CMD_GET_DEVICE_STATUS); 00153 return SIEReadData(SIE_CMD_GET_DEVICE_STATUS); 00154 } 00155 00156 void SIEsetAddress(uint8_t address) { 00157 // Write SIE device address register 00158 SIECommand(SIE_CMD_SET_ADDRESS); 00159 SIEWriteData((address & 0x7f) | SIE_DSA_DEV_EN); 00160 } 00161 00162 static uint8_t SIEselectEndpoint(uint8_t endpoint) { 00163 // SIE select endpoint command 00164 SIECommand(SIE_CMD_SELECT_ENDPOINT(endpoint)); 00165 return SIEReadData(SIE_CMD_SELECT_ENDPOINT(endpoint)); 00166 } 00167 00168 static uint8_t SIEclearBuffer(void) { 00169 // SIE clear buffer command 00170 SIECommand(SIE_CMD_CLEAR_BUFFER); 00171 return SIEReadData(SIE_CMD_CLEAR_BUFFER); 00172 } 00173 00174 static void SIEvalidateBuffer(void) { 00175 // SIE validate buffer command 00176 SIECommand(SIE_CMD_VALIDATE_BUFFER); 00177 } 00178 00179 static void SIEsetEndpointStatus(uint8_t endpoint, uint8_t status) { 00180 // SIE set endpoint status command 00181 SIECommand(SIE_CMD_SET_ENDPOINT_STATUS(endpoint)); 00182 SIEWriteData(status); 00183 } 00184 00185 static uint16_t SIEgetFrameNumber(void) __attribute__ ((unused)); 00186 static uint16_t SIEgetFrameNumber(void) { 00187 // Read current frame number 00188 uint16_t lowByte; 00189 uint16_t highByte; 00190 00191 SIECommand(SIE_CMD_READ_FRAME_NUMBER); 00192 lowByte = SIEReadData(SIE_CMD_READ_FRAME_NUMBER); 00193 highByte = SIEReadData(SIE_CMD_READ_FRAME_NUMBER); 00194 00195 return (highByte << 8) | lowByte; 00196 } 00197 00198 static void SIEconfigureDevice(void) { 00199 // SIE Configure device command 00200 SIECommand(SIE_CMD_CONFIGURE_DEVICE); 00201 SIEWriteData(SIE_CONF_DEVICE); 00202 } 00203 00204 static void SIEunconfigureDevice(void) { 00205 // SIE Configure device command 00206 SIECommand(SIE_CMD_CONFIGURE_DEVICE); 00207 SIEWriteData(0); 00208 } 00209 00210 static void SIEconnect(void) { 00211 // Connect USB device 00212 uint8_t status; 00213 00214 status = SIEgetDeviceStatus(); 00215 SIEsetDeviceStatus(status | SIE_DS_CON); 00216 } 00217 00218 00219 static void SIEdisconnect(void) { 00220 // Disconnect USB device 00221 uint8_t status; 00222 00223 status = SIEgetDeviceStatus(); 00224 SIEsetDeviceStatus(status & ~SIE_DS_CON); 00225 } 00226 00227 00228 static uint8_t selectEndpointClearInterrupt(uint8_t endpoint) { 00229 // Implemented using using EP_INT_CLR. 00230 LPC_USB->USBEpIntClr = EP(endpoint); 00231 while (!(LPC_USB->USBDevIntSt & CDFULL)); 00232 return (uint8_t)LPC_USB->USBCmdData; 00233 } 00234 00235 00236 00237 00238 00239 static void enableEndpointEvent(uint8_t endpoint) { 00240 // Enable an endpoint interrupt 00241 LPC_USB->USBEpIntEn |= EP(endpoint); 00242 } 00243 00244 static void disableEndpointEvent(uint8_t endpoint) __attribute__ ((unused)); 00245 static void disableEndpointEvent(uint8_t endpoint) { 00246 // Disable an endpoint interrupt 00247 LPC_USB->USBEpIntEn &= ~EP(endpoint); 00248 } 00249 00250 static volatile uint32_t __attribute__((used)) dummyRead; 00251 00252 00253 uint32_t USBHAL::endpointReadcore(uint8_t endpoint, uint8_t *buffer) { 00254 // Read from an OUT endpoint 00255 uint32_t size; 00256 uint32_t i; 00257 uint32_t data = 0; 00258 uint8_t offset; 00259 00260 LPC_USB->USBCtrl = LOG_ENDPOINT(endpoint) | RD_EN; 00261 while (!(LPC_USB->USBRxPLen & PKT_RDY)); 00262 00263 size = LPC_USB->USBRxPLen & PKT_LNGTH_MASK; 00264 00265 offset = 0; 00266 00267 if (size > 0) { 00268 for (i=0; i<size; i++) { 00269 if (offset==0) { 00270 // Fetch up to four bytes of data as a word 00271 data = LPC_USB->USBRxData; 00272 } 00273 00274 // extract a byte 00275 *buffer = (data>>offset) & 0xff; 00276 buffer++; 00277 00278 // move on to the next byte 00279 offset = (offset + 8) % 32; 00280 } 00281 } else { 00282 dummyRead = LPC_USB->USBRxData; 00283 } 00284 00285 LPC_USB->USBCtrl = 0; 00286 00287 if ((endpoint >> 1) % 3 || (endpoint >> 1) == 0) { 00288 SIEselectEndpoint(endpoint); 00289 SIEclearBuffer(); 00290 } 00291 00292 return size; 00293 } 00294 00295 static void endpointWritecore(uint8_t endpoint, uint8_t *buffer, uint32_t size) { 00296 // Write to an IN endpoint 00297 uint32_t temp, data; 00298 uint8_t offset; 00299 00300 LPC_USB->USBCtrl = LOG_ENDPOINT(endpoint) | WR_EN; 00301 00302 LPC_USB->USBTxPLen = size; 00303 offset = 0; 00304 data = 0; 00305 00306 if (size>0) { 00307 do { 00308 // Fetch next data byte into a word-sized temporary variable 00309 temp = *buffer++; 00310 00311 // Add to current data word 00312 temp = temp << offset; 00313 data = data | temp; 00314 00315 // move on to the next byte 00316 offset = (offset + 8) % 32; 00317 size--; 00318 00319 if ((offset==0) || (size==0)) { 00320 // Write the word to the endpoint 00321 LPC_USB->USBTxData = data; 00322 data = 0; 00323 } 00324 } while (size>0); 00325 } else { 00326 LPC_USB->USBTxData = 0; 00327 } 00328 00329 // Clear WR_EN to cover zero length packet case 00330 LPC_USB->USBCtrl=0; 00331 00332 SIEselectEndpoint(endpoint); 00333 SIEvalidateBuffer(); 00334 } 00335 00336 00337 00338 00339 00340 00341 00342 USBHAL::USBHAL(void) { 00343 // Disable IRQ 00344 NVIC_DisableIRQ(USB_IRQn); 00345 00346 // Enable power to USB device controller 00347 LPC_SC->PCONP |= PCUSB; 00348 00349 // Enable USB clocks 00350 LPC_USB->USBClkCtrl |= DEV_CLK_EN | AHB_CLK_EN; 00351 while (LPC_USB->USBClkSt != (DEV_CLK_ON | AHB_CLK_ON)); 00352 00353 // Configure pins P0.29 and P0.30 to be USB D+ and USB D- 00354 LPC_PINCON->PINSEL1 &= 0xc3ffffff; 00355 LPC_PINCON->PINSEL1 |= 0x14000000; 00356 00357 // Disconnect USB device 00358 SIEdisconnect(); 00359 00360 // Configure pin P2.9 to be Connect 00361 LPC_PINCON->PINSEL4 &= 0xfffcffff; 00362 LPC_PINCON->PINSEL4 |= 0x00040000; 00363 00364 // Connect must be low for at least 2.5uS 00365 wait(0.3); 00366 00367 // Set the maximum packet size for the control endpoints 00368 realiseEndpoint(EP0IN, MAX_PACKET_SIZE_EP0, 0); 00369 realiseEndpoint(EP0OUT, MAX_PACKET_SIZE_EP0, 0); 00370 00371 // Attach IRQ 00372 instance = this; 00373 NVIC_SetVector(USB_IRQn, (uint32_t)&_usbisr); 00374 NVIC_EnableIRQ(USB_IRQn); 00375 00376 // Enable interrupts for device events and EP0 00377 LPC_USB->USBDevIntEn = EP_SLOW | DEV_STAT | FRAME; 00378 enableEndpointEvent(EP0IN); 00379 enableEndpointEvent(EP0OUT); 00380 } 00381 00382 USBHAL::~USBHAL(void) { 00383 // Ensure device disconnected 00384 SIEdisconnect(); 00385 00386 // Disable USB interrupts 00387 NVIC_DisableIRQ(USB_IRQn); 00388 } 00389 00390 void USBHAL::connect(void) { 00391 // Connect USB device 00392 SIEconnect(); 00393 } 00394 00395 void USBHAL::disconnect(void) { 00396 // Disconnect USB device 00397 SIEdisconnect(); 00398 } 00399 00400 void USBHAL::configureDevice(void) { 00401 SIEconfigureDevice(); 00402 } 00403 00404 void USBHAL::unconfigureDevice(void) { 00405 SIEunconfigureDevice(); 00406 } 00407 00408 void USBHAL::setAddress(uint8_t address) { 00409 SIEsetAddress(address); 00410 } 00411 00412 void USBHAL::EP0setup(uint8_t *buffer) { 00413 endpointReadcore(EP0OUT, buffer); 00414 } 00415 00416 void USBHAL::EP0read(void) { 00417 // Not required 00418 } 00419 00420 uint32_t USBHAL::EP0getReadResult(uint8_t *buffer) { 00421 return endpointReadcore(EP0OUT, buffer); 00422 } 00423 00424 void USBHAL::EP0write(uint8_t *buffer, uint32_t size) { 00425 endpointWritecore(EP0IN, buffer, size); 00426 } 00427 00428 void USBHAL::EP0getWriteResult(void) { 00429 // Not required 00430 } 00431 00432 void USBHAL::EP0stall(void) { 00433 // This will stall both control endpoints 00434 stallEndpoint(EP0OUT); 00435 } 00436 00437 EP_STATUS USBHAL::endpointRead(uint8_t endpoint, uint32_t maximumSize) { 00438 return EP_PENDING; 00439 } 00440 00441 EP_STATUS USBHAL::endpointReadResult(uint8_t endpoint, uint8_t * buffer, uint32_t *bytesRead) { 00442 00443 //for isochronous endpoint, we don't wait an interrupt 00444 if ((endpoint >> 1) % 3 || (endpoint >> 1) == 0) { 00445 if (!(epComplete & EP(endpoint))) 00446 return EP_PENDING; 00447 } 00448 00449 *bytesRead = endpointReadcore(endpoint, buffer); 00450 epComplete &= ~EP(endpoint); 00451 return EP_COMPLETED; 00452 } 00453 00454 EP_STATUS USBHAL::endpointWrite(uint8_t endpoint, uint8_t *data, uint32_t size) { 00455 if (getEndpointStallState(endpoint)) { 00456 return EP_STALLED; 00457 } 00458 00459 epComplete &= ~EP(endpoint); 00460 00461 endpointWritecore(endpoint, data, size); 00462 return EP_PENDING; 00463 } 00464 00465 EP_STATUS USBHAL::endpointWriteResult(uint8_t endpoint) { 00466 if (epComplete & EP(endpoint)) { 00467 epComplete &= ~EP(endpoint); 00468 return EP_COMPLETED; 00469 } 00470 00471 return EP_PENDING; 00472 } 00473 00474 bool USBHAL::realiseEndpoint(uint8_t endpoint, uint32_t maxPacket, uint32_t flags) { 00475 // Realise an endpoint 00476 LPC_USB->USBDevIntClr = EP_RLZED; 00477 LPC_USB->USBReEp |= EP(endpoint); 00478 LPC_USB->USBEpInd = endpoint; 00479 LPC_USB->USBMaxPSize = maxPacket; 00480 00481 while (!(LPC_USB->USBDevIntSt & EP_RLZED)); 00482 LPC_USB->USBDevIntClr = EP_RLZED; 00483 00484 // Clear stall state 00485 endpointStallState &= ~EP(endpoint); 00486 00487 enableEndpointEvent(endpoint); 00488 return true; 00489 } 00490 00491 void USBHAL::stallEndpoint(uint8_t endpoint) { 00492 // Stall an endpoint 00493 if ( (endpoint==EP0IN) || (endpoint==EP0OUT) ) { 00494 // Conditionally stall both control endpoints 00495 SIEsetEndpointStatus(EP0OUT, SIE_SES_CND_ST); 00496 } else { 00497 SIEsetEndpointStatus(endpoint, SIE_SES_ST); 00498 00499 // Update stall state 00500 endpointStallState |= EP(endpoint); 00501 } 00502 } 00503 00504 void USBHAL::unstallEndpoint(uint8_t endpoint) { 00505 // Unstall an endpoint. The endpoint will also be reinitialised 00506 SIEsetEndpointStatus(endpoint, 0); 00507 00508 // Update stall state 00509 endpointStallState &= ~EP(endpoint); 00510 } 00511 00512 bool USBHAL::getEndpointStallState(uint8_t endpoint) { 00513 // Returns true if endpoint stalled 00514 return endpointStallState & EP(endpoint); 00515 } 00516 00517 void USBHAL::remoteWakeup(void) { 00518 // Remote wakeup 00519 uint8_t status; 00520 00521 // Enable USB clocks 00522 LPC_USB->USBClkCtrl |= DEV_CLK_EN | AHB_CLK_EN; 00523 while (LPC_USB->USBClkSt != (DEV_CLK_ON | AHB_CLK_ON)); 00524 00525 status = SIEgetDeviceStatus(); 00526 SIEsetDeviceStatus(status & ~SIE_DS_SUS); 00527 } 00528 00529 00530 00531 00532 00533 void USBHAL::_usbisr(void) { 00534 instance->usbisr(); 00535 } 00536 00537 00538 void USBHAL::usbisr(void) { 00539 uint8_t devStat; 00540 00541 if (LPC_USB->USBDevIntSt & FRAME) { 00542 // Start of frame event 00543 SOF(SIEgetFrameNumber()); 00544 // Clear interrupt status flag 00545 LPC_USB->USBDevIntClr = FRAME; 00546 } 00547 00548 if (LPC_USB->USBDevIntSt & DEV_STAT) { 00549 // Device Status interrupt 00550 // Must clear the interrupt status flag before reading the device status from the SIE 00551 LPC_USB->USBDevIntClr = DEV_STAT; 00552 00553 // Read device status from SIE 00554 devStat = SIEgetDeviceStatus(); 00555 //printf("devStat: %d\r\n", devStat); 00556 00557 if (devStat & SIE_DS_SUS_CH) { 00558 // Suspend status changed 00559 if((devStat & SIE_DS_SUS) != 0) { 00560 suspendStateChanged(0); 00561 } 00562 } 00563 00564 if (devStat & SIE_DS_RST) { 00565 // Bus reset 00566 if((devStat & SIE_DS_SUS) == 0) { 00567 suspendStateChanged(1); 00568 } 00569 busReset(); 00570 } 00571 } 00572 00573 if (LPC_USB->USBDevIntSt & EP_SLOW) { 00574 // (Slow) Endpoint Interrupt 00575 00576 // Process each endpoint interrupt 00577 if (LPC_USB->USBEpIntSt & EP(EP0OUT)) { 00578 if (selectEndpointClearInterrupt(EP0OUT) & SIE_SE_STP) { 00579 // this is a setup packet 00580 EP0setupCallback(); 00581 } else { 00582 EP0out(); 00583 } 00584 LPC_USB->USBDevIntClr = EP_SLOW; 00585 } 00586 00587 if (LPC_USB->USBEpIntSt & EP(EP0IN)) { 00588 selectEndpointClearInterrupt(EP0IN); 00589 LPC_USB->USBDevIntClr = EP_SLOW; 00590 EP0in(); 00591 } 00592 00593 // TODO: This should cover all endpoints, not just EP1,2,3: 00594 if (LPC_USB->USBEpIntSt & EP(EP1IN)) { 00595 selectEndpointClearInterrupt(EP1IN); 00596 epComplete |= EP(EP1IN); 00597 LPC_USB->USBDevIntClr = EP_SLOW; 00598 if (EP1_IN_callback()) 00599 epComplete &= ~EP(EP1IN); 00600 } 00601 00602 if (LPC_USB->USBEpIntSt & EP(EP1OUT)) { 00603 selectEndpointClearInterrupt(EP1OUT); 00604 epComplete |= EP(EP1OUT); 00605 LPC_USB->USBDevIntClr = EP_SLOW; 00606 if (EP1_OUT_callback()) 00607 epComplete &= ~EP(EP1OUT); 00608 } 00609 00610 if (LPC_USB->USBEpIntSt & EP(EP2IN)) { 00611 selectEndpointClearInterrupt(EP2IN); 00612 epComplete |= EP(EP2IN); 00613 LPC_USB->USBDevIntClr = EP_SLOW; 00614 if (EP2_IN_callback()) 00615 epComplete &= ~EP(EP2IN); 00616 } 00617 00618 if (LPC_USB->USBEpIntSt & EP(EP2OUT)) { 00619 selectEndpointClearInterrupt(EP2OUT); 00620 epComplete |= EP(EP2OUT); 00621 LPC_USB->USBDevIntClr = EP_SLOW; 00622 if (EP2_OUT_callback()) 00623 epComplete &= ~EP(EP2OUT); 00624 } 00625 00626 if (LPC_USB->USBEpIntSt & EP(EP3IN)) { 00627 selectEndpointClearInterrupt(EP3IN); 00628 epComplete |= EP(EP3IN); 00629 LPC_USB->USBDevIntClr = EP_SLOW; 00630 if (EP3_IN_callback()) 00631 epComplete &= ~EP(EP3IN); 00632 } 00633 00634 if (LPC_USB->USBEpIntSt & EP(EP3OUT)) { 00635 selectEndpointClearInterrupt(EP3OUT); 00636 epComplete |= EP(EP3OUT); 00637 LPC_USB->USBDevIntClr = EP_SLOW; 00638 if (EP3_OUT_callback()) 00639 epComplete &= ~EP(EP3OUT); 00640 } 00641 } 00642 } 00643 00644 #endif
Generated on Wed Jul 13 2022 03:25:45 by
1.7.2
