From 3b1026b0a66100dad5eceefe63cb06eccb52a1bf Mon Sep 17 00:00:00 2001 From: Michael McMaster Date: Tue, 23 Feb 2021 20:36:56 +1000 Subject: [PATCH] Reapply STMCubeMX patches and FIX USB sense codes and workaround for USB<->SDIO dma consistency problem --- STM32CubeMX/2020c.diff | 18 +++-- .../Src/stm32f2xx_hal_sd.c | 70 +++++++++++++------ STM32CubeMX/2020c/Src/fsmc.c | 24 ++++++- STM32CubeMX/2020c/Src/sdio.c | 5 +- STM32CubeMX/2020c/Src/spi.c | 2 + STM32CubeMX/2020c/Src/usbd_conf.c | 15 +++- STM32CubeMX/2021.diff | 24 ++++--- .../Src/stm32f4xx_hal_sd.c | 70 +++++++++++++------ STM32CubeMX/2021/Src/fmc.c | 24 ++++++- STM32CubeMX/2021/Src/sdio.c | 5 +- STM32CubeMX/2021/Src/spi.c | 2 + STM32CubeMX/2021/Src/usbd_conf.c | 14 +++- src/firmware/usb_device/usbd_composite.c | 9 ++- src/firmware/usb_device/usbd_msc_bot.c | 24 +++---- src/firmware/usb_device/usbd_msc_bot.h | 7 +- src/firmware/usb_device/usbd_msc_scsi.c | 64 ++++++++--------- 16 files changed, 251 insertions(+), 126 deletions(-) diff --git a/STM32CubeMX/2020c.diff b/STM32CubeMX/2020c.diff index cc21a39e..5a582b17 100644 --- a/STM32CubeMX/2020c.diff +++ b/STM32CubeMX/2020c.diff @@ -174,7 +174,7 @@ index 03a1b12..1b01446 100644 GPIO_InitStruct.Pin = GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10 |GPIO_PIN_11|GPIO_PIN_12|GPIO_PIN_13|GPIO_PIN_14 diff --git a/STM32CubeMX/2020c/Src/sdio.c b/STM32CubeMX/2020c/Src/sdio.c -index aeec4fa..01f716a 100644 +index f2a0b7c..a00c6a8 100644 --- a/STM32CubeMX/2020c/Src/sdio.c +++ b/STM32CubeMX/2020c/Src/sdio.c @@ -40,6 +40,8 @@ void MX_SDIO_SD_Init(void) @@ -210,7 +210,7 @@ index 902bdb2..4935bf0 100644 hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB; hspi1.Init.TIMode = SPI_TIMODE_DISABLE; diff --git a/STM32CubeMX/2020c/Src/usbd_conf.c b/STM32CubeMX/2020c/Src/usbd_conf.c -index adb664f..9b9b800 100644 +index eee1fd8..9567a95 100644 --- a/STM32CubeMX/2020c/Src/usbd_conf.c +++ b/STM32CubeMX/2020c/Src/usbd_conf.c @@ -458,9 +458,12 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) @@ -218,7 +218,7 @@ index adb664f..9b9b800 100644 HAL_PCD_RegisterIsoInIncpltCallback(&hpcd_USB_OTG_FS, PCD_ISOINIncompleteCallback); #endif /* USE_HAL_PCD_REGISTER_CALLBACKS */ + -+ // Sum of all FIFOs must be <= 320. ++ // Combined RX + TX fifo of 0x140 4-byte words (1280 bytes) HAL_PCDEx_SetRxFiFo(&hpcd_USB_OTG_FS, 0x80); HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 0, 0x40); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 1, 0x80); @@ -227,15 +227,21 @@ index adb664f..9b9b800 100644 } if (pdev->id == DEVICE_HS) { /* Link the driver to the stack. */ -@@ -498,8 +501,9 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) +@@ -497,9 +500,15 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) + HAL_PCD_RegisterIsoOutIncpltCallback(&hpcd_USB_OTG_HS, PCD_ISOOUTIncompleteCallback); HAL_PCD_RegisterIsoInIncpltCallback(&hpcd_USB_OTG_HS, PCD_ISOINIncompleteCallback); #endif /* USE_HAL_PCD_REGISTER_CALLBACKS */ ++ // Combined RX + TX fifo of 0x400 4-byte words (4096 bytes) HAL_PCDEx_SetRxFiFo(&hpcd_USB_OTG_HS, 0x200); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 0, 0x80); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x174); + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 0, 0x40); -+ HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x40); -+ HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 2, 0x174); ++ ++// HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x100); ++// HOst requests 7 sectors, which is an odd number and doesn't fill the ++// fifo, looks like it doesn't complete in this case !!!! ++ HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x80); // 512 bytes ++ HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 2, 0x40); } return USBD_OK; } diff --git a/STM32CubeMX/2020c/Drivers/STM32F2xx_HAL_Driver/Src/stm32f2xx_hal_sd.c b/STM32CubeMX/2020c/Drivers/STM32F2xx_HAL_Driver/Src/stm32f2xx_hal_sd.c index 569c8b1c..cd27bd74 100644 --- a/STM32CubeMX/2020c/Drivers/STM32F2xx_HAL_Driver/Src/stm32f2xx_hal_sd.c +++ b/STM32CubeMX/2020c/Drivers/STM32F2xx_HAL_Driver/Src/stm32f2xx_hal_sd.c @@ -430,6 +430,10 @@ HAL_StatusTypeDef HAL_SD_InitCard(SD_HandleTypeDef *hsd) /* Enable SDIO Clock */ __HAL_SD_ENABLE(hsd); + /* 1ms: required power up waiting time before starting the SD initialization + sequence */ + HAL_Delay(1); + /* Identify card operating voltage */ errorstate = SD_PowerON(hsd); if(errorstate != HAL_SD_ERROR_NONE) @@ -1227,22 +1231,22 @@ HAL_StatusTypeDef HAL_SD_ReadBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, u else { /* Enable SD DMA transfer */ - __HAL_SD_DMA_ENABLE(hsd); + // MM disabled, as this fails on fast cards. __HAL_SD_DMA_ENABLE(hsd); if(hsd->SdCard.CardType != CARD_SDHC_SDXC) { add *= 512U; - } - /* Set Block Size for Card */ - errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE); - if(errorstate != HAL_SD_ERROR_NONE) - { - /* Clear all the static flags */ - __HAL_SD_CLEAR_FLAG(hsd, SDIO_STATIC_FLAGS); - hsd->ErrorCode |= errorstate; - hsd->State = HAL_SD_STATE_READY; - return HAL_ERROR; + /* Set Block Size for Card */ + errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE); + if(errorstate != HAL_SD_ERROR_NONE) + { + /* Clear all the static flags */ + __HAL_SD_CLEAR_FLAG(hsd, SDIO_STATIC_FLAGS); + hsd->ErrorCode |= errorstate; + hsd->State = HAL_SD_STATE_READY; + return HAL_ERROR; + } } /* Configure the SD DPSM (Data Path State Machine) */ @@ -1252,6 +1256,11 @@ HAL_StatusTypeDef HAL_SD_ReadBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, u config.TransferDir = SDIO_TRANSFER_DIR_TO_SDIO; config.TransferMode = SDIO_TRANSFER_MODE_BLOCK; config.DPSM = SDIO_DPSM_ENABLE; + + // We cannot enable DMA too early on UHS-I class 3 SD cards, or else the + // data is just discarded before the dpsm is started. + __HAL_SD_DMA_ENABLE(hsd); + (void)SDIO_ConfigData(hsd->Instance, &config); /* Read Blocks in DMA mode */ @@ -1343,17 +1352,17 @@ HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, if(hsd->SdCard.CardType != CARD_SDHC_SDXC) { add *= 512U; - } - /* Set Block Size for Card */ - errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE); - if(errorstate != HAL_SD_ERROR_NONE) - { - /* Clear all the static flags */ - __HAL_SD_CLEAR_FLAG(hsd, SDIO_STATIC_FLAGS); - hsd->ErrorCode |= errorstate; - hsd->State = HAL_SD_STATE_READY; - return HAL_ERROR; + /* Set Block Size for Card */ + errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE); + if(errorstate != HAL_SD_ERROR_NONE) + { + /* Clear all the static flags */ + __HAL_SD_CLEAR_FLAG(hsd, SDIO_STATIC_FLAGS); + hsd->ErrorCode |= errorstate; + hsd->State = HAL_SD_STATE_READY; + return HAL_ERROR; + } } /* Write Blocks in Polling mode */ @@ -1361,6 +1370,18 @@ HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, { hsd->Context = (SD_CONTEXT_WRITE_MULTIPLE_BLOCK | SD_CONTEXT_DMA); + /* MM: Prepare for write */ +/* TODO + SDMMC_CmdAppCommand(hsd->Instance, (uint32_t)(hsd->RCA << 16)); + SDIO_CmdInitTypeDef mm_cmdinit; + mm_cmdinit.Argument = (uint32_t)NumberOfBlocks; + mm_cmdinit.CmdIndex = SDMMC_CMD_SET_BLOCK_COUNT; + mm_cmdinit.Response = SDIO_RESPONSE_SHORT; + mm_cmdinit.WaitForInterrupt = SDIO_WAIT_NO; + mm_cmdinit.CPSM = SDIO_CPSM_ENABLE; + (void)SDIO_SendCommand(hsd->Instance, &mm_cmdinit); + SDMMC_GetCmdResp1(hsd->Instance, SDMMC_CMD_SET_BLOCK_COUNT, SDIO_CMDTIMEOUT);*/ + /* Write Multi Block command */ errorstate = SDMMC_CmdWriteMultiBlock(hsd->Instance, add); } @@ -1382,7 +1403,7 @@ HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, } /* Enable SDIO DMA transfer */ - __HAL_SD_DMA_ENABLE(hsd); + // MM disabled, as this fails on fast cards. __HAL_SD_DMA_ENABLE(hsd); /* Enable the DMA Channel */ if(HAL_DMA_Start_IT(hsd->hdmatx, (uint32_t)pData, (uint32_t)&hsd->Instance->FIFO, (uint32_t)(BLOCKSIZE * NumberOfBlocks)/4U) != HAL_OK) @@ -1403,6 +1424,11 @@ HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, config.TransferDir = SDIO_TRANSFER_DIR_TO_CARD; config.TransferMode = SDIO_TRANSFER_MODE_BLOCK; config.DPSM = SDIO_DPSM_ENABLE; + + // We cannot enable DMA too early on UHS-I class 3 SD cards, or else the + // data is just discarded before the dpsm is started. + __HAL_SD_DMA_ENABLE(); + (void)SDIO_ConfigData(hsd->Instance, &config); return HAL_OK; diff --git a/STM32CubeMX/2020c/Src/fsmc.c b/STM32CubeMX/2020c/Src/fsmc.c index 03a1b12b..1b01446f 100644 --- a/STM32CubeMX/2020c/Src/fsmc.c +++ b/STM32CubeMX/2020c/Src/fsmc.c @@ -50,12 +50,28 @@ void MX_FSMC_Init(void) hsram1.Init.AsynchronousWait = FSMC_ASYNCHRONOUS_WAIT_DISABLE; hsram1.Init.WriteBurst = FSMC_WRITE_BURST_DISABLE; /* Timing */ + + // 1 clock to read the address, + 1 for synchroniser skew Timing.AddressSetupTime = 2; Timing.AddressHoldTime = 1; + + // Writes to device: + // 1 for synchroniser skew (dbx also delayed) + // 1 to skip hold time + // 1 to write data. + + // Reads from device: + // 3 for syncroniser + // 1 to write back to fsmc bus. Timing.DataSetupTime = 4; + + // Allow a clock for us to release signals + // Need to avoid both devices acting as outputs + // on the multiplexed lines at the same time. Timing.BusTurnAroundDuration = 1; - Timing.CLKDivision = 16; - Timing.DataLatency = 17; + + Timing.CLKDivision = 16; // Ignored for async + Timing.DataLatency = 17; // Ignored for async Timing.AccessMode = FSMC_ACCESS_MODE_A; /* ExtTiming */ @@ -105,6 +121,10 @@ static void HAL_FSMC_MspInit(void){ PE0 ------> FSMC_NBL0 PE1 ------> FSMC_NBL1 */ + + // MM: GPIO_SPEED_FREQ_MEDIUM is rated up to 50MHz, which is fine as all the + // fsmc timings are > 1 (ie. so clock speed / 2 is around 50MHz). + /* GPIO_InitStruct */ GPIO_InitStruct.Pin = GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10 |GPIO_PIN_11|GPIO_PIN_12|GPIO_PIN_13|GPIO_PIN_14 diff --git a/STM32CubeMX/2020c/Src/sdio.c b/STM32CubeMX/2020c/Src/sdio.c index f2a0b7ce..a00c6a8e 100644 --- a/STM32CubeMX/2020c/Src/sdio.c +++ b/STM32CubeMX/2020c/Src/sdio.c @@ -40,6 +40,8 @@ void MX_SDIO_SD_Init(void) hsd.Init.BusWide = SDIO_BUS_WIDE_1B; hsd.Init.HardwareFlowControl = SDIO_HARDWARE_FLOW_CONTROL_DISABLE; hsd.Init.ClockDiv = 0; + + /* if (HAL_SD_Init(&hsd) != HAL_OK) { Error_Handler(); @@ -47,8 +49,7 @@ void MX_SDIO_SD_Init(void) if (HAL_SD_ConfigWideBusOperation(&hsd, SDIO_BUS_WIDE_4B) != HAL_OK) { Error_Handler(); - } - + }*/ } void HAL_SD_MspInit(SD_HandleTypeDef* sdHandle) diff --git a/STM32CubeMX/2020c/Src/spi.c b/STM32CubeMX/2020c/Src/spi.c index 902bdb2d..4935bf00 100644 --- a/STM32CubeMX/2020c/Src/spi.c +++ b/STM32CubeMX/2020c/Src/spi.c @@ -37,6 +37,8 @@ void MX_SPI1_Init(void) hspi1.Init.CLKPolarity = SPI_POLARITY_HIGH; hspi1.Init.CLKPhase = SPI_PHASE_2EDGE; hspi1.Init.NSS = SPI_NSS_SOFT; + + // 13.5Mbaud FPGA device allows up to 25MHz write hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_4; hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB; hspi1.Init.TIMode = SPI_TIMODE_DISABLE; diff --git a/STM32CubeMX/2020c/Src/usbd_conf.c b/STM32CubeMX/2020c/Src/usbd_conf.c index eee1fd89..9567a957 100644 --- a/STM32CubeMX/2020c/Src/usbd_conf.c +++ b/STM32CubeMX/2020c/Src/usbd_conf.c @@ -458,9 +458,12 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) HAL_PCD_RegisterIsoOutIncpltCallback(&hpcd_USB_OTG_FS, PCD_ISOOUTIncompleteCallback); HAL_PCD_RegisterIsoInIncpltCallback(&hpcd_USB_OTG_FS, PCD_ISOINIncompleteCallback); #endif /* USE_HAL_PCD_REGISTER_CALLBACKS */ + + // Combined RX + TX fifo of 0x140 4-byte words (1280 bytes) HAL_PCDEx_SetRxFiFo(&hpcd_USB_OTG_FS, 0x80); HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 0, 0x40); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 1, 0x80); + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 1, 0x40); + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 2, 0x40); } if (pdev->id == DEVICE_HS) { /* Link the driver to the stack. */ @@ -497,9 +500,15 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) HAL_PCD_RegisterIsoOutIncpltCallback(&hpcd_USB_OTG_HS, PCD_ISOOUTIncompleteCallback); HAL_PCD_RegisterIsoInIncpltCallback(&hpcd_USB_OTG_HS, PCD_ISOINIncompleteCallback); #endif /* USE_HAL_PCD_REGISTER_CALLBACKS */ + // Combined RX + TX fifo of 0x400 4-byte words (4096 bytes) HAL_PCDEx_SetRxFiFo(&hpcd_USB_OTG_HS, 0x200); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 0, 0x80); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x174); + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 0, 0x40); + +// HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x100); +// HOst requests 7 sectors, which is an odd number and doesn't fill the +// fifo, looks like it doesn't complete in this case !!!! + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x80); // 512 bytes + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 2, 0x40); } return USBD_OK; } diff --git a/STM32CubeMX/2021.diff b/STM32CubeMX/2021.diff index b67f732e..d77cad7a 100644 --- a/STM32CubeMX/2021.diff +++ b/STM32CubeMX/2021.diff @@ -174,7 +174,7 @@ index dae179a..995fd15 100644 GPIO_InitStruct.Pin = GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10 |GPIO_PIN_11|GPIO_PIN_12|GPIO_PIN_13|GPIO_PIN_14 diff --git a/STM32CubeMX/2021/Src/sdio.c b/STM32CubeMX/2021/Src/sdio.c -index 3c8aff3..f187a45 100644 +index 01e3895..33fbae1 100644 --- a/STM32CubeMX/2021/Src/sdio.c +++ b/STM32CubeMX/2021/Src/sdio.c @@ -40,6 +40,8 @@ void MX_SDIO_SD_Init(void) @@ -197,7 +197,7 @@ index 3c8aff3..f187a45 100644 void HAL_SD_MspInit(SD_HandleTypeDef* sdHandle) diff --git a/STM32CubeMX/2021/Src/spi.c b/STM32CubeMX/2021/Src/spi.c -index 902bdb2..1d8d45e 100644 +index 2f9fbfb..aa786dd 100644 --- a/STM32CubeMX/2021/Src/spi.c +++ b/STM32CubeMX/2021/Src/spi.c @@ -37,6 +37,8 @@ void MX_SPI1_Init(void) @@ -210,11 +210,14 @@ index 902bdb2..1d8d45e 100644 hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB; hspi1.Init.TIMode = SPI_TIMODE_DISABLE; diff --git a/STM32CubeMX/2021/Src/usbd_conf.c b/STM32CubeMX/2021/Src/usbd_conf.c -index 1e08ba4..110da2f 100644 +index 5b10126..a2c4047 100644 --- a/STM32CubeMX/2021/Src/usbd_conf.c +++ b/STM32CubeMX/2021/Src/usbd_conf.c -@@ -468,7 +468,8 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) +@@ -466,9 +466,11 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) + HAL_PCD_RegisterIsoOutIncpltCallback(&hpcd_USB_OTG_FS, PCD_ISOOUTIncompleteCallback); + HAL_PCD_RegisterIsoInIncpltCallback(&hpcd_USB_OTG_FS, PCD_ISOINIncompleteCallback); #endif /* USE_HAL_PCD_REGISTER_CALLBACKS */ ++ // Combined RX + TX fifo of 0x140 4-byte words (1280 bytes) HAL_PCDEx_SetRxFiFo(&hpcd_USB_OTG_FS, 0x80); HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 0, 0x40); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 1, 0x80); @@ -223,16 +226,21 @@ index 1e08ba4..110da2f 100644 } if (pdev->id == DEVICE_HS) { /* Link the driver to the stack. */ -@@ -507,8 +508,9 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) +@@ -506,9 +508,15 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) + HAL_PCD_RegisterIsoOutIncpltCallback(&hpcd_USB_OTG_HS, PCD_ISOOUTIncompleteCallback); HAL_PCD_RegisterIsoInIncpltCallback(&hpcd_USB_OTG_HS, PCD_ISOINIncompleteCallback); #endif /* USE_HAL_PCD_REGISTER_CALLBACKS */ ++ // Combined RX + TX fifo of 0x400 4-byte words (4096 bytes) HAL_PCDEx_SetRxFiFo(&hpcd_USB_OTG_HS, 0x200); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 0, 0x80); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x174); + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 0, 0x40); -+ HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x40); -+ HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 2, 0x174); ++ ++// HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x100); ++// HOst requests 7 sectors, which is an odd number and doesn't fill the ++// fifo, looks like it doesn't complete in this case !!!! ++ HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x80); // 512 bytes ++ HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 2, 0x40); } return USBD_OK; } - diff --git a/STM32CubeMX/2021/Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal_sd.c b/STM32CubeMX/2021/Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal_sd.c index d2a88d75..6fffb514 100644 --- a/STM32CubeMX/2021/Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal_sd.c +++ b/STM32CubeMX/2021/Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal_sd.c @@ -430,6 +430,10 @@ HAL_StatusTypeDef HAL_SD_InitCard(SD_HandleTypeDef *hsd) /* Enable SDIO Clock */ __HAL_SD_ENABLE(hsd); + /* 1ms: required power up waiting time before starting the SD initialization + sequence */ + HAL_Delay(1); + /* Identify card operating voltage */ errorstate = SD_PowerON(hsd); if(errorstate != HAL_SD_ERROR_NONE) @@ -1247,22 +1251,22 @@ HAL_StatusTypeDef HAL_SD_ReadBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, u else { /* Enable SD DMA transfer */ - __HAL_SD_DMA_ENABLE(hsd); + // MM disabled, as this fails on fast cards. __HAL_SD_DMA_ENABLE(hsd); if(hsd->SdCard.CardType != CARD_SDHC_SDXC) { add *= 512U; - } - /* Set Block Size for Card */ - errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE); - if(errorstate != HAL_SD_ERROR_NONE) - { - /* Clear all the static flags */ - __HAL_SD_CLEAR_FLAG(hsd, SDIO_STATIC_FLAGS); - hsd->ErrorCode |= errorstate; - hsd->State = HAL_SD_STATE_READY; - return HAL_ERROR; + /* Set Block Size for Card */ + errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE); + if(errorstate != HAL_SD_ERROR_NONE) + { + /* Clear all the static flags */ + __HAL_SD_CLEAR_FLAG(hsd, SDIO_STATIC_FLAGS); + hsd->ErrorCode |= errorstate; + hsd->State = HAL_SD_STATE_READY; + return HAL_ERROR; + } } /* Configure the SD DPSM (Data Path State Machine) */ @@ -1272,6 +1276,11 @@ HAL_StatusTypeDef HAL_SD_ReadBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, u config.TransferDir = SDIO_TRANSFER_DIR_TO_SDIO; config.TransferMode = SDIO_TRANSFER_MODE_BLOCK; config.DPSM = SDIO_DPSM_ENABLE; + + // We cannot enable DMA too early on UHS-I class 3 SD cards, or else the + // data is just discarded before the dpsm is started. + __HAL_SD_DMA_ENABLE(); + (void)SDIO_ConfigData(hsd->Instance, &config); /* Read Blocks in DMA mode */ @@ -1367,17 +1376,17 @@ HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, if(hsd->SdCard.CardType != CARD_SDHC_SDXC) { add *= 512U; - } - /* Set Block Size for Card */ - errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE); - if(errorstate != HAL_SD_ERROR_NONE) - { - /* Clear all the static flags */ - __HAL_SD_CLEAR_FLAG(hsd, SDIO_STATIC_FLAGS); - hsd->ErrorCode |= errorstate; - hsd->State = HAL_SD_STATE_READY; - return HAL_ERROR; + /* Set Block Size for Card */ + errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE); + if(errorstate != HAL_SD_ERROR_NONE) + { + /* Clear all the static flags */ + __HAL_SD_CLEAR_FLAG(hsd, SDIO_STATIC_FLAGS); + hsd->ErrorCode |= errorstate; + hsd->State = HAL_SD_STATE_READY; + return HAL_ERROR; + } } /* Write Blocks in Polling mode */ @@ -1385,6 +1394,18 @@ HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, { hsd->Context = (SD_CONTEXT_WRITE_MULTIPLE_BLOCK | SD_CONTEXT_DMA); + /* MM: Prepare for write */ +/* TODO + SDMMC_CmdAppCommand(hsd->Instance, (uint32_t)(hsd->RCA << 16)); + SDIO_CmdInitTypeDef mm_cmdinit; + mm_cmdinit.Argument = (uint32_t)NumberOfBlocks; + mm_cmdinit.CmdIndex = SDMMC_CMD_SET_BLOCK_COUNT; + mm_cmdinit.Response = SDIO_RESPONSE_SHORT; + mm_cmdinit.WaitForInterrupt = SDIO_WAIT_NO; + mm_cmdinit.CPSM = SDIO_CPSM_ENABLE; + (void)SDIO_SendCommand(hsd->Instance, &mm_cmdinit); + SDMMC_GetCmdResp1(hsd->Instance, SDMMC_CMD_SET_BLOCK_COUNT, SDIO_CMDTIMEOUT);*/ + /* Write Multi Block command */ errorstate = SDMMC_CmdWriteMultiBlock(hsd->Instance, add); } @@ -1406,7 +1427,7 @@ HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, } /* Enable SDIO DMA transfer */ - __HAL_SD_DMA_ENABLE(hsd); + // MM disabled, as this fails on fast cards. __HAL_SD_DMA_ENABLE(hsd); /* Enable the DMA Channel */ if(HAL_DMA_Start_IT(hsd->hdmatx, (uint32_t)pData, (uint32_t)&hsd->Instance->FIFO, (uint32_t)(BLOCKSIZE * NumberOfBlocks)/4U) != HAL_OK) @@ -1431,6 +1452,11 @@ HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, config.TransferDir = SDIO_TRANSFER_DIR_TO_CARD; config.TransferMode = SDIO_TRANSFER_MODE_BLOCK; config.DPSM = SDIO_DPSM_ENABLE; + + // We cannot enable DMA too early on UHS-I class 3 SD cards, or else the + // data is just discarded before the dpsm is started. + __HAL_SD_DMA_ENABLE(); + (void)SDIO_ConfigData(hsd->Instance, &config); return HAL_OK; diff --git a/STM32CubeMX/2021/Src/fmc.c b/STM32CubeMX/2021/Src/fmc.c index dae179a8..995fd15d 100644 --- a/STM32CubeMX/2021/Src/fmc.c +++ b/STM32CubeMX/2021/Src/fmc.c @@ -52,12 +52,28 @@ void MX_FMC_Init(void) hsram1.Init.WriteFifo = FMC_WRITE_FIFO_ENABLE; hsram1.Init.PageSize = FMC_PAGE_SIZE_NONE; /* Timing */ + + // 1 clock to read the address, + 1 for synchroniser skew Timing.AddressSetupTime = 2; Timing.AddressHoldTime = 1; + + // Writes to device: + // 1 for synchroniser skew (dbx also delayed) + // 1 to skip hold time + // 1 to write data. + + // Reads from device: + // 3 for syncroniser + // 1 to write back to fsmc bus. Timing.DataSetupTime = 4; + + // Allow a clock for us to release signals + // Need to avoid both devices acting as outputs + // on the multiplexed lines at the same time. Timing.BusTurnAroundDuration = 1; - Timing.CLKDivision = 16; - Timing.DataLatency = 17; + + Timing.CLKDivision = 16; // Ignored for async + Timing.DataLatency = 17; // Ignored for async Timing.AccessMode = FMC_ACCESS_MODE_A; /* ExtTiming */ @@ -107,6 +123,10 @@ static void HAL_FMC_MspInit(void){ PE0 ------> FMC_NBL0 PE1 ------> FMC_NBL1 */ + + // MM: GPIO_SPEED_FREQ_MEDIUM is rated up to 50MHz, which is fine as all the + // fsmc timings are > 1 (ie. so clock speed / 2 is around 50MHz). + /* GPIO_InitStruct */ GPIO_InitStruct.Pin = GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10 |GPIO_PIN_11|GPIO_PIN_12|GPIO_PIN_13|GPIO_PIN_14 diff --git a/STM32CubeMX/2021/Src/sdio.c b/STM32CubeMX/2021/Src/sdio.c index 01e38956..33fbae16 100644 --- a/STM32CubeMX/2021/Src/sdio.c +++ b/STM32CubeMX/2021/Src/sdio.c @@ -40,6 +40,8 @@ void MX_SDIO_SD_Init(void) hsd.Init.BusWide = SDIO_BUS_WIDE_1B; hsd.Init.HardwareFlowControl = SDIO_HARDWARE_FLOW_CONTROL_ENABLE; hsd.Init.ClockDiv = 0; + + /* if (HAL_SD_Init(&hsd) != HAL_OK) { Error_Handler(); @@ -47,8 +49,7 @@ void MX_SDIO_SD_Init(void) if (HAL_SD_ConfigWideBusOperation(&hsd, SDIO_BUS_WIDE_4B) != HAL_OK) { Error_Handler(); - } - + }*/ } void HAL_SD_MspInit(SD_HandleTypeDef* sdHandle) diff --git a/STM32CubeMX/2021/Src/spi.c b/STM32CubeMX/2021/Src/spi.c index 2f9fbfbc..aa786dd2 100644 --- a/STM32CubeMX/2021/Src/spi.c +++ b/STM32CubeMX/2021/Src/spi.c @@ -37,6 +37,8 @@ void MX_SPI1_Init(void) hspi1.Init.CLKPolarity = SPI_POLARITY_HIGH; hspi1.Init.CLKPhase = SPI_PHASE_2EDGE; hspi1.Init.NSS = SPI_NSS_SOFT; + + // 22.5Mbaud. FPGA device allows up to 25MHz write hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_4; hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB; hspi1.Init.TIMode = SPI_TIMODE_DISABLE; diff --git a/STM32CubeMX/2021/Src/usbd_conf.c b/STM32CubeMX/2021/Src/usbd_conf.c index 5b101266..a2c40472 100644 --- a/STM32CubeMX/2021/Src/usbd_conf.c +++ b/STM32CubeMX/2021/Src/usbd_conf.c @@ -466,9 +466,11 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) HAL_PCD_RegisterIsoOutIncpltCallback(&hpcd_USB_OTG_FS, PCD_ISOOUTIncompleteCallback); HAL_PCD_RegisterIsoInIncpltCallback(&hpcd_USB_OTG_FS, PCD_ISOINIncompleteCallback); #endif /* USE_HAL_PCD_REGISTER_CALLBACKS */ + // Combined RX + TX fifo of 0x140 4-byte words (1280 bytes) HAL_PCDEx_SetRxFiFo(&hpcd_USB_OTG_FS, 0x80); HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 0, 0x40); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 1, 0x80); + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 1, 0x40); + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_FS, 2, 0x40); } if (pdev->id == DEVICE_HS) { /* Link the driver to the stack. */ @@ -506,9 +508,15 @@ USBD_StatusTypeDef USBD_LL_Init(USBD_HandleTypeDef *pdev) HAL_PCD_RegisterIsoOutIncpltCallback(&hpcd_USB_OTG_HS, PCD_ISOOUTIncompleteCallback); HAL_PCD_RegisterIsoInIncpltCallback(&hpcd_USB_OTG_HS, PCD_ISOINIncompleteCallback); #endif /* USE_HAL_PCD_REGISTER_CALLBACKS */ + // Combined RX + TX fifo of 0x400 4-byte words (4096 bytes) HAL_PCDEx_SetRxFiFo(&hpcd_USB_OTG_HS, 0x200); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 0, 0x80); - HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x174); + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 0, 0x40); + +// HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x100); +// HOst requests 7 sectors, which is an odd number and doesn't fill the +// fifo, looks like it doesn't complete in this case !!!! + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 1, 0x80); // 512 bytes + HAL_PCDEx_SetTxFiFo(&hpcd_USB_OTG_HS, 2, 0x40); } return USBD_OK; } diff --git a/src/firmware/usb_device/usbd_composite.c b/src/firmware/usb_device/usbd_composite.c index aea505da..32d98304 100755 --- a/src/firmware/usb_device/usbd_composite.c +++ b/src/firmware/usb_device/usbd_composite.c @@ -511,15 +511,14 @@ void s2s_usbDevicePoll(USBD_HandleTypeDef *pdev) { if (classData->DataInReady) { - int tmp = classData->DataInReady; classData->DataInReady = 0; - MSC_BOT_DataIn(pdev, tmp); + MSC_BOT_DataIn(pdev); } - if (classData->DataOutReady) { - int tmp = classData->DataOutReady; + if (classData->DataOutReady) + { classData->DataOutReady = 0; - MSC_BOT_DataOut(pdev, tmp); + MSC_BOT_DataOut(pdev); } } diff --git a/src/firmware/usb_device/usbd_msc_bot.c b/src/firmware/usb_device/usbd_msc_bot.c index 98ac924e..85164a85 100755 --- a/src/firmware/usb_device/usbd_msc_bot.c +++ b/src/firmware/usb_device/usbd_msc_bot.c @@ -167,7 +167,7 @@ void MSC_BOT_DeInit (USBD_HandleTypeDef *pdev) * @param epnum: endpoint index * @retval None */ -void MSC_BOT_DataIn (USBD_HandleTypeDef *pdev, uint8_t epnum) +void MSC_BOT_DataIn (USBD_HandleTypeDef *pdev) { USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); @@ -194,10 +194,9 @@ void MSC_BOT_DataIn (USBD_HandleTypeDef *pdev, uint8_t epnum) * @brief MSC_BOT_DataOut * Process MSC OUT data * @param pdev: device instance -* @param epnum: endpoint index * @retval None */ -void MSC_BOT_DataOut (USBD_HandleTypeDef *pdev, uint8_t epnum) +void MSC_BOT_DataOut (USBD_HandleTypeDef *pdev) { USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); @@ -252,14 +251,14 @@ static void MSC_BOT_CBW_Decode (USBD_HandleTypeDef *pdev) { if(SCSI_ProcessCmd(pdev, hmsc->cbw.bLUN, &hmsc->cbw.CB[0]) < 0) { - if(hmsc->bot_state == USBD_BOT_NO_DATA) - { + // if(hmsc->bot_state == USBD_BOT_NO_DATA) + // { MSC_BOT_SendCSW (pdev, USBD_CSW_CMD_FAILED); - } - else - { - MSC_BOT_Abort(pdev); - } + // } + // else + // { + // MSC_BOT_Abort(pdev); + // } } /*Burst xfer handled internally*/ else if ((hmsc->bot_state != USBD_BOT_DATA_IN) && @@ -293,12 +292,13 @@ static void MSC_BOT_SendData(USBD_HandleTypeDef *pdev, USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); - len = MIN (hmsc->cbw.dDataLength, len); + uint16_t length = (uint16_t)MIN(hmsc->cbw.dDataLength, len); + hmsc->csw.dDataResidue -= len; hmsc->csw.bStatus = USBD_CSW_CMD_PASSED; hmsc->bot_state = USBD_BOT_SEND_DATA; - USBD_LL_Transmit (pdev, MSC_EPIN_ADDR, buf, len); + USBD_LL_Transmit (pdev, MSC_EPIN_ADDR, buf, length); } /** diff --git a/src/firmware/usb_device/usbd_msc_bot.h b/src/firmware/usb_device/usbd_msc_bot.h index 61b4f6cd..d453d4f2 100755 --- a/src/firmware/usb_device/usbd_msc_bot.h +++ b/src/firmware/usb_device/usbd_msc_bot.h @@ -127,11 +127,8 @@ USBD_MSC_BOT_CSWTypeDef; void MSC_BOT_Init (USBD_HandleTypeDef *pdev); void MSC_BOT_Reset (USBD_HandleTypeDef *pdev); void MSC_BOT_DeInit (USBD_HandleTypeDef *pdev); -void MSC_BOT_DataIn (USBD_HandleTypeDef *pdev, - uint8_t epnum); - -void MSC_BOT_DataOut (USBD_HandleTypeDef *pdev, - uint8_t epnum); +void MSC_BOT_DataIn (USBD_HandleTypeDef *pdev); +void MSC_BOT_DataOut (USBD_HandleTypeDef *pdev); void MSC_BOT_SendCSW (USBD_HandleTypeDef *pdev, uint8_t CSW_Status); diff --git a/src/firmware/usb_device/usbd_msc_scsi.c b/src/firmware/usb_device/usbd_msc_scsi.c index 63ddca6d..aa0880c2 100755 --- a/src/firmware/usb_device/usbd_msc_scsi.c +++ b/src/firmware/usb_device/usbd_msc_scsi.c @@ -507,11 +507,9 @@ static int8_t SCSI_Read10(USBD_HandleTypeDef *pdev, uint8_t lun , uint8_t *para } hmsc->bot_state = USBD_BOT_DATA_IN; - hmsc->scsi_blk_addr *= hmsc->scsi_blk_size; - hmsc->scsi_blk_len *= hmsc->scsi_blk_size; /* cases 4,5 : Hi <> Dn */ - if (hmsc->cbw.dDataLength != hmsc->scsi_blk_len) + if (hmsc->cbw.dDataLength != (hmsc->scsi_blk_len * hmsc->scsi_blk_size)) { SCSI_SenseCode(pdev, hmsc->cbw.bLUN, @@ -535,12 +533,12 @@ static int8_t SCSI_Read10(USBD_HandleTypeDef *pdev, uint8_t lun , uint8_t *para static int8_t SCSI_Write10 (USBD_HandleTypeDef *pdev, uint8_t lun , uint8_t *params) { - USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; - USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); + USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; + USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); + uint32_t len; if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */ { - /* case 8 : Hi <> Do */ if ((hmsc->cbw.bmFlags & 0x80) == 0x80) @@ -588,12 +586,11 @@ static int8_t SCSI_Write10 (USBD_HandleTypeDef *pdev, uint8_t lun , uint8_t *pa { return -1; /* error */ } - - hmsc->scsi_blk_addr *= hmsc->scsi_blk_size; - hmsc->scsi_blk_len *= hmsc->scsi_blk_size; + + len = hmsc->scsi_blk_len * hmsc->scsi_blk_size; /* cases 3,11,13 : Hn,Ho <> D0 */ - if (hmsc->cbw.dDataLength != hmsc->scsi_blk_len) + if (hmsc->cbw.dDataLength != len) { SCSI_SenseCode(pdev, hmsc->cbw.bLUN, @@ -601,13 +598,15 @@ static int8_t SCSI_Write10 (USBD_HandleTypeDef *pdev, uint8_t lun , uint8_t *pa INVALID_CDB); return -1; } + + len = MIN(len, S2S_MSC_MEDIA_PACKET); /* Prepare EP to receive first data packet */ hmsc->bot_state = USBD_BOT_DATA_OUT; USBD_LL_PrepareReceive (pdev, MSC_EPOUT_ADDR, hmsc->bot_data, - MIN (hmsc->scsi_blk_len, S2S_MSC_MEDIA_PACKET)); + len); } else /* Write Process ongoing */ { @@ -698,16 +697,19 @@ static int8_t SCSI_CheckAddressRange (USBD_HandleTypeDef *pdev, uint8_t lun , u */ static int8_t SCSI_ProcessRead (USBD_HandleTypeDef *pdev, uint8_t lun) { - USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; - USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); + USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; + USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); - uint32_t len; - - len = MIN(hmsc->scsi_blk_len , S2S_MSC_MEDIA_PACKET); - + uint32_t len = hmsc->scsi_blk_len * hmsc->scsi_blk_size; + + len = MIN(len, S2S_MSC_MEDIA_PACKET); + + // TODO there is a dcache issue here. + // work out how, and when, to flush cashes between sdio dma and usb dma + memset (hmsc->bot_data, 0xAA, len); if( ((USBD_StorageTypeDef *)pdev->pUserData)->Read(lun , hmsc->bot_data, - hmsc->scsi_blk_addr / hmsc->scsi_blk_size, + hmsc->scsi_blk_addr, len / hmsc->scsi_blk_size) < 0) { @@ -724,9 +726,8 @@ static int8_t SCSI_ProcessRead (USBD_HandleTypeDef *pdev, uint8_t lun) hmsc->bot_data, len); - - hmsc->scsi_blk_addr += len; - hmsc->scsi_blk_len -= len; + hmsc->scsi_blk_addr += (len / hmsc->scsi_blk_size); + hmsc->scsi_blk_len -= (len / hmsc->scsi_blk_size); /* case 6 : Hi = Di */ hmsc->csw.dDataResidue -= len; @@ -747,15 +748,16 @@ static int8_t SCSI_ProcessRead (USBD_HandleTypeDef *pdev, uint8_t lun) static int8_t SCSI_ProcessWrite (USBD_HandleTypeDef *pdev, uint8_t lun) { - uint32_t len; - USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; - USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); + USBD_CompositeClassData *classData = (USBD_CompositeClassData*) pdev->pClassData; + USBD_MSC_BOT_HandleTypeDef *hmsc = &(classData->msc); - len = MIN(hmsc->scsi_blk_len , S2S_MSC_MEDIA_PACKET); + uint32_t len = hmsc->scsi_blk_len * hmsc->scsi_blk_size; + + len = MIN(len, S2S_MSC_MEDIA_PACKET); if(((USBD_StorageTypeDef *)pdev->pUserData)->Write(lun , hmsc->bot_data, - hmsc->scsi_blk_addr / hmsc->scsi_blk_size, + hmsc->scsi_blk_addr, len / hmsc->scsi_blk_size) < 0) { SCSI_SenseCode(pdev, @@ -766,8 +768,8 @@ static int8_t SCSI_ProcessWrite (USBD_HandleTypeDef *pdev, uint8_t lun) } - hmsc->scsi_blk_addr += len; - hmsc->scsi_blk_len -= len; + hmsc->scsi_blk_addr += (len / hmsc->scsi_blk_size); + hmsc->scsi_blk_len -= (len / hmsc->scsi_blk_size); /* case 12 : Ho = Do */ hmsc->csw.dDataResidue -= len; @@ -778,11 +780,9 @@ static int8_t SCSI_ProcessWrite (USBD_HandleTypeDef *pdev, uint8_t lun) } else { + len = MIN((hmsc->scsi_blk_len * hmsc->scsi_blk_size), S2S_MSC_MEDIA_PACKET); /* Prepare EP to Receive next packet */ - USBD_LL_PrepareReceive (pdev, - MSC_EPOUT_ADDR, - hmsc->bot_data, - MIN (hmsc->scsi_blk_len, S2S_MSC_MEDIA_PACKET)); + USBD_LL_PrepareReceive (pdev, MSC_EPOUT_ADDR, hmsc->bot_data, len); } return 0; -- 2.38.5