Using I2S on the RP2040 for an ADC.... #1863
-
@pschatzmann , After reading your great success and example to use an RP Pico and Audio Tools to send output to a DAC, I assumed Audio Tools was ready for an ADC and I modified your code so it looks like this:
It builds just fine and appears to work but the results in Audacity look like this:
The PCM1808 can either use 24 or 32 bits, which seems to be more than the USB can handle, so we need to do some shifts to make int32_t r[500] and l[500] into int16_t. It does not handle 16 bits over I2S. I went looking at I2SRP2040.h to see what I should shift things over and saw notes that it only works for TX (to a DAC). It also looked like you made some changes very recently, so I assume you might be working on this now.
I am planning to use this code for my Electronics II class spring quarter this year. Do you recommend I work on modifying the I2SRP2040.h so it works for me, or do you recommend I modify my code below so it uses both cores and gives me good data, or do you suspect you will be working on this and might have it working by the time I need it? |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment 1 reply
-
Why do you think you need to modify the I2SRP2040.h ? My recommendation would be to keep things as simple as possible and if the one core solution is working, stick with that! I think that would be also a great opportunity to show maybe different solutions and ask the students for advantages and disadvantages of each approach. The AudioTools is using the I2S.h so any API should work in the end: I would propose a third solution which would use the data conversion functionality of the AudioTools with something like the follows: AudioInfo infoI2S(44100, 32, 2);
AudioInfo infoUSB(44100,16,2);
I2SStream i2s;
FormatConverterStream converter(i2s);
size_t readCB(uint8_t* data, size_t len, Adafruit_USBD_Audio& ref) {
// provide data in 16 bits
return converter.readBytes(data, size);
}
void setup() {
// setup i2s for 32 bits
auto cfgI2s = i2s.defaultConfig(RX_MODE);
cfgi2s.copyFrom(infoI2S);
i2s.begin(cfgI2S);
// convert from 32 bits to 16
converter.begin(infoI2S, infoUSB);
// setup usb
usb.setReadCallback(readCB);
usb.begin(infoUSB.sample_rate, infoUSB.channels, infoUSB.bits_per_sample);
I personally prefer the shorter more declarative versions because it makes it easier to reason about the code and play with different varients. |
Beta Was this translation helpful? Give feedback.
Why do you think you need to modify the I2SRP2040.h ?
My recommendation would be to keep things as simple as possible and if the one core solution is working, stick with that!
I think that would be also a great opportunity to show maybe different solutions and ask the students for advantages and disadvantages of each approach.
The AudioTools is using the I2S.h so any API should work in the end: I would propose a third solution which would use the data conversion functionality of the AudioTools with something like the follows: