1
Discussion - Software / Re: MPSSE_SPI - long time between end of transmit and disasserting SS
« on: July 17, 2020, 01:07:40 PM »
I contacted the FTDI support directly and managed to solve my problem. To help others, which may have the same problem, I want to share my solution here.
Removing the LibMPSSE and using D2XX library will increase the speed of writing and reading a lot. My solution is based on this example:
https://www.ftdichip.com/Support/Documents/AppNotes/AN_114_FTDI_Hi_Speed_USB_To_SPI_Example.pdf
U4 SPI_FTDI_WRITE(FT_HANDLE handle, SPI_READBUFFER_pt pReadBuf, uint8* buffer, const U4 sizeToTransfer)
{
uint32 sizeTransfered = 0;
//SPI_Enable();
for (int loop = 0; loop < 5; loop++) //one 0x80 command can keep 0.2us, do 5 times to stay in this situation for 1us
{
OutputBuffer[dwNumBytesToSend++] = '\x80'; // GPIO command for ADBUS
OutputBuffer[dwNumBytesToSend++] = '\xf0'; // set CS low, MOSI and SCL
OutputBuffer[dwNumBytesToSend++] = '\xfb'; // bit3: CS, bit2: MISO, bit1: MOSI, bit0: SCK
}
//send data
OutputBuffer[dwNumBytesToSend++] = MSB_FALLING_EDGE_CLOCK_BYTE_OUT_IN; // 0x11 Write command
OutputBuffer[dwNumBytesToSend++] = (sizeToTransfer - 1); // Length lower byte
OutputBuffer[dwNumBytesToSend++] = (sizeToTransfer - 1) >> 8; // Length higher byte
for (U4 i = 0; i < sizeToTransfer; i++) // size to transfer
{
OutputBuffer[dwNumBytesToSend++] = buffer;
}
//SPI_CSDisable();
for (int loop = 0; loop < 5; loop++) //one 0x80 command can keep 0.2us, do 5 times to stay in this situation for 1us
{
OutputBuffer[dwNumBytesToSend++] = '\x80'; //GPIO command for ADBUS
OutputBuffer[dwNumBytesToSend++] = '\xf8'; //set CS, MOSI and SCL low
OutputBuffer[dwNumBytesToSend++] = '\xfb'; //bit3:CS, bit2:MISO, bit1:MOSI, bit0 : SCK
}
ftStatus = FT_Write(handle, OutputBuffer, dwNumBytesToSend, &sizeTransfered);
dwNumBytesToSend = 0;
ftStatus = FT_Read(handle, inBuffer, sizeToTransfer, &dwNumBytesRead);
sizeTransfered = sizeTransfered ? sizeTransfered - 33 : sizeTransfered;
}
uint32 SPI_FTDI_READ(FT_HANDLE handle, SPI_READBUFFER_pt pReadBuf, uint8* spiData, uint32 size)
{
const uint32 secureSize = MIN(50, size);
uint32 sizeRead;
dwNumBytesSent = 0;
//SPI_Enable();
for (int loop = 0; loop < 5; loop++) //one 0x80 command can keep 0.2us, do 5 times to stay in this situation for 1us
{
OutputBuffer[dwNumBytesToSend++] = '\x80';// GPIO command for ADBUS
OutputBuffer[dwNumBytesToSend++] = '\xf2';// set CS, MOSI and SCL low
OutputBuffer[dwNumBytesToSend++] = '\xfb';// bit3:CS, bit2:MISO, bit1:MOSI, bit0 : SCK
}
//read data
OutputBuffer[dwNumBytesToSend++] = MSB_FALLING_EDGE_CLOCK_BYTE_IN;
OutputBuffer[dwNumBytesToSend++] = (secureSize - 1);
OutputBuffer[dwNumBytesToSend++] = (secureSize - 1) >> 8;
//SPI_CSDisable();
for (int loop = 0; loop < 5; loop++) //one 0x80 command can keep 0.2us, do 5 times to stay in this situation for 1us
{
OutputBuffer[dwNumBytesToSend++] = '\x80';//GPIO command for ADBUS
OutputBuffer[dwNumBytesToSend++] = '\xfa';//set CS, MOSI and SCL low
OutputBuffer[dwNumBytesToSend++] = '\xfb';//bit3:CS, bit2:MISO, bit1:MOSI, bit0 : SCK
}
ftStatus = FT_Write(handle, OutputBuffer, dwNumBytesToSend, &dwNumBytesSent);
dwNumBytesToSend = 0;
ftStatus = FT_Read(handle, spiDataRest, secureSize, &sizeRead);
}
Removing the LibMPSSE and using D2XX library will increase the speed of writing and reading a lot. My solution is based on this example:
https://www.ftdichip.com/Support/Documents/AppNotes/AN_114_FTDI_Hi_Speed_USB_To_SPI_Example.pdf
U4 SPI_FTDI_WRITE(FT_HANDLE handle, SPI_READBUFFER_pt pReadBuf, uint8* buffer, const U4 sizeToTransfer)
{
uint32 sizeTransfered = 0;
//SPI_Enable();
for (int loop = 0; loop < 5; loop++) //one 0x80 command can keep 0.2us, do 5 times to stay in this situation for 1us
{
OutputBuffer[dwNumBytesToSend++] = '\x80'; // GPIO command for ADBUS
OutputBuffer[dwNumBytesToSend++] = '\xf0'; // set CS low, MOSI and SCL
OutputBuffer[dwNumBytesToSend++] = '\xfb'; // bit3: CS, bit2: MISO, bit1: MOSI, bit0: SCK
}
//send data
OutputBuffer[dwNumBytesToSend++] = MSB_FALLING_EDGE_CLOCK_BYTE_OUT_IN; // 0x11 Write command
OutputBuffer[dwNumBytesToSend++] = (sizeToTransfer - 1); // Length lower byte
OutputBuffer[dwNumBytesToSend++] = (sizeToTransfer - 1) >> 8; // Length higher byte
for (U4 i = 0; i < sizeToTransfer; i++) // size to transfer
{
OutputBuffer[dwNumBytesToSend++] = buffer;
}
//SPI_CSDisable();
for (int loop = 0; loop < 5; loop++) //one 0x80 command can keep 0.2us, do 5 times to stay in this situation for 1us
{
OutputBuffer[dwNumBytesToSend++] = '\x80'; //GPIO command for ADBUS
OutputBuffer[dwNumBytesToSend++] = '\xf8'; //set CS, MOSI and SCL low
OutputBuffer[dwNumBytesToSend++] = '\xfb'; //bit3:CS, bit2:MISO, bit1:MOSI, bit0 : SCK
}
ftStatus = FT_Write(handle, OutputBuffer, dwNumBytesToSend, &sizeTransfered);
dwNumBytesToSend = 0;
ftStatus = FT_Read(handle, inBuffer, sizeToTransfer, &dwNumBytesRead);
sizeTransfered = sizeTransfered ? sizeTransfered - 33 : sizeTransfered;
}
uint32 SPI_FTDI_READ(FT_HANDLE handle, SPI_READBUFFER_pt pReadBuf, uint8* spiData, uint32 size)
{
const uint32 secureSize = MIN(50, size);
uint32 sizeRead;
dwNumBytesSent = 0;
//SPI_Enable();
for (int loop = 0; loop < 5; loop++) //one 0x80 command can keep 0.2us, do 5 times to stay in this situation for 1us
{
OutputBuffer[dwNumBytesToSend++] = '\x80';// GPIO command for ADBUS
OutputBuffer[dwNumBytesToSend++] = '\xf2';// set CS, MOSI and SCL low
OutputBuffer[dwNumBytesToSend++] = '\xfb';// bit3:CS, bit2:MISO, bit1:MOSI, bit0 : SCK
}
//read data
OutputBuffer[dwNumBytesToSend++] = MSB_FALLING_EDGE_CLOCK_BYTE_IN;
OutputBuffer[dwNumBytesToSend++] = (secureSize - 1);
OutputBuffer[dwNumBytesToSend++] = (secureSize - 1) >> 8;
//SPI_CSDisable();
for (int loop = 0; loop < 5; loop++) //one 0x80 command can keep 0.2us, do 5 times to stay in this situation for 1us
{
OutputBuffer[dwNumBytesToSend++] = '\x80';//GPIO command for ADBUS
OutputBuffer[dwNumBytesToSend++] = '\xfa';//set CS, MOSI and SCL low
OutputBuffer[dwNumBytesToSend++] = '\xfb';//bit3:CS, bit2:MISO, bit1:MOSI, bit0 : SCK
}
ftStatus = FT_Write(handle, OutputBuffer, dwNumBytesToSend, &dwNumBytesSent);
dwNumBytesToSend = 0;
ftStatus = FT_Read(handle, spiDataRest, secureSize, &sizeRead);
}