Browse Source

Expand direct SD interface to reads over 128 sectors

Michael McMaster 3 years ago
parent
commit
e578450e88
3 changed files with 31 additions and 32 deletions
  1. 13 21
      lib/SCSI2SD/src/firmware/disk.c
  2. 16 10
      lib/SCSI2SD/src/firmware/sd.c
  3. 2 1
      lib/SCSI2SD/src/firmware/sd.h

+ 13 - 21
lib/SCSI2SD/src/firmware/disk.c

@@ -38,8 +38,6 @@
 #include "time.h"
 #include "bsp.h"
 
-#include "led.h"
-
 #include <string.h>
 
 // Global
@@ -690,7 +688,7 @@ static void diskDataInBuffered(int totalSDSectors, uint32_t sdLBA, int useSlowDa
 // Only functional for 512 byte sectors.
 static void diskDataInDirect(uint32_t totalSDSectors, uint32_t sdLBA, int useSlowDataCount, uint32_t* phaseChangeDelayNs)
 {
-    sdReadPIO(sdLBA, totalSDSectors);
+    sdReadCmd(sdLBA, totalSDSectors);
 
     // Wait while the SD card starts buffering data
     if (*phaseChangeDelayNs > 0)
@@ -701,11 +699,18 @@ static void diskDataInDirect(uint32_t totalSDSectors, uint32_t sdLBA, int useSlo
 
     for (int i = 0; i < totalSDSectors && !scsiDev.resetFlag; ++i)
     {
-        // TODO if i %128 == 0, and not in an error state, then do another read.
-
-        if (useSlowDataCount)
+        if (i % 128 == 0)
         {
-            scsiSetDataCount(SD_SECTOR_SIZE);
+            // SD DPSM has 24 bit limit. Re-use 128 (DMA limit)
+            uint32_t chunk = totalSDSectors - i > 128 ? 128 : totalSDSectors - i;
+            sdReadPIOData(chunk);
+
+            if (useSlowDataCount)
+            {
+                while (!scsiDev.resetFlag && !scsiPhyComplete())
+                {}
+                scsiSetDataCount(chunk * SD_SECTOR_SIZE); // SCSI_XFER_MAX > 65536
+            }
         }
 
         // The SCSI fifo is a full sector so we only need to check once.
@@ -735,13 +740,6 @@ static void diskDataInDirect(uint32_t totalSDSectors, uint32_t sdLBA, int useSlo
                     *((volatile uint32_t*)SCSI_FIFO_DATA) = data[1];
                     *((volatile uint32_t*)SCSI_FIFO_DATA) = data[2];
                     *((volatile uint32_t*)SCSI_FIFO_DATA) = data[3];
-
-                    /*
-                    scsiPhyTx32(data[0] & 0xFFFF, data[0] >> 16);
-                    scsiPhyTx32(data[1] & 0xFFFF, data[1] >> 16);
-                    scsiPhyTx32(data[2] & 0xFFFF, data[2] >> 16);
-                    scsiPhyTx32(data[3] & 0xFFFF, data[3] >> 16);
-                    */
                 }
 
                 byteCount += 64;
@@ -784,14 +782,8 @@ static void diskDataInDirect(uint32_t totalSDSectors, uint32_t sdLBA, int useSlo
             scsiPhyTx32(0, 0);
             byteCount += 4;
         }
-
-        while (useSlowDataCount && !scsiDev.resetFlag && !scsiPhyComplete())
-        {
-        }
     }
 
-//while(1) { s2s_ledOn(); s2s_delay_ms(1000); s2s_ledOff(); s2s_delay_ms(1000); }
-
     /* Send stop transmission command in case of multiblock read */
     if(totalSDSectors > 1U)
     {
@@ -838,7 +830,7 @@ static void diskDataIn()
 
 #ifdef STM32F4xx
     // Direct mode requires hardware flow control to be working on the SD peripheral
-    if (bytesPerSector == SD_SECTOR_SIZE && totalSDSectors < 128)
+    if (bytesPerSector == SD_SECTOR_SIZE)
     {
         diskDataInDirect(totalSDSectors, sdLBA, useSlowDataCount, &phaseChangeDelayNs);
     }

+ 16 - 10
lib/SCSI2SD/src/firmware/sd.c

@@ -83,7 +83,7 @@ void sdReadDMA(uint32_t lba, uint32_t sectors, uint8_t* outputBuffer)
 	}
 }
 
-void sdReadPIO(uint32_t lba, uint32_t sectors)
+void sdReadCmd(uint32_t lba, uint32_t sectors)
 {
 	uint32_t errorstate;
 	hsd.ErrorCode = HAL_SD_ERROR_NONE;
@@ -117,15 +117,6 @@ void sdReadPIO(uint32_t lba, uint32_t sectors)
 		}
 	}
 
-	SDIO_DataInitTypeDef config;
-	config.DataTimeOut   = SDMMC_DATATIMEOUT;
-	config.DataLength    = sectors * 512u;
-	config.DataBlockSize = SDIO_DATABLOCK_SIZE_512B;
-	config.TransferDir   = SDIO_TRANSFER_DIR_TO_SDIO;
-	config.TransferMode  = SDIO_TRANSFER_MODE_BLOCK;
-	config.DPSM          = SDIO_DPSM_ENABLE;
-	SDIO_ConfigData(hsd.Instance, &config);
-
 	if(sectors > 1U)
 	{
 		hsd.Context = SD_CONTEXT_READ_MULTIPLE_BLOCK;
@@ -154,6 +145,21 @@ void sdReadPIO(uint32_t lba, uint32_t sectors)
 	}
 }
 
+void sdReadPIOData(uint32_t sectors)
+{
+	/* Initialize data control register */
+	hsd.Instance->DCTRL = 0U;
+
+	SDIO_DataInitTypeDef config;
+	config.DataTimeOut   = SDMMC_DATATIMEOUT;
+	config.DataLength    = sectors * 512u;
+	config.DataBlockSize = SDIO_DATABLOCK_SIZE_512B;
+	config.TransferDir   = SDIO_TRANSFER_DIR_TO_SDIO;
+	config.TransferMode  = SDIO_TRANSFER_MODE_BLOCK;
+	config.DPSM          = SDIO_DPSM_ENABLE;
+	SDIO_ConfigData(hsd.Instance, &config);
+}
+
 
 void sdCompleteTransfer()
 {

+ 2 - 1
lib/SCSI2SD/src/firmware/sd.h

@@ -37,7 +37,8 @@ int sdInit(void);
 void sdReadDMA(uint32_t lba, uint32_t sectors, uint8_t* outputBuffer);
 int sdReadDMAPoll(uint32_t remainingSectors);
 
-void sdReadPIO(uint32_t lba, uint32_t sectors);
+void sdReadCmd(uint32_t lba, uint32_t sectors);
+void sdReadPIOData(uint32_t sectors);
 
 void sdCompleteTransfer();
 void sdKeepAlive();