static void SideShow_GetApplicationOrder(SideShow_PacketHeader_t* const PacketHeader) { uint8_t TotalApplications = 0; Endpoint_ClearOUT(); for (uint8_t App = 0; App < MAX_APPLICATIONS; App++) { if (InstalledApplications[App].InUse) TotalApplications++; } PacketHeader->Length = sizeof(SideShow_PacketHeader_t) + sizeof(uint32_t) + (TotalApplications * sizeof(GUID_t)); Endpoint_SelectEndpoint(SIDESHOW_IN_EPNUM); Endpoint_Write_Stream_LE(PacketHeader, sizeof(SideShow_PacketHeader_t), NULL); Endpoint_Write_32_LE(TotalApplications); for (uint8_t App = 0; App < MAX_APPLICATIONS; App++) { if (InstalledApplications[App].InUse) Endpoint_Write_Stream_LE(&InstalledApplications[App].ApplicationID, sizeof(GUID_t), NULL); } Endpoint_ClearIN(); }
/** Command processing for an issued SCSI MODE SENSE (6) command. This command returns various informational pages about * the SCSI device, as well as the device's Write Protect status. * * \param[in] MSInterfaceInfo Pointer to the Mass Storage class interface structure that the command is associated with * * \return Boolean \c true if the command completed successfully, \c false otherwise. */ static bool SCSI_Command_ModeSense_6(USB_ClassInfo_MS_Device_t* const MSInterfaceInfo) { /* Send an empty header response indicating Write Protect flag is off */ Endpoint_Write_32_LE(0); Endpoint_ClearIN(); /* Update the bytes transferred counter and succeed the command */ MSInterfaceInfo->State.CommandBlock.DataTransferLength -= 4; return true; }
/** Event handler for the USB_ControlRequest event. This is used to catch and process control requests sent to * the device from the USB host before passing along unhandled control requests to the library for processing * internally. */ void EVENT_USB_Device_ControlRequest(void) { uint8_t TMCRequestStatus = TMC_STATUS_SUCCESS; /* Process TMC specific control requests */ switch (USB_ControlRequest.bRequest) { case Req_InitiateAbortBulkOut: if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_ENDPOINT)) { /* Check that no split transaction is already in progress and the data transfer tag is valid */ if (RequestInProgress != 0) { TMCRequestStatus = TMC_STATUS_SPLIT_IN_PROGRESS; } else if (USB_ControlRequest.wValue != CurrentTransferTag) { TMCRequestStatus = TMC_STATUS_TRANSFER_NOT_IN_PROGRESS; } else { /* Indicate that all in-progress/pending data OUT requests should be aborted */ IsTMCBulkOUTReset = true; /* Save the split request for later checking when a new request is received */ RequestInProgress = Req_InitiateAbortBulkOut; } Endpoint_ClearSETUP(); /* Write the request response byte */ Endpoint_Write_8(TMCRequestStatus); Endpoint_ClearIN(); Endpoint_ClearStatusStage(); } break; case Req_CheckAbortBulkOutStatus: if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_ENDPOINT)) { /* Check that an ABORT BULK OUT transaction has been requested and that the request has completed */ if (RequestInProgress != Req_InitiateAbortBulkOut) TMCRequestStatus = TMC_STATUS_SPLIT_NOT_IN_PROGRESS; else if (IsTMCBulkOUTReset) TMCRequestStatus = TMC_STATUS_PENDING; else RequestInProgress = 0; Endpoint_ClearSETUP(); /* Write the request response bytes */ Endpoint_Write_8(TMCRequestStatus); Endpoint_Write_16_LE(0); Endpoint_Write_32_LE(LastTransferLength); Endpoint_ClearIN(); Endpoint_ClearStatusStage(); } break; case Req_InitiateAbortBulkIn: if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_ENDPOINT)) { /* Check that no split transaction is already in progress and the data transfer tag is valid */ if (RequestInProgress != 0) { TMCRequestStatus = TMC_STATUS_SPLIT_IN_PROGRESS; } else if (USB_ControlRequest.wValue != CurrentTransferTag) { TMCRequestStatus = TMC_STATUS_TRANSFER_NOT_IN_PROGRESS; } else { /* Indicate that all in-progress/pending data IN requests should be aborted */ IsTMCBulkINReset = true; /* Save the split request for later checking when a new request is received */ RequestInProgress = Req_InitiateAbortBulkIn; } Endpoint_ClearSETUP(); /* Write the request response bytes */ Endpoint_Write_8(TMCRequestStatus); Endpoint_Write_8(CurrentTransferTag); Endpoint_ClearIN(); Endpoint_ClearStatusStage(); } break; case Req_CheckAbortBulkInStatus: if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_ENDPOINT)) { /* Check that an ABORT BULK IN transaction has been requested and that the request has completed */ if (RequestInProgress != Req_InitiateAbortBulkIn) TMCRequestStatus = TMC_STATUS_SPLIT_NOT_IN_PROGRESS; else if (IsTMCBulkINReset) TMCRequestStatus = TMC_STATUS_PENDING; else RequestInProgress = 0; Endpoint_ClearSETUP(); /* Write the request response bytes */ Endpoint_Write_8(TMCRequestStatus); Endpoint_Write_16_LE(0); Endpoint_Write_32_LE(LastTransferLength); Endpoint_ClearIN(); Endpoint_ClearStatusStage(); } break; case Req_InitiateClear: if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE)) { /* Check that no split transaction is already in progress */ if (RequestInProgress != 0) { Endpoint_Write_8(TMC_STATUS_SPLIT_IN_PROGRESS); } else { /* Indicate that all in-progress/pending data IN and OUT requests should be aborted */ IsTMCBulkINReset = true; IsTMCBulkOUTReset = true; /* Save the split request for later checking when a new request is received */ RequestInProgress = Req_InitiateClear; } Endpoint_ClearSETUP(); /* Write the request response byte */ Endpoint_Write_8(TMCRequestStatus); Endpoint_ClearIN(); Endpoint_ClearStatusStage(); } break; case Req_CheckClearStatus: if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE)) { /* Check that a CLEAR transaction has been requested and that the request has completed */ if (RequestInProgress != Req_InitiateClear) TMCRequestStatus = TMC_STATUS_SPLIT_NOT_IN_PROGRESS; else if (IsTMCBulkINReset || IsTMCBulkOUTReset) TMCRequestStatus = TMC_STATUS_PENDING; else RequestInProgress = 0; Endpoint_ClearSETUP(); /* Write the request response bytes */ Endpoint_Write_8(TMCRequestStatus); Endpoint_Write_8(0); Endpoint_ClearIN(); Endpoint_ClearStatusStage(); } break; case Req_GetCapabilities: if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE)) { Endpoint_ClearSETUP(); /* Write the device capabilities to the control endpoint */ Endpoint_Write_Control_Stream_LE(&Capabilities, sizeof(TMC_Capabilities_t)); Endpoint_ClearOUT(); } break; } }
void CDC_Device_ProcessControlRequest(USB_ClassInfo_CDC_Device_t* const CDCInterfaceInfo) { if (!(Endpoint_IsSETUPReceived())) return; if (USB_ControlRequest.wIndex != CDCInterfaceInfo->Config.ControlInterfaceNumber) return; switch (USB_ControlRequest.bRequest) { case CDC_REQ_GetLineEncoding: if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE)) { Endpoint_ClearSETUP(); while (!(Endpoint_IsINReady())); Endpoint_Write_32_LE(CDCInterfaceInfo->State.LineEncoding.BaudRateBPS); Endpoint_Write_8(CDCInterfaceInfo->State.LineEncoding.CharFormat); Endpoint_Write_8(CDCInterfaceInfo->State.LineEncoding.ParityType); Endpoint_Write_8(CDCInterfaceInfo->State.LineEncoding.DataBits); Endpoint_ClearIN(); Endpoint_ClearStatusStage(); } break; case CDC_REQ_SetLineEncoding: if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE)) { Endpoint_ClearSETUP(); while (!(Endpoint_IsOUTReceived())) { if (USB_DeviceState == DEVICE_STATE_Unattached) return; } CDCInterfaceInfo->State.LineEncoding.BaudRateBPS = Endpoint_Read_32_LE(); CDCInterfaceInfo->State.LineEncoding.CharFormat = Endpoint_Read_8(); CDCInterfaceInfo->State.LineEncoding.ParityType = Endpoint_Read_8(); CDCInterfaceInfo->State.LineEncoding.DataBits = Endpoint_Read_8(); Endpoint_ClearOUT(); Endpoint_ClearStatusStage(); EVENT_CDC_Device_LineEncodingChanged(CDCInterfaceInfo); } break; case CDC_REQ_SetControlLineState: if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE)) { Endpoint_ClearSETUP(); Endpoint_ClearStatusStage(); CDCInterfaceInfo->State.ControlLineStates.HostToDevice = USB_ControlRequest.wValue; EVENT_CDC_Device_ControLineStateChanged(CDCInterfaceInfo); } break; case CDC_REQ_SendBreak: if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE)) { Endpoint_ClearSETUP(); Endpoint_ClearStatusStage(); EVENT_CDC_Device_BreakSent(CDCInterfaceInfo, (uint8_t)USB_ControlRequest.wValue); } break; } }