Skip to content

I2S sampling freq not correct for 8-bit @ 8 kHz #310

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
andrewjfox opened this issue Mar 2, 2018 · 9 comments
Closed

I2S sampling freq not correct for 8-bit @ 8 kHz #310

andrewjfox opened this issue Mar 2, 2018 · 9 comments

Comments

@andrewjfox
Copy link

andrewjfox commented Mar 2, 2018

Hi,

I've been trying to get audio from a modem using the I2S/PCM interface and having some troubles getting accurate clock frequencies.

I'm trying to read single 16bit words from modem @ 8kHz, by configuring the I2S as 8bit slots, since I see in the library it's expecting stereo so has min 2 slots. Following is code to init device, note that I am adjusting clock polarity and FS width to suit modem.

 I2S.onReceive(ISR_onI2SReceive); 
 
  if(!I2S.begin(I2S_PHILIPS_MODE, 8000, 8)) return false;  
  
  /*  SAMD21 I2S peripheral samples data on +ve clock edge, however modem data is valid on -ve edge
   *  if SAMD is master then can invert output clock, this only changes output, so internal operation is unchanged
   *  modem requires FS to be 1 bit width (in slave mode)
  */
  i2s_disable();
  REG_I2S_CLKCTRL0 &= ~I2S_CLKCTRL_FSWIDTH_Msk;  //clear FS width
  REG_I2S_CLKCTRL0 |= I2S_CLKCTRL_SCKOUTINV | (I2S_CLKCTRL_FSWIDTH_BIT_Val << I2S_CLKCTRL_FSWIDTH_Pos);  //invert clock output, FS 1 bit wide (TDM mode)
  i2s_enable();

For this setup, with 8kHz sample rate I would expect SCLK to be 8000 * 2 * 8 = 128kHz, however when I monitor the I2S lines using logic analyser, the clock is around 400kHz, and FS is around 25kHz. See attached screen capture,
logic_i2s_8khz_8bit

If I have it configured for 8kHz and 16bit data, then clock and frame are at 256kHz and 8kHz resepctively, as expected.

I had a look at the driver code but the clock setting is a bit complex at first glance so wasn't really able to locate where the issue is.

Regards
Andrew

@andrewjfox
Copy link
Author

Hi @sandeepmistry , just bumping this to see if I can get a response, and I think you've been involved in the I2S stuff before.

@andrewjfox
Copy link
Author

Please! Is anyone able to validate that this is a bug in the I2S library?

@sandeepmistry
Copy link
Contributor

The library is fine, I tried the simple tone example with 8 kHz and 16 kHz:

screen shot 2018-03-20 at 11 54 58 am

screen shot 2018-03-20 at 11 56 49 am

Since you made modifications, I suggest you discuss on the forum or create pull request to get your suggestions included in the core.

@andrewjfox
Copy link
Author

Did you read the post! I didn't make modifications to the library. I added an extra call, in my own code, to the registers to change the frame sync bit width. And I didn't say changing sampling freqs didn't work, I clearly stated that changing word width from 16 bits to 8 bits caused problem.

@andrewjfox
Copy link
Author

andrewjfox commented Mar 22, 2018

@sandeepmistry this is not closed.

I try this code,

#include <I2s.h>

#define I2S_SAMPLERATE_HZ     8000
#define I2S_WORD_BITS         8

void setup() {
  I2S.begin(I2S_PHILIPS_MODE, I2S_SAMPLERATE_HZ, I2S_WORD_BITS);  
}

void loop() {
 if(I2S.available()) I2S.read();    
}

and I get following result

image

I haven't modifed library, I only changed bit width to 8 bits in I2S.begin
If you change bit width back to 16 it works as expected.

@sandeepmistry sandeepmistry reopened this Mar 22, 2018
@sandeepmistry
Copy link
Contributor

@andrewjfox thanks for the sketch to reproduce, I can reproduce the problem with it.

Calculations

48000000 / (8 * 2 * 8000) = 375 

is too big to fit in the 8-bit divider value, so gets truncated to 119. If you use 8-bit @ 16kHz or 16-bit @ 8 kHz the issue does not occur. Just 8-bit @ 8 kHz

@sandeepmistry sandeepmistry changed the title I2S sampling freq not correct I2S sampling freq not correct for 8-bit @ 8 kHz Mar 22, 2018
@sandeepmistry
Copy link
Contributor

Please provide your feedback on pull request #317 and let us know if it fixes the sketch from #310 (comment). Thanks.

@andrewjfox
Copy link
Author

Yep, that's fixed it. Thanks for the quick reply.

@sandeepmistry
Copy link
Contributor

Closed via #317.

boseji pushed a commit to go-ut/combined-ArduinoCore-samd that referenced this issue Nov 10, 2021
Add int64_t and uint64_t data types to Serial.print(ln)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants