//***************************************************************************** // // This function is called by the USB device stack whenever a request for a // non-standard descriptor is received. // // \param pvDFUInstance is the instance data for this request. // \param psUSBRequest points to the request received. // // This call parses the provided request structure and determines which // descriptor is being requested. Assuming the descriptor can be found, it is // scheduled for transmission via endpoint zero. If the descriptor cannot be // found, the endpoint is stalled to indicate an error to the host. // //***************************************************************************** static void HandleGetDescriptor(void *pvDFUInstance, tUSBRequest *psUSBRequest) { uint32_t ui32Size; ASSERT(pvDFUInstance != 0); // // Which type of class descriptor are we being asked for? We only support // 1 type - the DFU functional descriptor. // if(((readusb16_t(&(psUSBRequest->wValue)) >> 8) == USB_DFU_FUNC_DESCRIPTOR_TYPE) && ((readusb16_t(&(psUSBRequest->wValue)) & 0xFF) == 0)) { // // If there is more data to send than the host requested then just // send the requested amount of data. // if((uint16_t)g_pui8DFUFunctionalDesc[0] > readusb16_t(&(psUSBRequest->wLength))) { ui32Size = (uint32_t)readusb16_t(&(psUSBRequest->wLength)); } else { ui32Size = (uint32_t)g_pui8DFUFunctionalDesc[0]; } // // Send the data via endpoint 0. // USBDCDSendDataEP0(0, g_pui8DFUFunctionalDesc, ui32Size); } else {
//***************************************************************************** // // This function is called by the USB device stack whenever a request for a // non-standard descriptor is received. // // \param pvInstance is the instance data for this request. // \param pUSBRequest points to the request received. // // This call parses the provided request structure and determines which // descriptor is being requested. Assuming the descriptor can be found, it is // scheduled for transmission via endpoint zero. If the descriptor cannot be // found, the endpoint is stalled to indicate an error to the host. // //***************************************************************************** static void HandleGetDescriptor(void *pvInstance, tUSBRequest *pUSBRequest) { unsigned long ulSize; ASSERT(pvInstance != 0); // // Which type of class descriptor are we being asked for? We only support // 1 type - the DFU functional descriptor. // if(((pUSBRequest->wValue >> 8) == USB_DFU_FUNC_DESCRIPTOR_TYPE) && ((pUSBRequest->wValue & 0xFF) == 0)) { // // If there is more data to send than the host requested then just // send the requested amount of data. // if((unsigned short)g_pDFUFunctionalDesc[0] > pUSBRequest->wLength) { ulSize = (unsigned long)pUSBRequest->wLength; } else { ulSize = (unsigned long)g_pDFUFunctionalDesc[0]; } // // Send the data via endpoint 0. // USBDCDSendDataEP0(0, g_pDFUFunctionalDesc, ulSize); } else {
//***************************************************************************** // // Get the communication parameters in use on the UART. // //***************************************************************************** static void GetLineCoding(tLineCoding *psLineCoding) { // // Always report 115,200, 8-N-1. // psLineCoding->ulRate = 115200; psLineCoding->ucDatabits = 8; psLineCoding->ucParity = USB_CDC_PARITY_NONE; psLineCoding->ucStop = USB_CDC_STOP_BITS_1; // // Send the information back to the host. // USBDCDSendDataEP0(0, (unsigned char *)psLineCoding, sizeof(tLineCoding)); }
//***************************************************************************** // // This function is called by the USB device stack whenever a request for a // non-standard descriptor is received. // // \param pvInstance is the instance data for this request. // \param pUSBRequest points to the request received. // // This call parses the provided request structure and determines which // descriptor is being requested. Assuming the descriptor can be found, it is // scheduled for transmission via endpoint zero. If the descriptor cannot be // found, the endpoint is stalled to indicate an error to the host. // //***************************************************************************** static void HandleGetDescriptor(void *pvInstance, tUSBRequest *pUSBRequest) { unsigned long ulSize; const tUSBDDFUDevice *psDevice; tDFUInstance *psInst; ASSERT(pvInstance != 0); // // Which device are we dealing with? // psDevice = pvInstance; // // Get a pointer to our instance data. // psInst = psDevice->psPrivateDFUData; // // Which type of class descriptor are we being asked for? We only support // 1 type - the DFU functional descriptor. // if(((pUSBRequest->wValue >> 8) == USB_DFU_FUNC_DESCRIPTOR_TYPE) && ((pUSBRequest->wValue & 0xFF) == 0)) { // // If there is more data to send than the host requested then just // send the requested amount of data. // if((unsigned short)g_pDFUFunctionalDesc[0] > pUSBRequest->wLength) { ulSize = (unsigned long)pUSBRequest->wLength; } else { ulSize = (unsigned long)g_pDFUFunctionalDesc[0]; } // // Send the data via endpoint 0. // USBDCDSendDataEP0(USB_BASE_TO_INDEX(psInst->ulUSBBase), g_pDFUFunctionalDesc, ulSize); } else {
//***************************************************************************** // // This function is called by the USB device stack whenever a non-standard // request is received. // // \param pvAudioDevice is the instance data for this request. // \param psUSBRequest points to the request received. // // This call parses the provided request structure to the type of request and // will respond to all commands that are understood by the class. // // \return None. // //***************************************************************************** static void HandleRequests(void *pvAudioDevice, tUSBRequest *psUSBRequest) { uint32_t ui32Control, ui32Recipient, ui32Stall; tAudioInstance *psInst; tUSBDAudioDevice *psAudioDevice; ASSERT(pvAudioDevice != 0); // // The audio device structure pointer. // psAudioDevice = (tUSBDAudioDevice *)pvAudioDevice; // // Create a pointer to the audio instance data. // psInst = &psAudioDevice->sPrivateData; // // Make sure to acknowledge that the data was read, this will not send and // ACK that has already been done at this point. This just tells the // hardware that the data was read. // MAP_USBDevEndpointDataAck(USB0_BASE, USB_EP_0, false); // // Don't stall by default. // ui32Stall = 0; // // Get the request type. // ui32Recipient = psUSBRequest->bmRequestType & USB_RTYPE_RECIPIENT_M; // // Save the request type and request value. // psInst->ui16RequestType = psUSBRequest->bmRequestType; psInst->ui8Request = psUSBRequest->bRequest; // // Check if this is an endpoint request to the audio streaming endpoint. // if((ui32Recipient == USB_RTYPE_ENDPOINT) && (readusb16_t(&(psUSBRequest->wIndex)) == USBEPToIndex(psInst->ui8OUTEndpoint))) { // // Determine the type of request. // switch(psInst->ui8Request) { case USB_AC_SET_CUR: { // // Handle retrieving the sample rate. // if(readusb16_t(&(psUSBRequest->wValue)) == SAMPLING_FREQ_CONTROL) { // // Retrieve the requested sample rate. // USBDCDRequestDataEP0(0, (uint8_t *)&psInst->ui32SampleRate, 3); // // Save what we are updating. // psInst->ui16Update = SAMPLING_FREQ_CONTROL; } break; } case USB_AC_GET_CUR: { // // Handle retrieving the sample rate. // if(readusb16_t(&(psUSBRequest->wValue)) == SAMPLING_FREQ_CONTROL) { // // Send back the current sample rate. // USBDCDSendDataEP0(0, (uint8_t *)&psInst->ui32SampleRate, 3); } break; } default: { // // Stall on unknown commands. // ui32Stall = 1; break; } } } else if(ui32Recipient == USB_RTYPE_INTERFACE) { // // Make sure the request was for the control interface. // if((uint8_t)readusb16_t(&(psUSBRequest->wIndex)) != psInst->ui8InterfaceControl) { return; } // // Extract the control value from the message. // ui32Control = readusb16_t(&(psUSBRequest->wValue)) & USB_CS_CONTROL_M; // // Handle an audio control request to the feature control unit. // if(((uint32_t)AUDIO_CONTROL_ID << 8) == (readusb16_t(&(psUSBRequest->wIndex)) & USB_CS_CONTROL_M)) { // // Determine the type of request. // switch(psInst->ui8Request) { case USB_AC_GET_MAX: { if(ui32Control == VOLUME_CONTROL) { // // Return the maximum volume setting. // USBDCDSendDataEP0(0, (uint8_t *)&psInst->i16VolumeMax, 2); } else { // // Stall on unknown commands. // ui32Stall = 1; } break; } case USB_AC_GET_MIN: { if(ui32Control == VOLUME_CONTROL) { // // Return the minimum volume setting. // USBDCDSendDataEP0(0, (uint8_t *)&psInst->i16VolumeMin, 2); } else { // // Stall on unknown commands. // ui32Stall = 1; } break; } case USB_AC_GET_RES: { if(ui32Control == VOLUME_CONTROL) { // // Return the volume step setting. // USBDCDSendDataEP0(0, (uint8_t *)&psInst->i16VolumeStep, 2); } else { // // Stall on unknown commands. // ui32Stall = 1; } break; } case USB_AC_GET_CUR: { if(ui32Control == VOLUME_CONTROL) { // // Send back the current volume level. // USBDCDSendDataEP0(0, (uint8_t *)&psInst->i16Volume, 2); } else if(ui32Control == MUTE_CONTROL) { // // Send back the current mute value. // USBDCDSendDataEP0(0, (uint8_t *)&psInst->ui8Mute, 1); } else { // // Stall on unknown commands. // ui32Stall = 1; } break; } case USB_AC_SET_CUR: { if(ui32Control == VOLUME_CONTROL) { // // Read the new volume level. // USBDCDRequestDataEP0(0, (uint8_t *)&psInst->i16Volume, 2); // // Save what we are updating. // psInst->ui16Update = VOLUME_CONTROL; } else if(ui32Control == MUTE_CONTROL) { // // Read the new mute setting. // USBDCDRequestDataEP0(0, (uint8_t *)&psInst->ui8Mute, 1); // // Save what we are updating. // psInst->ui16Update = MUTE_CONTROL; } else { // // Stall on unknown commands. // ui32Stall = 1; } break; } case USB_AC_SET_RES: { if(ui32Control == VOLUME_CONTROL) { // // Read the new volume step setting. // USBDCDRequestDataEP0(0, (uint8_t *)&psInst->i16VolumeStep, 2); // // Save what we are updating. // psInst->ui16Update = VOLUME_CONTROL; } else { // // Stall on unknown commands. // ui32Stall = 1; } break; } default: { // // Stall on unknown commands. // ui32Stall = 1; break; } } } } // // Stall on all unknown commands. // if(ui32Stall) { USBDCDStallEP0(0); } }