Porting XMOS USB 2.0 audio ref to custom hardware

If you have a simple question and just want an answer.
__BriKs__
Active Member
Posts: 39
Joined: Tue Nov 27, 2018 9:45 pm

Porting XMOS USB 2.0 audio ref to custom hardware

Postby __BriKs__ » Mon Jun 22, 2020 8:52 pm

Hello,

I'm prototyping an power amplifier with integrated DAC with XMOS XUF208-256-TQ64.
My custom pcba works, I can flash XUF208 and USB is working also (hid mouse exemple works).

Now I use AN00129 to port the USB 2.0 audio reference software to my design.
The port I did, following AN00129, builds and XCORE USB 2.0 as a sound card is detected by windows when I start the custom pcba.
But no sound :)

I designed the harware following the xCORE-200 multichannel audio platform shematic with a XUF208 instead of XE216 and with a TI PCM1792A Dac instead of CS4384. The clocking sheme is similar to audio platform (with PL611 as main oscillator and a CS2100 for spdif without asrc).

My wishes are:
simple stereo DAC with only PCM support, up to 24b/192khz
-a USB input (UAC 2.0)
-a spdif input
-a way to tell XUF208 stream USB or stream SPDIF input

For now I focus on USB. You can see shematics attached.

DAC PCM1792A start by default with 24 bits I2S format.

You can find my full project as attached files and also the pin mapping.


Then I investigate with the scope (I'm a hw guy) and founds following clocks:
MCLK_XCORE and AUDIO_CLK are 22.5792Mhz, looks great
DAC_LRCLK is 44.1Khz (?)
DAC_BCLK is 2.8Mhz (my scope isn't accurate enaugh to get exact value); looks great
DAC_DATA is always low level

My schematic differe from the audio ref platform especielly for I2C bus to configure DAC and CS2100.

Now I think I d'ont need to configure TI DAC but I've a question here:
how can I define ports for I2C regarding my project (based upon AN00129) ? In XN files I write the lines:
<Port Location="XS1_PORT_4C" Name="PORT_I2C"/>
<Port Location="XS1_PORT_4D" Name="PORT_I2C"/>
because I2C_SCL is XOD14 and I2C_SDA is XOD16 but I don't found where I can define these inside project, can you show me where these ports are defined ?

I have the same question for low speed GPIO like: DAC_RESET, PLL_SELECT and MCLK_FSEL, I see inside file in projet gpio_access.h some ports definitions but I didn't found where the port is defined ? I want to use P8C or P4E&P4F but I didn't understand where I write this is port P8C or P4E/P4F

And a last question: is the audio reference software platform designed for I2S 24b format dac or I need to reconfigure my DAC as 24B left or right justified ?

I'm looking inside projects, inside module, but really I didn't find such basic stuff for port and gpio definition, can anybody helps?

Best Regards,

Flo
You do not have the required permissions to view the files attached to this post.
__BriKs__
Active Member
Posts: 39
Joined: Tue Nov 27, 2018 9:45 pm

Postby __BriKs__ » Mon Jun 22, 2020 9:07 pm

Edit: when I play music on the XCORE USB 2.0 device on windows I see the bitstream on DAC_DATA
The others parts of the amp works, I have an analog line which works great

I feel I'm not far to make it working but without configuring I2C, or basic GPIO looks normal it didn't work (also I guess I have to change my dac configuration to other mode than I2S)
__BriKs__
Active Member
Posts: 39
Joined: Tue Nov 27, 2018 9:45 pm

Postby __BriKs__ » Tue Jun 23, 2020 9:19 pm

Hello,

I'm looking more accurately on signals; I think the XMOS is working good as streaming USB and feed correctly my DAC;
I see bit datastream on DAC_DATA, I see right clocks on others pins (BCLK is 2.8Mhz when playing@44.1Khz, 12Mhz when playing@192Khz, LRCLK switch correctly to 44.1,48,192K when playing these datarates, and AUDIO_CLK switch correctly to 22.5 or 24.5 Mhz when changing bitrate).
The reset of the DAC is correctly driven by XMOS (I use same low speed GPIO mapping than xCORE 200 audio plateforme) just like MCLK_FSEL and PLL_SELECT.
I understand that these GPIO are mapped internaly (in audio framework) to P8C.

But still not sound from DAC ! PCM1792A is supposed to be configured as I2S 24b format by default after a reset, so should works.

And also can someone explain me how to configure I2C ports ?
I have SCL on P4C0 and SDA on P4D0, when using this line inside audiohw.xc:
#ifndef IAP
/* If IAP not enabled, i2c ports not declared - still needs for DAC config */
on tile [0] : struct r_i2c r_i2c = {XS1_PORT_4C, XS1_PORT_4D};
#else
extern struct r_i2c r_i2c;
#endif

And add following lines on .xn files:
<Port Location="XS1_PORT_4C" Name="PORT_I2C"/>
<Port Location="XS1_PORT_4D" Name="PORT_I2C"/>

I see with scope than only SCL line works, SDA is still not working, this looks normal as I din't correctly configure I2C ports (when building a warning told me struct r_i2c is not correct). But how to configure I2C ports with audio framework ?
User avatar
mon2
XCore Legend
Posts: 1813
Joined: Thu Jun 10, 2010 11:43 am

Postby mon2 » Wed Jun 24, 2020 4:56 am

Hi.

I believe that the r_i2c struct contains 3 parameters. The last (missing) parameter is the I2C Clock speed. Try with a value of 1000.

Code: Select all

#ifndef IAP
/* If IAP not enabled, i2c ports not declared - still needs for DAC config */
on tile [0] : struct r_i2c r_i2c = {XS1_PORT_4C, XS1_PORT_4D, 1000};
#else
extern struct r_i2c r_i2c;
#endif
See section 3.3 of the attached document for reference.
I2C-Software-Component-_Documentation_X7033A.pdf
You do not have the required permissions to view the files attached to this post.
__BriKs__
Active Member
Posts: 39
Joined: Tue Nov 27, 2018 9:45 pm

Postby __BriKs__ » Wed Jun 24, 2020 8:56 pm

Hello,

I understand reading the framework code that the i2c module used is the framework is the single port type.
I guessI have to modify the audiohw.xc to use the simple i2c module instead.

Anyway my dac should works because I2S from Xmos seems correct, then I will first made working the dac before investigating on i2c (Normaly after a reset the dac is in I2S 24b format this is what is expected from audio framework I think).
MaximLiadov
Active Member
Posts: 35
Joined: Mon Apr 16, 2018 9:14 am

Postby MaximLiadov » Thu Jun 25, 2020 11:40 am

That's not correct.

<Port Location="XS1_PORT_4C" Name="PORT_I2C"/>
<Port Location="XS1_PORT_4D" Name="PORT_I2C"/>

PORT_I2C is just an alias to make souce code look readable. Name means nothing. If you have two I2C ports, correct way:

<Port Location="XS1_PORT_4C" Name="PORT_I2C_1"/>
<Port Location="XS1_PORT_4D" Name="PORT_I2C_2"/>

Name could be whatever you like. PORT_MICKEY_MOUSE. Doesn't matter. But it should be unique for sure. If you have just one I2C bus, you need just one 4-bit port declaration. First two bits will be I2C bus by default. I use I2C library only, so cannot help you with I2C module. Just look at any 4-bit example in any Application Notes.
MaximLiadov
Active Member
Posts: 35
Joined: Mon Apr 16, 2018 9:14 am

Postby MaximLiadov » Thu Jun 25, 2020 11:53 am

"really I didn't find such basic stuff for port and gpio definition, can anybody helps?"

To be honest. Official source codes are not ideal. It contains very old style port handling, for XS1 architecture compatibility, that should be avoided when possible. So that's why you see no documentation, but it works anyway.
__BriKs__
Active Member
Posts: 39
Joined: Tue Nov 27, 2018 9:45 pm

Postby __BriKs__ » Mon Jul 20, 2020 6:41 pm

Hello,

For those newbies guys like me, below the way to use IC with different ports for Xmos USB audio framework.
USB audio framework use library singleport for I2C which is expected to be used with a single port.
To use different port the key is to use instead the library simple port.
This require to modify the file audiohw.xc and to include i2c.h '#include "i2c.h"'.
Remove from makefile module_i2c_single and module_i2c_shared use instead module_i2c_simple.
After change the function call relative to i2c in audiohw.c, because function call is different between single library and simple library, for exemple:

#define DAC_REGWRITE(reg, val) {data[0] = val; i2c_master_write_reg(CS4384_I2C_ADDR, reg, data, 1, r_i2c);}
#define DAC_REGREAD(reg, val) {i2c_master_read_reg(CS4384_I2C_ADDR, reg, val, 1, r_i2c);}
#define ADC_REGWRITE(reg, val) {data[0] = val; i2c_master_write_reg(CS5368_I2C_ADDR, reg, data, 1, r_i2c);}

and add in audiohw.c following definitions:

#ifndef IAP
/* If IAP not enabled, i2c ports not declared - still needs for DAC config */
on tile [0] : struct r_i2c r_i2c = {
XS1_PORT_4C,
XS1_PORT_4D,
};
#else
extern struct r_i2c r_i2c;
#endif

My custom hw use ports 4C0 and 4D0 as SCL and SDA.
Last I have to add module_locks inside makefile I guess was called by other i2c module (shared or single) and now with simple was not called.

Finally I2C works :)

Who is online

Users browsing this forum: No registered users and 2 guests