Call dwt_softreset , then can‘t read ID

spi
dwm1000
dw1000
#1

I use stm32l432kc to communicate with dw1000. At first I can read ID, 0xDECA0130. But after calling dwt_softreset in dwt_initialise(DWT_LOADUCODE), I can only read ID, 0xffffffff. Before calling dwt_softreset, I had reduced the SPI rate to very slow, <2MBits/s, which did not feel like a SPI problem.

1 Like

#2

Hi

Are you using a DW1000 or DWM1000?

The device could be still in a sleep mode or did not initialise correctly when trying.

See also section 3 DW1000 INTERFACES (SPI AND GPIOS) in APS022, our debugging application note. Please have a look at our example code /API we have? They can be downloaded from our website : https://www.decawave.com/software/ and is called *DW1000 Application Programming Interface with STM32F10x Application examples
/Leo
*APS022_Debugging_DW1000_based_products_systems_v1.3.pdf (721.0 KB)

0 Likes

#3

Hi leo:
My code is as follows:

reset_DW1000(); /* Target specific drive of RSTn line into DW1000 low for a period. */
port_set_dw1000_slowrate();
osDelay(100);
printf("write data: \r\n");
for(int i=0; i<20; i++) {
	printf("%x ", dataA[i]);
}
dwt_writetodevice(0x21, 0, 20, &dataA[0]);
dwt_readfromdevice(0x21, 0 , 20, &dataB[0]);
printf("\r\n");
if(memcmp(&dataA[0],&dataB[0],20) != 0) {
	printf("spi communcation fail \r\n");
	printf("read data:  \r\n");
	for(int i=0; i<20; i++) {
		printf("%x ", dataB[i]);
	}
	printf("\r\n");
}
else {
	printf("spi communcation success \r\n");
}

log:

write data:
dd 2 1 1 22 87 99 32 55 22 10 11 22 ab cc 30 82 88 99 45
spi communcation fail
read data:
dd 2 1 1 22 87 99 32 55 22 10 11 ab 30 88 45 6d bf fc ff

I write 20 bytes of data, but when I read it, only the first 12 bytes were right and the rest were wrong.
Spi has four modes, all of which I have tried and none of which can be used.And there are three spi modes that read pretty much the same, all of which read ID, except for one mode that doesn’t read ID at all
I read and write after resetting the RSTn pin, so it’s not sleeping.

0 Likes

#4

Hi LEO,
int readfromspi(uint16_t headerLength,
const uint8_t *headerBuffer,
uint32_t readlength,
uint8_t *readBuffer)
{
int i;
decaIrqStatus_t stat ;
stat = decamutexon() ;

/* Blocking: Check whether previous transfer has been finished */
while (HAL_SPI_GetState(&hspi1) != HAL_SPI_STATE_READY);

HAL_GPIO_WritePin(DW_NSS_GPIO_Port, DW_NSS_Pin, GPIO_PIN_RESET); /**< Put chip select line low */

/* Send header */
for(i=0; i<headerLength; i++)
{
    HAL_SPI_Transmit(&hspi1, &headerBuffer[i], 1, HAL_MAX_DELAY); //No timeout
}

/* for the data buffer use LL functions directly as the HAL SPI read function
 * has issue reading single bytes */
while(readlength-- > 0)
{
    /* Wait until TXE flag is set to send data */
    while(__HAL_SPI_GET_FLAG(&hspi1, SPI_FLAG_TXE) == RESET)
    {
    }

    hspi1.Instance->DR = 0; /* set output to 0 (MOSI), this is necessary for
    e.g. when waking up DW1000 from DEEPSLEEP via dwt_spicswakeup() function.
    */

    /* Wait until RXNE flag is set to read data */
    while(__HAL_SPI_GET_FLAG(&hspi1, SPI_FLAG_RXNE) == RESET)
    {
    }

    (*readBuffer++) = hspi1.Instance->DR;  //copy data read form (MISO)
}

HAL_GPIO_WritePin(DW_NSS_GPIO_Port, DW_NSS_Pin, GPIO_PIN_SET); /**< Put chip select line high */

decamutexoff(stat);

return 0;

} // end readfromspi()

Why does the chip selection signal jitter occur in the code that SPI receive, as shown in the following figure?

0 Likes

#5

Hi LEO,
After dw1000 reset, SPI signal is very poor, 20 bytes read-only 12 bytes.


so the SPI acceptance driver function of STM32F103 can not be used directly on stm32l432kc, it needs to be modified before it can be used.
After modification, test with 20 bytes of data, send and receive successfully. And after dw1000 is initialized, SPI signal will also improve.

The modified code CS signal jitter also disappeared.
Modified code:
int readfromspi(uint16_t headerLength,
const uint8_t *headerBuffer,
uint32_t readlength,
uint8_t *readBuffer)
{
int i;
decaIrqStatus_t stat ;
stat = decamutexon() ;
char temp;

/* Blocking: Check whether previous transfer has been finished */
while (HAL_SPI_GetState(&hspi1) != HAL_SPI_STATE_READY);

HAL_GPIO_WritePin(DW_NSS_GPIO_Port, DW_NSS_Pin, GPIO_PIN_RESET); /**< Put chip select line low */

/* Send header */
for(i=0; i<headerLength; i++)
{
    //HAL_SPI_Transmit(&hspi1, &headerBuffer[i], 1, HAL_MAX_DELAY); //No timeout
	HAL_SPI_TransmitReceive(&hspi1, &headerBuffer[i], (uint8_t *)&temp, 1, HAL_MAX_DELAY);
}

/* for the data buffer use LL functions directly as the HAL SPI read function
 * has issue reading single bytes */
HAL_SPI_TransmitReceive(&hspi1, &headerBuffer[i], (uint8_t *)readBuffer, readlength, HAL_MAX_DELAY);

HAL_GPIO_WritePin(DW_NSS_GPIO_Port, DW_NSS_Pin, GPIO_PIN_SET); /**< Put chip select line high */

decamutexoff(stat);

return 0;

} // end readfromspi()

1 Like

#6

I suggest to write 1 to SPI_EDGE bit in the SYS_CFG register at startup.
Just write some default value like 0x00001600 - this may improve SPI read after that.

1 Like

#7

Thank you, your solution is really helpful for me!

0 Likes

#8

Yes. The patch fixed my problem too. However, I saw a problem in this patch:
HAL_SPI_TransmitReceive(&hspi1, &headerBuffer[i], (uint8_t *)readBuffer, readlength, HAL_MAX_DELAY);
It seems we are access out-of-bound in the headerBuffer. However, as this is the transmit buffer, it is not a big problem.

0 Likes