Estoy intentando establecer una interfaz con el TLE5012B (hoja de datos ) utilizando SPI. El maestro en este caso es un Nucleo F411RE, que utiliza un procesador STM32F4. El sensor se comunica en palabras de 16 bits, así que configuro el chip en Cube como se muestra (algunos otros periféricos que no se utilizarán en el código de esta pregunta también están activados):
Parecíaquetodoibabien,perosurgióunproblemacuandonotéqueSCLKhabíaregistradounapalabraadicionalcuandonoserecibíanadadelalíneadedatos,loquedabacomoresultadounpícaro0x0000
sealmacenaenelbúfer,loquedesordenalaslecturasfuturas.
Aquíestámicódigo:
#include"app_main.h"
#include "stm32f4xx_hal.h"
#include <stdint.h>
extern SPI_HandleTypeDef hspi2;
uint16_t command = 0x8088;
uint16_t safety = 0;
uint16_t data1[8];
int app_main()
{
HAL_Delay(1000);
HAL_GPIO_WritePin(GPIOB, GPIO_PIN_10, GPIO_PIN_RESET);
HAL_Delay(1);
HAL_SPI_Transmit(&hspi2, (uint8_t *)(&command), 1, 0xFF);
HAL_SPI_Receive(&hspi2, (uint8_t*)data1, 8, 0xFF);
HAL_SPI_Receive(&hspi2, (uint8_t *)(&safety), 1, 0xFF);
HAL_GPIO_WritePin(GPIOB, GPIO_PIN_10, GPIO_PIN_SET);
HAL_Delay(1);
while (1) {
}
return 0;
}
Y esto es lo que sucede en el SPI, leer usando un analizador lógico (las líneas en orden descendente son CS, MOSI / DATA, SCLK, CS cae bajo / se establece alto fuera del área ampliada):
Comosepuedeverenelcódigo,deberíaesperarenviarunapalabrayrecibir8másunapalabradeseguridad;sinembargo,seestánsincronizando10palabras,conelúltimo0x0000
debidoaquenohaydatosenlalínea,queluegopermanecebajadurantealgúntiempo.
Paratenerunamejorideadeloqueestabapasando,modifiquéligeramentemicódigo:
#include"app_main.h"
#include "stm32f4xx_hal.h"
#include <stdint.h>
extern SPI_HandleTypeDef hspi2;
uint16_t command = 0x8088;
uint16_t safety = 0;
uint16_t data1[8];
int app_main()
{
HAL_Delay(1000);
HAL_GPIO_WritePin(GPIOB, GPIO_PIN_10, GPIO_PIN_RESET);
HAL_Delay(105);
HAL_SPI_Transmit(&hspi2, (uint8_t *)(&command), 1, 0xFF);
HAL_Delay(75);
for(int i = 0; i < 8; i++)
{
HAL_Delay(15);
HAL_SPI_Receive(&hspi2, (uint8_t*)&data1[i*2], 1, 0xFF);
}
HAL_Delay(50);
HAL_SPI_Receive(&hspi2, (uint8_t *)(&safety), 1, 0xFF);
HAL_Delay(10);
HAL_GPIO_WritePin(GPIOB, GPIO_PIN_10, GPIO_PIN_SET);
while (1) {
}
return 0;
}
Esto produjo el siguiente resultado:
Desdeladistancia,estoparececorrecto;8palabrasrecibidasdevuelta,máslaseguridad.Alacercarse,sinembargo,elproblemasehacevisible;latransmisióndelcomandoestábien:
Sinembargo,laprimerapalabrarecibidanoesunapalabra,sinodosgrabadasalavezporSCLK:
Mientrasquelassiguientespalabrasestánbien:
Loquepareceestarhaciendoestadoblepalabraesempujarelbúferderecepciónantesdeloquerealmenteseestáleyendo,esdecir,cuandolapalabradeseguridaddebeleerse,seagrega0x0000
albúfer,yaquelapalabradeseguridadyarecibidoyalmacenado.
Podría valer la pena notar que algunos de los retrasos son un poco más pequeños / grandes de lo que deberían ser, pero mi pregunta es, ¿qué podría estar causando que se lea esta palabra doble? Intenté cambiar el periférico SPI al modo de 8 bits en lugar de 16; esto no solucionó el problema, simplemente hizo que la palabra adicional fuera de 8 bits en lugar de 16. Ejecutar un código similar en un procesador F3 también dio resultados incorrectos. El TLE no puede conducir la línea SCLK, por lo que debe ser el micro que está haciendo algo mal, pero no puedo, por mi vida, averiguar qué.
EDITAR: Hice algunos problemas con los cables y configuré el STM en dúplex completo con una resistencia en la línea MOSI. Esto solucionó el problema, pero no me dice qué lo causó en primer lugar. ¿Half-duplex tiene algún protocolo extraño que no conozco?