Hi.
I am using a custom board on an nRF52810 microcontroller and a LIS2DH12 accelerometer connected to it via SPI. SDK version 2.7.0.
Here's my settings:
.dts file -->
&spi0 { compatible = "nordic,nrf-spim"; status = "okay"; pinctrl-0 = <&spi0_default>; pinctrl-1 = <&spi0_sleep>; pinctrl-names = "default", "sleep"; cs-gpios = <&gpio0 8 GPIO_ACTIVE_LOW>; lis2dh12: lis2dh12@0{ compatible = "st,lis2dh"; reg = <0>; spi-max-frequency = <10000000>; }; };
Devicetree visual editor screen -->
pinctrl file -->
&pinctrl { spi0_default: spi0_default { group1 { psels = <NRF_PSEL(SPIM_SCK, 0, 9)>, <NRF_PSEL(SPIM_MOSI, 0, 6)>, <NRF_PSEL(SPIM_MISO, 0, 7)>; }; }; spi0_sleep: spi0_sleep { group1 { psels = <NRF_PSEL(SPIM_SCK, 0, 9)>, <NRF_PSEL(SPIM_MOSI, 0, 6)>, <NRF_PSEL(SPIM_MISO, 0, 7)>; low-power-enable; }; }; };
prj.conf -->
# Enable SPI CONFIG_SPI=y
main.c code -->
... #include <zephyr/drivers/spi.h> ... #define SLEEP_TIME_MS 3000 #define SPIOP SPI_WORD_SET(8) | SPI_TRANSFER_MSB struct spi_dt_spec lis2dh12_spi = SPI_DT_SPEC_GET(DT_NODELABEL(lis2dh12), SPIOP, 0); int32_t lis2dh12_read_reg(uint8_t reg, uint8_t *data, uint8_t size) { int ret; if (data == NULL || size == 0) { return -EINVAL; } uint8_t tx_buffer = reg | 0x80; struct spi_buf tx_spi_buf = {.buf = (void *)&tx_buffer, .len = 1}; struct spi_buf_set tx_spi_buf_set = {.buffers = &tx_spi_buf, .count = 1}; uint8_t rx_buffer[size + 1]; struct spi_buf rx_spi_bufs = {.buf = rx_buffer, .len = size + 1}; struct spi_buf_set rx_spi_buf_set = {.buffers = &rx_spi_bufs, .count = 1}; ret = spi_transceive_dt(&lis2dh12_spi, &tx_spi_buf_set, &rx_spi_buf_set); if (ret < 0) { LOG_ERR("spi_transceive_dt() failed, err: %d", ret); return ret; } memcpy(data, rx_buffer + 1, size); return 0; } int main(void) { int ret; uint8_t who_am_i; if (!device_is_ready(lis2dh12_spi.bus)) { printf("SPI bus %s is not ready\n", lis2dh12_spi.bus->name); return 0; } while (1) { // Read register WHO_AM_I ret = lis2dh12_read_reg(0x0F, &who_am_i, 1); if (ret == 0) { LOG_DBG("WHO_AM_I value: 0x%02X", who_am_i); if (who_am_i == 0x33) { // 0x33 - expected value for LIS2DH12 LOG_DBG("LIS2DH12 successfully identified"); } else { LOG_DBG("Unexpected value WHO_AM_I\n"); } } else { LOG_DBG("Error reading WHO_AM_I: %d\n", ret); } k_msleep(SLEEP_TIME_MS); } return 0; }
Terminal output -->
Logic analyzer output -->
As you can see, I get the wrong WHO_AM_I register value when reading. For some reason there is no signal on the SCK line (although there is physical contact between the microcontroller and LIS2DH12). Perhaps I made a mistake in the dts setup or code?
Please help me to solve this problem.
Also I don't understand why in devicetree editor the maximum frequency is 8MHz, although I set it to 10MHz?
Thanks.