/** Local function to handle incoming bulk data @param [in] bEP @param [in] bEPStatus */ static void BulkOut(U8 bEP, U8 bEPStatus) { int i, iLen; int result = 0; result = _fifo_free(&rxfifo); if (result < MAX_PACKET_SIZE) { return; } // get data from USB into intermediate buffer iLen = USBHwEPRead(bEP, abBulkBuf, sizeof(abBulkBuf)); for (i = 0; i < iLen; i++) { // put into FIFO if (!_fifo_put(&rxfifo, abBulkBuf[i])) { // overflow... :( ASSERT(FALSE); break; } } }
/************************************************************************* HandleDataOut ============= Handles data from host-to-device **************************************************************************/ static void HandleDataOut(void) { int iChunk; if (dwOffset < dwTransferSize) { // get data from host iChunk = USBHwEPRead(MSC_BULK_OUT_EP, pbData, dwTransferSize - dwOffset); // process data in SCSI layer pbData = SCSIHandleData(CBW.CBWCB, CBW.bCBWCBLength, pbData, dwOffset); if (pbData == NULL) { BOTStall(); SendCSW(STATUS_FAILED); return; } dwOffset += iChunk; } // are we done now? if (dwOffset == dwTransferSize) { if (dwOffset != CBW.dwCBWDataTransferLength) { // stall pipe DBG("stalling DOUT"); BOTStall(); } SendCSW(STATUS_PASSED); } }
/** Local function to handle incoming bulk data @param [in] bEP @param [in] bEPStatus */ static void BulkOut(U8 bEP, U8 bEPStatus) { int i, iLen; uint8_t tmpc; if (_fifo_free(&rxfifo) < MAX_PACKET_SIZE) { // may not fit into fifo return; } // get data from USB into intermediate buffer iLen = USBHwEPRead(bEP, abBulkBuf, sizeof(abBulkBuf)); for (i = 0; i < iLen; i++) { // put into FIFO if (!_fifo_put(&rxfifo, abBulkBuf[i])) { // overflow... :( ASSERT(FALSE); break; } tmpc = abBulkBuf[i]; UART_LINE[UART_LINE_LEN++]=tmpc; if((tmpc=='\r')||(tmpc=='\n')){ LINE_READY = 1; UART_LINE[UART_LINE_LEN-1]='\0'; UART_LINE_LEN=0; } // xprintf(INFO "abBulkBuf[i]=%c,tmpc=%c,UART_LINE=%s",abBulkBuf[i],tmpc,UART_LINE);FFL_(); } }
void USBSerialStream::BulkOut(U8 bEP, U8 bEPStatus) { int i, iLen; iLen = USBHwEPRead(bEP, dataBuf, sizeof(dataBuf)); instance()->m_outfifo.push(dataBuf, iLen); }
/* Local function to handle incoming bulk data @param [in] bEP @param [in] bEPStatus */ void BulkOut(uint8_t bEP, uint8_t bEPStatus) { int i; /* disable_USB_interrupts(); */ for(i=0;i<=USB_BUFFER_SIZE-1;i++) { usbReceiveBuffer[i] = 0; } USBHwEPRead(bEP, usbReceiveBuffer, sizeof(usbReceiveBuffer)); usbReceiveBufferSize = usbReceiveBuffer[0]<<8 | usbReceiveBuffer[1]; usbReceiveBufferSize = usbReceiveBufferSize - 1; }
/** Local function to handle incoming bulk data @param [in] bEP @param [in] bEPStatus */ static void BulkOut(unsigned char bEP, unsigned char bEPStatus) { int i, iLen; long lHigherPriorityTaskWoken = pdFALSE; ( void ) bEPStatus; // get data from USB into intermediate buffer iLen = USBHwEPRead(bEP, abBulkBuf, sizeof(abBulkBuf)); for (i = 0; i < iLen; i++) { // put into queue xQueueSendFromISR( xRxedChars, &( abBulkBuf[ i ] ), &lHigherPriorityTaskWoken ); } portEND_SWITCHING_ISR( lHigherPriorityTaskWoken ); }
/** Local function to handle incoming bulk data @param [in] bEP @param [in] bEPStatus */ static void BulkOut(uint8_t bEP, uint8_t bEPStatus) { int i, iLen; // if (fifo_free(&rxfifo) < MAX_PACKET_SIZE) { // may not fit into fifo // return; // } // get data from USB into intermediate buffer iLen = USBHwEPRead(bEP, abBulkBuf, sizeof(abBulkBuf)); for (i = 0; i < iLen; i++) { // put into FIFO // if (!fifo_put(&rxfifo, abBulkBuf[i])) { // overflow... :( // ASSERT(FALSE); // break; // } } }
/** Local function to handle incoming bulk data @param [in] bEP @param [in] bEPStatus */ static void BulkOut(U8 bEP, U8 bEPStatus __attribute__((unused))) { int i, iLen; if (fifo_free(&rxfifo) < MAX_PACKET_SIZE) { // may not fit into fifo BulkOut_is_blocked = true; return; } // get data from USB into intermediate buffer iLen = USBHwEPRead(bEP, abBulkBuf, sizeof(abBulkBuf)); for (i = 0; i < iLen; i++) { // put into FIFO if (!fifo_put(&rxfifo, abBulkBuf[i])) { // overflow... :( ASSERT(FALSE); break; } } }
/** Local function to handle incoming bulk data @param [in] bEP @param [in] bEPStatus */ static void BulkOut(U8 bEP, U8 bEPStatus) { int i, iLen; int j = 0; //DBG ("\nBulk Out...\n"); DBG ("\nBo\n"); if( !(bEPStatus & EP_STATUS_DATA) ) { return; } if (fifo_free(&bulk_txfifo) <= MAX_PACKET_SIZE_BULK) { // may not fit into fifo return; } // get data from USB into intermediate buffer (bulk_rxfifo) iLen = USBHwEPRead(bEP, bulkBuf, sizeof(bulkBuf)); DBG("l=%d", iLen); for (i = 0; i < iLen; i++) { // put into FIFO /* if (!fifo_put(&bulk_rxfifo, bulkBuf[i])) { */ /* // overflow... :( */ /* ASSERT(FALSE); */ /* break; */ /* } */ // copy rxfifo to txfifo? seems right for echo case... if (!fifo_put(&bulk_txfifo, bulkBuf[i])) { // overflow... :( ASSERT(FALSE); break; } else { //DBG("%c",bulkBuf[i]); } } SendNextBulkIn(BULK_IN_EP, 0); }
/** Handles the BOT bulk OUT endpoint @param [in] bEP Endpoint number @param [in] bEPStatus Endpoint status (indicates NAK, STALL, etc) */ void MSCBotBulkOut(U8 bEP, U8 bEPStatus) { int iLen, iChunk; BOOL fHostIn, fDevIn; // ignore events on stalled EP if (bEPStatus & EP_STATUS_STALLED) { return; } switch (eState) { case eCBW: iLen = USBHwEPRead(bEP, (U8 *)&CBW, sizeof(CBW)); // check if we got a good CBW if (!CheckCBW(&CBW, iLen)) { // see 6.6.1 USBHwEPStall(MSC_BULK_IN_EP, TRUE); USBHwEPStall(MSC_BULK_OUT_EP, TRUE); eState = eStalled; break; } DBG("CBW: len=%d, flags=%x, cmd=%x, cmdlen=%d\n", CBW.dwCBWDataTransferLength, CBW.bmCBWFlags, CBW.CBWCB[0], CBW.bCBWCBLength); dwOffset = 0; dwTransferSize = 0; fHostIn = ((CBW.bmCBWFlags & 0x80) != 0); // verify request pbData = SCSIHandleCmd(CBW.CBWCB, CBW.bCBWCBLength, &iLen, &fDevIn); if (pbData == NULL) { // unknown command BOTStall(); SendCSW(STATUS_FAILED); break; } // rule: if device and host disagree on direction, send CSW with status 2 if ((iLen > 0) && ((fHostIn && !fDevIn) || (!fHostIn && fDevIn))) { DBG("Host and device disagree on direction\n"); BOTStall(); SendCSW(STATUS_PHASE_ERR); break; } // rule: if D > H, send CSW with status 2 if (iLen > CBW.dwCBWDataTransferLength) { DBG("Negative residue\n"); BOTStall(); SendCSW(STATUS_PHASE_ERR); break; } dwTransferSize = iLen; if ((dwTransferSize == 0) || fDevIn) { // data from device-to-host eState = eDataIn; HandleDataIn(); } else { // data from host-to-device eState = eDataOut; } break; case eDataOut: HandleDataOut(); break; case eDataIn: case eCSW: iChunk = USBHwEPRead(bEP, NULL, 0); DBG("Phase error in state %d, %d bytes\n", eState, iChunk); eState = eCBW; break; case eStalled: // keep stalling USBHwEPStall(MSC_BULK_OUT_EP, TRUE); break; default: DBG("Invalid state %d\n", eState); ASSERT(FALSE); break; } }
/** * Handles IN/OUT transfers on EP0 * * @param [in] bEP Endpoint address * @param [in] bEPStat Endpoint status */ void USBHandleControlTransfer(U8 bEP, U8 bEPStat) { int iChunk, iType; if (bEP == 0x00) { // OUT transfer if (bEPStat & EP_STATUS_SETUP) { // setup packet, reset request message state machine USBHwEPRead(0x00, (U8 *)&Setup, sizeof(Setup)); DBG("S%x", Setup.bRequest); // defaults for data pointer and residue iType = REQTYPE_GET_TYPE(Setup.bmRequestType); pbData = apbDataStore[iType]; iResidue = Setup.wLength; iLen = Setup.wLength; if ((Setup.wLength == 0) || (REQTYPE_GET_DIR(Setup.bmRequestType) == REQTYPE_DIR_TO_HOST)) { // ask installed handler to process request if (!_HandleRequest(&Setup, &iLen, &pbData)) { DBG("_HandleRequest1 failed\n"); StallControlPipe(bEPStat); return; } // send smallest of requested and offered length iResidue = MIN(iLen, Setup.wLength); // send first part (possibly a zero-length status message) DataIn(); } } else { if (iResidue > 0) { // store data iChunk = USBHwEPRead(0x00, pbData, iResidue); if (iChunk < 0) { StallControlPipe(bEPStat); return; } pbData += iChunk; iResidue -= iChunk; if (iResidue == 0) { // received all, send data to handler iType = REQTYPE_GET_TYPE(Setup.bmRequestType); pbData = apbDataStore[iType]; if (!_HandleRequest(&Setup, &iLen, &pbData)) { DBG("_HandleRequest2 failed\n"); StallControlPipe(bEPStat); return; } // send status to host DataIn(); } } else { // absorb zero-length status message iChunk = USBHwEPRead(0x00, NULL, 0); DBG(iChunk > 0 ? "?" : ""); } } } else if (bEP == 0x80) { // IN transfer // send more data if available (possibly a 0-length packet) DataIn(); } else { ASSERT(FALSE); } }
/************************************************************************* USBHandleControlTransfer ======================== Handles IN/OUT transfers on EP0 **************************************************************************/ void USBHandleControlTransfer(U8 bEP, U8 bEPStat) { int iChunk; if (bEP == 0x00) { // OUT transfer if (bEPStat & EP_STATUS_SETUP) { // setup packet, reset request message state machine USBHwEPRead(0x00, (U8 *)&Setup, &iLen); //mmmm DBG("S%x", Setup.bRequest); // defaults for data pointer and residue pbData = abControlData; iResidue = Setup.wLength; iLen = Setup.wLength; // ask installed handler to pre process request if (!_PreHandleRequest(&Setup, &iLen, &pbData)) { // silently ignore non installed handler } if ((Setup.wLength == 0) || (REQTYPE_GET_DIR(Setup.bmRequestType) == REQTYPE_DIR_TO_HOST)) { // ask installed handler to process request if (!_HandleRequest(&Setup, &iLen, &pbData)) { DBG("_HandleRequest1 failed\n"); StallControlPipe(bEPStat); return; } // send smallest of requested and offered length iResidue = MIN(iLen, Setup.wLength); // send first part (possibly a zero-length status message) DataIn(); } if ((Setup.wLength != 0) && (REQTYPE_GET_DIR(Setup.bmRequestType) == REQTYPE_DIR_TO_DEVICE)) { if (!_PreHandleRequest(&Setup, &iLen, &pbData)) { // this is not a must, might fail } } } else { if (iResidue > 0) { // store data iChunk = 0; USBHwEPRead(0x00, pbData, &iChunk); pbData += iChunk; iResidue -= iChunk; if (iResidue == 0) { // received all, send data to handler // TODO set pointer correctly pbData = abControlData; if (!_HandleRequest(&Setup, &iLen, &pbData)) { StallControlPipe(bEPStat); DBG("_HandleRequest2 failed\n"); return; } // send status to host DataIn(); } } else { // absorb zero-length status message USBHwEPRead(0x00, NULL, &iChunk); DBG(iChunk > 0 ? "?" : ""); } } } else if (bEP == 0x80) { // IN transfer // send more data if available (possibly a 0-length packet) DataIn(); } else { ASSERT(FALSE); } }