Disconnect on SCSI eject command from host

USG_1.0
Robert Fisk 7 years ago
parent 190a601f85
commit e890e9df7a

@ -117,6 +117,10 @@
#define STANDARD_INQUIRY_DATA_LEN 0x24 #define STANDARD_INQUIRY_DATA_LEN 0x24
#define BLKVFY 0x04 #define BLKVFY 0x04
#define START_STOP_DATA_MASK 0x03
#define START_STOP_DATA_EJECT_STOP_MOTOR 0x02
extern uint8_t Page00_Inquiry_Data[]; extern uint8_t Page00_Inquiry_Data[];
extern uint8_t Standard_Inquiry_Data[]; extern uint8_t Standard_Inquiry_Data[];
extern uint8_t Standard_Inquiry_Data2[]; extern uint8_t Standard_Inquiry_Data2[];

@ -101,6 +101,7 @@ static void SCSI_ReadFormatCapacity(void);
static void SCSI_ReadCapacity10(void); static void SCSI_ReadCapacity10(void);
static void SCSI_RequestSense (void); static void SCSI_RequestSense (void);
static void SCSI_StartStopUnit(void); static void SCSI_StartStopUnit(void);
static void SCSI_AllowMediumRemoval(void);
static void SCSI_ModeSense6 (void); static void SCSI_ModeSense6 (void);
static void SCSI_ModeSense10 (void); static void SCSI_ModeSense10 (void);
static void SCSI_Write10(void); static void SCSI_Write10(void);
@ -171,7 +172,7 @@ void SCSI_ProcessCmd(USBD_HandleTypeDef *pdev,
return; return;
case SCSI_ALLOW_MEDIUM_REMOVAL: case SCSI_ALLOW_MEDIUM_REMOVAL:
SCSI_StartStopUnit(); SCSI_AllowMediumRemoval();
return; return;
case SCSI_MODE_SENSE6: case SCSI_MODE_SENSE6:
@ -546,10 +547,23 @@ void SCSI_SenseCode(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t sKey, uint8_
*/ */
static void SCSI_StartStopUnit(void) static void SCSI_StartStopUnit(void)
{ {
if ((SCSI_ProcessCmd_params[4] & START_STOP_DATA_MASK) == START_STOP_DATA_EJECT_STOP_MOTOR)
{
USBD_RequestStop(SCSI_ProcessCmd_pdev); //Host is signalling us to disconnect
}
SCSI_ProcessCmd_hmsc->bot_data_length = 0; SCSI_ProcessCmd_hmsc->bot_data_length = 0;
SCSI_ProcessCmd_callback(0); SCSI_ProcessCmd_callback(0);
} }
static void SCSI_AllowMediumRemoval(void)
{
SCSI_ProcessCmd_hmsc->bot_data_length = 0;
SCSI_ProcessCmd_callback(0);
}
/** /**
* @brief SCSI_Read10 * @brief SCSI_Read10
* Process Read10 command * Process Read10 command

@ -92,6 +92,7 @@ USBD_StatusTypeDef USBD_Init(USBD_HandleTypeDef *pdev, USBD_DescriptorsTypeDef *
USBD_ClassTypeDef* USBD_DeInit(USBD_HandleTypeDef *pdev); USBD_ClassTypeDef* USBD_DeInit(USBD_HandleTypeDef *pdev);
USBD_StatusTypeDef USBD_Start (USBD_HandleTypeDef *pdev); USBD_StatusTypeDef USBD_Start (USBD_HandleTypeDef *pdev);
USBD_StatusTypeDef USBD_Stop (USBD_HandleTypeDef *pdev); USBD_StatusTypeDef USBD_Stop (USBD_HandleTypeDef *pdev);
USBD_StatusTypeDef USBD_RequestStop(USBD_HandleTypeDef *pdev);
USBD_StatusTypeDef USBD_RegisterClass(USBD_HandleTypeDef *pdev, USBD_ClassTypeDef *pclass); USBD_StatusTypeDef USBD_RegisterClass(USBD_HandleTypeDef *pdev, USBD_ClassTypeDef *pclass);
USBD_StatusTypeDef USBD_RunTestMode (USBD_HandleTypeDef *pdev); USBD_StatusTypeDef USBD_RunTestMode (USBD_HandleTypeDef *pdev);

@ -222,10 +222,18 @@ typedef struct
uint32_t maxpacket; uint32_t maxpacket;
} USBD_EndpointTypeDef; } USBD_EndpointTypeDef;
typedef enum
{
USB_STATUS_STOP,
USB_STATUS_START,
USB_STATUS_REQUEST_EJECT
} UsbCoreStatusTypeDef;
/* USB Device handle structure */ /* USB Device handle structure */
typedef struct _USBD_HandleTypeDef typedef struct _USBD_HandleTypeDef
{ {
uint8_t id;
uint32_t dev_config; uint32_t dev_config;
uint32_t dev_default_config; uint32_t dev_default_config;
uint32_t dev_config_status; uint32_t dev_config_status;
@ -234,6 +242,9 @@ typedef struct _USBD_HandleTypeDef
USBD_EndpointTypeDef ep_out[15]; USBD_EndpointTypeDef ep_out[15];
uint32_t ep0_state; uint32_t ep0_state;
uint32_t ep0_data_len; uint32_t ep0_data_len;
uint32_t usbRequestEjectTime;
uint8_t id;
uint8_t usbCoreStatus;
uint8_t dev_state; uint8_t dev_state;
uint8_t dev_old_state; uint8_t dev_old_state;
uint8_t dev_address; uint8_t dev_address;

@ -121,6 +121,8 @@ USBD_StatusTypeDef USBD_Init(USBD_HandleTypeDef *pdev, USBD_DescriptorsTypeDef *
/* Initialize low level driver */ /* Initialize low level driver */
USBD_LL_Init(pdev); USBD_LL_Init(pdev);
pdev->usbCoreStatus = USB_STATUS_STOP;
return USBD_OK; return USBD_OK;
} }
@ -184,10 +186,11 @@ USBD_StatusTypeDef USBD_RegisterClass(USBD_HandleTypeDef *pdev, USBD_ClassTypeD
*/ */
USBD_StatusTypeDef USBD_Start (USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_Start (USBD_HandleTypeDef *pdev)
{ {
/* Start the low level driver */ /* Start the low level driver */
USBD_LL_Start(pdev); USBD_LL_Start(pdev);
pdev->usbCoreStatus = USB_STATUS_START;
return USBD_OK; return USBD_OK;
} }
@ -205,9 +208,23 @@ USBD_StatusTypeDef USBD_Stop (USBD_HandleTypeDef *pdev)
/* Stop the low level driver */ /* Stop the low level driver */
USBD_LL_Stop(pdev); USBD_LL_Stop(pdev);
pdev->usbCoreStatus = USB_STATUS_STOP;
return USBD_OK;
}
USBD_StatusTypeDef USBD_RequestStop(USBD_HandleTypeDef *pdev)
{
if (pdev->usbCoreStatus == USB_STATUS_START)
{
pdev->usbCoreStatus = USB_STATUS_REQUEST_EJECT;
pdev->usbRequestEjectTime = HAL_GetTick() + 5; //Allow > 1ms to transmit the SCSI eject reply before disconnecting
}
return USBD_OK; return USBD_OK;
} }
/** /**
* @brief USBD_RunTestMode * @brief USBD_RunTestMode
* Launch test mode process * Launch test mode process
@ -216,6 +233,8 @@ USBD_StatusTypeDef USBD_Stop (USBD_HandleTypeDef *pdev)
*/ */
USBD_StatusTypeDef USBD_RunTestMode (USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_RunTestMode (USBD_HandleTypeDef *pdev)
{ {
UNUSED(pdev);
return USBD_OK; return USBD_OK;
} }
@ -500,6 +519,14 @@ USBD_StatusTypeDef USBD_SOF(USBD_HandleTypeDef *pdev)
pdev->pClass->SOF(pdev); pdev->pClass->SOF(pdev);
} }
} }
if (pdev->usbCoreStatus == USB_STATUS_REQUEST_EJECT)
{
if ((int32_t)(HAL_GetTick() - pdev->usbRequestEjectTime) >= 0)
{
USBD_Stop(pdev);
}
}
return USBD_OK; return USBD_OK;
} }
@ -511,6 +538,8 @@ USBD_StatusTypeDef USBD_SOF(USBD_HandleTypeDef *pdev)
*/ */
USBD_StatusTypeDef USBD_IsoINIncomplete(USBD_HandleTypeDef *pdev, uint8_t epnum) USBD_StatusTypeDef USBD_IsoINIncomplete(USBD_HandleTypeDef *pdev, uint8_t epnum)
{ {
UNUSED(pdev);
return USBD_OK; return USBD_OK;
} }
@ -522,6 +551,8 @@ USBD_StatusTypeDef USBD_IsoINIncomplete(USBD_HandleTypeDef *pdev, uint8_t epnum
*/ */
USBD_StatusTypeDef USBD_IsoOUTIncomplete(USBD_HandleTypeDef *pdev, uint8_t epnum) USBD_StatusTypeDef USBD_IsoOUTIncomplete(USBD_HandleTypeDef *pdev, uint8_t epnum)
{ {
UNUSED(pdev);
return USBD_OK; return USBD_OK;
} }
@ -533,6 +564,8 @@ USBD_StatusTypeDef USBD_IsoOUTIncomplete(USBD_HandleTypeDef *pdev, uint8_t epnu
*/ */
USBD_StatusTypeDef USBD_DevConnected(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_DevConnected(USBD_HandleTypeDef *pdev)
{ {
UNUSED(pdev);
return USBD_OK; return USBD_OK;
} }

@ -292,7 +292,7 @@ USBD_StatusTypeDef USBD_LL_Init (USBD_HandleTypeDef *pdev)
hpcd_USB_OTG_FS.Init.dma_enable = DISABLE; hpcd_USB_OTG_FS.Init.dma_enable = DISABLE;
hpcd_USB_OTG_FS.Init.ep0_mps = DEP0CTL_MPS_64; hpcd_USB_OTG_FS.Init.ep0_mps = DEP0CTL_MPS_64;
hpcd_USB_OTG_FS.Init.phy_itface = PCD_PHY_EMBEDDED; hpcd_USB_OTG_FS.Init.phy_itface = PCD_PHY_EMBEDDED;
hpcd_USB_OTG_FS.Init.Sof_enable = DISABLE; hpcd_USB_OTG_FS.Init.Sof_enable = ENABLE;
hpcd_USB_OTG_FS.Init.low_power_enable = DISABLE; hpcd_USB_OTG_FS.Init.low_power_enable = DISABLE;
hpcd_USB_OTG_FS.Init.vbus_sensing_enable = DISABLE; hpcd_USB_OTG_FS.Init.vbus_sensing_enable = DISABLE;
hpcd_USB_OTG_FS.Init.use_dedicated_ep1 = DISABLE; hpcd_USB_OTG_FS.Init.use_dedicated_ep1 = DISABLE;

Loading…
Cancel
Save