我有一个嵌入式应用程序,它是读取SD卡上的16位带符号的音频数据,通过8位读取与SPI,所以uint8_t的缓冲区是音频样本的2倍长,然后通过I2S转发它,它想要相同的数据作为16位的值,所以一个int16_t的缓冲区。由于数组中的数据已经是16位的值,但又分成了8位的框,所以我现在希望将该数组作为int16_t数组来处理。这有可能在不复制内容的情况下实现吗?下面是一个例子:
uint8_t i2s_buffer[4096];
/* spi_read performs 8-bit reads, so it reads the first half (MSB)
* of the 16-bit signed audio sample first, then reads the second
* half (LSB)
*/
spi_read(i2s_buffer, sizeof(12s_buffer), address);
/* Now i2s register is 32-bit wide, so takes
* 4 8-bit samples, 2 16-bit samples, etc
* but the width is set to 16-bit signed since the audio sample
* is 16-bit signed, so we want the system to think of the
* values as 16-bit, thus forcing the LRCLK to tick every half-buffer.
*/
i2s_start( <<i2s_buffer but 16 bits at a time as int16_t>> , sizeof((int16_t*)i2s_buffer) / sizeof(int32_t));发布于 2021-02-08 05:24:50
在嵌入式上下文中,有些事情没有受到惩罚,因为您在特定的环境中工作,使用特定的编译器期望特定的结果。只需确保buffer与您想要访问它的数据类型正确对齐,就可以了。
_Alignas(uint16_t) uint8_t buffer[N];
spi_receive_data(buffer, sizeof(buffer));
invert_endianess_if_necessary((uint16_t*)buffer, sizeof(buffer)/sizeof(uint16_t));
i2c_forward_it((uint16_t*)buffer, sizeof(buffer)/sizeof(uint16_t));但是,如果SD卡中存储的数据已经是uint16_t格式(“逻辑上”),那么您实际上是在读取uint16_t,而不是uint8_t。uint8_t是8位的数据类型--它不是“字节”(语义上)。要在C中表示一个“字节”,请使用char、signed char或最多使用unsigned char。因此,您可以从一开始就将数据读取到适当的容器中:
uint16_t buffer[N];
spi_receive_data((unsigned char*)buffer, sizeof(buffer));
invert_endianess_if_necessary(buffer);
invert_endianess_if_necessary(buffer, sizeof(buffer)/sizeof(*buffer));
i2c_forward_it(buffer, sizeof(buffer)/sizeof(*buffer));https://stackoverflow.com/questions/66093014
复制相似问题