espressif / esp-idf

Espressif IoT Development Framework. Official development framework for Espressif SoCs.
Apache License 2.0
13.84k stars 7.32k forks source link

ADE7963 SPI (IDFGH-13671) #14547

Open stefano055415 opened 2 months ago

stefano055415 commented 2 months ago

I am trying to create a firmware that can read data from ade7953 (current meter) via SPI

//****Object Definition***** ADE7953::ADE7953(int SS, int SPI_freq) { _SS = SS; _SPI_freq = SPI_freq; } //**** //****Initialization**** void ADE7953::initialize() { spi_bus_config_t buscfg = { .mosi_io_num = GPIO_NUM_23, .miso_io_num = GPIO_NUM_19, .sclk_io_num = GPIO_NUM_22, .quadwp_io_num = -1, .quadhd_io_num = -1 , .max_transfer_sz = 32, };

spi_device_interface_config_t devcfg = { .mode = 3, .clock_speed_hz = _SPI_freq, .spics_io_num = _SS, .queue_size = 7, .pre_cb = NULL, .post_cb = NULL};

// Initialize the SPI bus esp_err_t ret = spi_bus_initialize(VSPI_HOST, &buscfg, 1); ESP_ERROR_CHECK(ret);

// Attach the ADE7953 to the SPI bus ret = spi_bus_add_device(VSPI_HOST, &devcfg, &spi); ESP_ERROR_CHECK(ret);

// Configure the CS pin gpio_set_direction((gpio_num_t)_SS, GPIO_MODE_OUTPUT); gpio_set_level((gpio_num_t)_SS, 1); vTaskDelay(pdMS_TO_TICKS(50));

// Enable data transfer by bringing CS line LOW gpio_set_level((gpio_num_t)_SS, 0);

// Send initialization bytes uint8_t data[] = {0x00, 0xFE, WRITE, 0x00, 0xAD, 0x01, 0x20, WRITE, 0x00, 0x30}; spi_transaction_t t; memset(&t, 0, sizeof(t)); t.length = sizeof(data) * 8; t.tx_buffer = data; ret = spi_device_transmit(spi, &t); ESP_ERROR_CHECK(ret);

// Disable data transfer by bringing CS line HIGH gpio_set_level((gpio_num_t)_SS, 1);

// Delay for 100 ms vTaskDelay(pdMS_TO_TICKS(100));

// Initial Start-up Init. Commands spiAlgorithm32_write((functionBitVal(AP_NOLOAD_32, 1)), (functionBitVal(AP_NOLOAD_32, 0)), 0x00, 0x00, 0x00, 0x01); vTaskDelay(pdMS_TO_TICKS(100)); spiAlgorithm8_write((functionBitVal(LCYCMODE_8, 1)), (functionBitVal(LCYCMODE_8, 0)), 0b01111111); vTaskDelay(pdMS_TO_TICKS(100)); spiAlgorithm16_write((functionBitVal(LINECYC_16, 1)), (functionBitVal(LINECYC_16, 0)), 0x00, 0x78); vTaskDelay(pdMS_TO_TICKS(100)); } uint8_t ADE7953::spiAlgorithm8_read(uint8_t MSB, uint8_t LSB) { // Enable data transfer by bringing CS line LOW gpio_set_level((gpio_num_t)_SS, 0);

// Send initialization bytes uint8_t data[] = {MSB, LSB, READ, WRITE, WRITE}; spi_transaction_t t; memset(&t, 0, sizeof(t)); t.length = sizeof(data) * 8; t.tx_buffer = data; t.rxlength = 8; uint8_t rx_data[2] = {0}; t.rx_buffer = rx_data; esp_err_t ret = spi_device_transmit(spi, &t); // Disable data transfer by bringing CS line HIGH gpio_set_level((gpio_num_t)_SS, 1);

if (ret != ESP_OK) { ESP_LOGE(TAG, "SPI transmit failed: %s", esp_err_to_name(ret)); return 0; // or handle error appropriately } ESP_LOGI(TAG, "Received data: %02X %02X", rx_data[1], rx_data[0]);

uint32_t result = rx_data[1]; return result; }

When I try to read any register I always get FF FF

Can someone help me?

Thanks

wanckl commented 1 month ago

@stefano055415 Hi

  1. please confirme ADE7963 have data send when do spi transaction
  2. you add device as not half duplex, spi_device_transmit of your read option is a full duplex transaction, if this chip need send some command then read data, you shouldn't code as this.
  3. transaction with max length 32 byte don't need DMA enable.

thanks, waitting for your good news.