📄 usbehcdrhemulation.c
字号:
break; } case USBHST_RECIPIENT_INTERFACE: /* Interface recipient */ case USBHST_RECIPIENT_ENDPOINT: /* Endpoint recipient */ { /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } default: { /* Invalid recipient value */ pURB->nStatus = USBHST_INVALID_REQUEST; break; } } break; } case USBHST_REQ_GET_CONFIGURATION:/* Get Configuration request */ { /* * Update the URB transfer buffer with the current configuration * value for the root hub */ pURB->pTransferBuffer[0] = pHCDData->RHData.uConfigValue; /* Update the URB transfer length */ pURB->uTransferLength = USB_EHCD_RH_GET_CONFIG_SIZE; /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } case USBHST_REQ_GET_DESCRIPTOR:/* Get Descriptor request */ { /* Check the descriptor type */ switch (pSetup->wValue >> USB_EHCD_RH_DESCRIPTOR_BITPOSITION) { case USBHST_DEVICE_DESC: { /* Check the length of descriptor requested */ if (pSetup->wLength >= USB_EHCD_RH_DEVICE_DESC_SIZE) { /* Update the URB transfer length */ pURB->uTransferLength = USB_EHCD_RH_DEVICE_DESC_SIZE; } else { /* Update the URB transfer length */ pURB->uTransferLength = pSetup->wLength; } /* Copy the descriptor to the URB transfer buffer */ OS_MEMCPY(pURB->pTransferBuffer, gRHDeviceDescriptor, pURB->uTransferLength); /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } case USBHST_CONFIG_DESC: { /* Check the length of descriptor requested */ if (pSetup->wLength >= USB_EHCD_RH_CONFIG_DESC_SIZE) { /* Update the URB transfer length */ pURB->uTransferLength = USB_EHCD_RH_CONFIG_DESC_SIZE; } else { /* Update the URB transfer length */ pURB->uTransferLength = pSetup->wLength; } /* Copy the descriptor to the URB transfer buffer */ OS_MEMCPY(pURB->pTransferBuffer, gRHConfigDescriptor, pURB->uTransferLength); /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } default: { /* Invalid descriptor type */ pURB->nStatus = USBHST_INVALID_REQUEST; break; } } break; } case USBHST_REQ_GET_STATUS:/* Get Status request */ { /* Based on the recipient value, handle the request */ switch (pSetup->bmRequestType & USB_EHCD_RH_RECIPIENT_MASK) { case USBHST_RECIPIENT_DEVICE:/* Device recipient */ { /* Clear the URB transfer buffer */ OS_MEMSET(pURB->pTransferBuffer, 0, USB_EHCD_RH_GET_STATUS_SIZE); /* Update the device status - Self powered */ pURB->pTransferBuffer[0] = 0x01; /* If remote wakeup is enabled, update the status */ if (TRUE == pHCDData->RHData.bRemoteWakeupEnabled) { /* Remote wakeup is enabled */ pURB->pTransferBuffer[0] |= 0x02; } /* Update the URB transfer length */ pURB->uTransferLength = USB_EHCD_RH_GET_STATUS_SIZE; /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } case USBHST_RECIPIENT_INTERFACE: /* Interface recipient */ case USBHST_RECIPIENT_ENDPOINT: /* Endpoint recipient */ { /* Update the URB transfer buffer */ OS_MEMSET(pURB->pTransferBuffer, 0, USB_EHCD_RH_GET_STATUS_SIZE); /* Update the URB transfer length */ pURB->uTransferLength = USB_EHCD_RH_GET_STATUS_SIZE; /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } default : { /* Invalid recipient value */ pURB->nStatus = USBHST_INVALID_REQUEST; break; } } break; } case USBHST_REQ_SET_ADDRESS:/* Set Address request */ { /* Check whether the address is valid */ if (0 == pSetup->wValue) { /* Address is not valid */ pURB->nStatus = USBHST_INVALID_REQUEST; break; } /* Update the RH address */ pHCDData->RHData.uDeviceAddress = (UINT8)pSetup->wValue; /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } case USBHST_REQ_SET_CONFIGURATION:/* Set Configuration request */ { /* Check whether the configuration value is valid */ if ((0 != pSetup->wValue) && (1 != pSetup->wValue)) { /* Invalid configuration value. Update the URB status */ pURB->nStatus = USBHST_INVALID_REQUEST; break; } /* Update the current configuration value for the root hub */ pHCDData->RHData.uConfigValue = (UINT8)pSetup->wValue; /* * Enable the EHCI interrupts - this is done as only * after configuration of the Root hub any device other than * Root hub will be serviced. */ USB_EHCD_WRITE_REG(pHCDData, USB_EHCD_USBINTR, USB_EHCD_RH_CONFIG_INTERRUPT_MASK); /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } case USBHST_REQ_SET_FEATURE:/* Set feature request */ { /* Based on the recipient, handle the request */ switch (pSetup->bmRequestType & USB_EHCD_RH_RECIPIENT_MASK) { case USBHST_RECIPIENT_DEVICE: /* Device recipient */ { /* Check the feature selector */ if (USBHST_FEATURE_DEVICE_REMOTE_WAKEUP == pSetup->wValue) { /* Disable the device remote wakeup feature */ pHCDData->RHData.bRemoteWakeupEnabled = TRUE; } /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } case USBHST_RECIPIENT_INTERFACE: /* Interface recipient */ case USBHST_RECIPIENT_ENDPOINT: /* Endpoint recipient */ { /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } default: { /* Invalid recipient value */ pURB->nStatus = USBHST_INVALID_REQUEST; break; } } break; } default :/* Invalid request */ { pURB->nStatus = USBHST_INVALID_REQUEST; break; } }/* End of switch () */ /* If a callback function is registered, call the callback function */ if (NULL != pURB->pfCallback) { (pURB->pfCallback)(pURB); } OS_LOG_MESSAGE_LOW(EHCD,"usbEhcdRhProcessStandardRequest - Exit\n",0,0,0,0); return Status; } /* End of usbEhcdRhProcessStandardRequest() *//***************************************************************************** usbEhcdRhClearPortFeature - clears a feature of the port** This routine clears a feature of the port.** RETURNS: USBHST_SUCCESS- if the URB is submitted successfully.* USBHST_INVALID_PARAMETER- if the parameters are not valid.** ERRNO:* None.*/USBHST_STATUS usbEhcdRhClearPortFeature ( pUSB_EHCD_DATA pHCDData, /* Ptr to HCD block */ pUSBHST_URB pURB /* Ptr to User Request Block */ ) { /* To hold the request status */ USBHST_STATUS Status = USBHST_SUCCESS; /* Pointer to the setup packet */ pUSBHST_SETUP_PACKET pSetup = NULL; UINT32 uBusIndex = 0; /* index of the host controller */ OS_LOG_MESSAGE_LOW(EHCD,"usbEhcdRhClearPortFeature - Entry\n",0,0,0,0); /* Check the validity of the parameters */ if (NULL == pHCDData || NULL == pURB || NULL == pURB->pTransferSpecificData) { OS_LOG_MESSAGE_HIGH(EHCD,"usbEhcdRhClearPortFeature - \ Invalid parameters\n",0,0,0,0); pURB->nStatus = USBHST_INVALID_PARAMETER; return USBHST_INVALID_PARAMETER; } /* Extract the index of the host controller */ uBusIndex = pHCDData->uBusIndex; /* Extract the setup packet */ pSetup = (pUSBHST_SETUP_PACKET)pURB->pTransferSpecificData; /* Check whether the members are valid */ if (pSetup->wIndex > pHCDData->RHData.uNumDownstreamPorts) { OS_LOG_MESSAGE_HIGH(EHCD,"usbEhcdRhClearPortFeature - \ Invalid port index\n",0,0,0,0); pURB->nStatus = USBHST_INVALID_PARAMETER; return USBHST_INVALID_PARAMETER; } /* Handle the request based on the feature to be cleared */ switch(pSetup->wValue) { case USB_EHCD_RH_PORT_ENABLE:/* Port enable */ { /* Clear the enable bit */ USB_EHCD_CLR_BIT_PORT(pHCDData, (pSetup->wIndex) -1, PORT_ENABLED_DISABLED); /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; break; } case USB_EHCD_RH_PORT_SUSPEND:/* Port Suspend */ { /* To hold the status of the port */ UINT32 uPortStatus = 0; /* Drive port resume */ USB_EHCD_SET_BIT_PORT(pHCDData, ((pSetup->wIndex) -1), FORCE_PORT_RESUME); /* * The resume signal should be generated for atleast * 20ms. Additional 10 ms is for handling the * software delays. * Should be checked whether there is any performance issue * with this delay. */ OS_DELAY_MS(30); /* Stop port resume */ USB_EHCD_CLR_BIT_PORT(pHCDData, (pSetup->wIndex) -1, FORCE_PORT_RESUME); /* Update the URB status */ pURB->nStatus = USBHST_SUCCESS; /* Copy the value in the port status register */ OS_MEMCPY(&uPortStatus, (pHCDData->RHData.pPortStatus + (pSetup->wIndex -1)), USB_EHCD_RH_PORT_STATUS_SIZE); /* Swap the data to the LE format */ uPortStatus = USB_EHCD_SWAP_DATA(uBusIndex,uPortStatus);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -