I managed to continue my code, he it is:
Code: Select all
#include <stdint.h>
#include <stdlib.h>
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "driver/i2s_std.h"
#include "driver/gpio.h"
#include "esp_check.h"
#include "sdkconfig.h"
#define BUFFER_SIZE 2048
static i2s_chan_handle_t rx_chan; // I2S RX channel handler
static void i2s_read_task(void *args)
{
uint8_t *r_buf = (uint8_t *)calloc(1, BUFFER_SIZE);
assert(r_buf); // Check if the r_buf allocation was successful
size_t r_bytes = 0;
// Enable the RX channel
ESP_ERROR_CHECK(i2s_channel_enable(rx_chan));
while (1)
{
// Read I2S data
if (i2s_channel_read(rx_chan, r_buf, BUFFER_SIZE, &r_bytes, 1000) == ESP_OK)
{
printf("Read Task: i2s read %zu bytes\n-----------------------------------\n", r_bytes);
// Print the buffer as samples
const uint32_t *samples = (const uint32_t *)r_buf;
int num_samples = r_bytes / sizeof(uint32_t);
// Print the 32-bit samples and their 18-bit versions
for (int i = 0; i < num_samples; i++)
{
uint32_t sample = samples[i];
// Print the original 32-bit sample bit by bit
printf("Original 32-bit Sample: ");
for (int bit = 31; bit >= 0; bit--)
{
printf("%ld", (sample >> bit) & 1);
}
printf("\n");
// Trim the last 14 bits
uint32_t trimmed_sample = (sample >> 14) & 0x3FFFF; // Trim the last 14 bits and keep the lower 18 bits
// Print the trimmed 18-bit sample bit by bit
printf("Trimmed 18-bit Sample: ");
for (int bit = 17; bit >= 0; bit--)
{
printf("%ld", (trimmed_sample >> bit) & 1);
}
printf("\n");
}
}
else
{
printf("Read Task: i2s read failed\n");
}
vTaskDelay(pdMS_TO_TICKS(200));
}
free(r_buf);
vTaskDelete(NULL);
}
static void i2s_init_sph0645lm4h(void)
{
// I2S channel configuration
i2s_chan_config_t chan_cfg = I2S_CHANNEL_DEFAULT_CONFIG(I2S_NUM_AUTO, I2S_ROLE_MASTER);
ESP_ERROR_CHECK(i2s_new_channel(&chan_cfg, NULL, &rx_chan));
// I2S standard configuration
i2s_std_config_t std_cfg = {
.clk_cfg = {
.sample_rate_hz = 48000,
.clk_src = I2S_CLK_SRC_DEFAULT,
.mclk_multiple = I2S_MCLK_MULTIPLE_256,
},
// Philips or standard configuration
//.slot_cfg = I2S_STD_MSB_SLOT_DEFAULT_CONFIG(I2S_DATA_BIT_WIDTH_32BIT, I2S_SLOT_MODE_MONO),
.slot_cfg = I2S_STD_PHILIPS_SLOT_DEFAULT_CONFIG(I2S_DATA_BIT_WIDTH_32BIT, I2S_SLOT_MODE_MONO),
.gpio_cfg = {
.mclk = I2S_GPIO_UNUSED,
.bclk = GPIO_NUM_4,
.ws = GPIO_NUM_5,
.dout = I2S_GPIO_UNUSED, // Only read, no write
.din = GPIO_NUM_19,
.invert_flags = {
.mclk_inv = false,
.bclk_inv = false,
.ws_inv = false,
},
},
};
std_cfg.slot_cfg.slot_mask = I2S_STD_SLOT_LEFT;
ESP_ERROR_CHECK(i2s_channel_init_std_mode(rx_chan, &std_cfg));
}
void app_main(void)
{
// I2S initialization
i2s_init_sph0645lm4h();
// Task creation
xTaskCreate(i2s_read_task, "i2s_read_task", 4096, NULL, 5, NULL);
}
But I don't know how to proceed further.
How can I decode the I2s communication ?
And do I have to use two's complement transformation on my trimmed_sample ?
Also here is an output of my code:
Code: Select all
Original 32-bit Sample:111101010011000100 00000000000000
Trimmed 18-bit Sample: 111101010011000100
Original 32-bit Sample:111101010010111000 00000000000000
Trimmed 18-bit Sample: 111101010010111000
Reading the datasheet of my mic, it seems okey.
(
https://www.knowles.com/docs/default-so ... asheet.pdf)
Figure 7 shows, that from the 18th bit the data stream should be only zeros, and that's the case here.