MILKV-DUO256 Audio out

Hello,
I am looking to test the built-in codec on duo 256. I’m looking to determine the SNR etc. in order to determine it’s viability for audio development, synthesis and DSP stuff.
Using the Alpine Linux image, I installed ALSA, and configured the ADAC.
aplay test.wav seems to run, but I just hear a steady loud pop from the DAC.
Previous threads mention that this is related to ETH. Reading the threads and blog posts, there seems to be success, but for an external codec (max98357) and it is not clear how to apply this to the internal DAC. Is anyone able to recommend a solution? thank you!

1 Like

Hi @marchingband are you referring to the internal CODEC on the SG2002? That is tuned for telephony. Have you tried Jack as well as ALSA? Any luck with I2S?

Hello @ewp, yes I am referring to the internal CODEC in SG2002. What do you mean by “tuned for telephony”? Does that mean it will not produce good audio?
I have not tried Jack, is that likely to produce different results?
I am not sure what role i2s plays in the system, is there an internal i2s protocol running between the codec and the core? I’m not sure how to test that.

The CODECs listed in the datasheet are used in VoIP, so unsure if they are useful for general audio. Jack is good for low-latency real-time audio and might resolve your audio issues. It will cope with jitter well. I2S can be used to transfer digital audio to or from the core – leaving the core to just do DSP stuff, and using external ADC and DAC.

@ewp thanks, I am specifically interested in the internal DAC, this is the reason for my inquiry. I will try jack, but it appears to just use ALSA under the hood.
this thread documents how the ETH peripheral is confusingly interacting with the Audio Out pin. My experience matches this description, where I hear periodic pops (bursts of high-speed data), so I believe there is some configuration that needs to be modified, but I am unable to determine quite what, based on the thread 【i2s】Milk-V Duo添加speaker——max98357a解码器驱动 - #58 by LangZhao

If Jack needs to use the ALSA backend, then don’t use it for now since it’s just another layer of complexity. The thread concerns MAX98357A which is an I2S DAC (class-D). It’s not clear if there was any success with cv182xadac which I believe is your preference. The thread details crosstalk from Ethernet, so the MAC and PHY were disabled. Try that next?

@ewp thanks so much
I assume that this code snippet refers to the device tree.
I have used find to search through the files on my device for any .dts files, and searched everywhere, but I do not see any. Am I able to change the device tree from the command line on the duo? Or do i need to recompile? Again I am running the Alpine image. Thank you for your help, I do appreciate it!

Yes. You will need to recompile/relink the FSBL and U-Boot only, you can keep your Alpine root filesystem. Look under build/boards for the dts – they are there. Also check your PINMUX in cvi_board_init.c.

The internal DAC on the Duo can be used and does not conflict with the ETH pins - it is output on the same pin as the blue “breathe” LED. You need to enable the internal DAC drivers in the kernel configuration and device tree and you need to disable the LED flash script as described in Duo documentation, then you need to connect a wire to the LED GPIO pin prior to the MOSFET driver transistor.

@emeb thanks for your response. I was under the impression that this LED thing was true for the DUO, but not for the DUO256, I have the 256 … am I mistaken in that?

You’re right - on the Duo 256 the audio output is brought out to pin 34 of the board edge connector and is not on the LED.

@emeb @ewp here is the result I am seeing, maybe there is a clue?

aplay -l returns:

**** List of PLAYBACK Hardware Devices ****
card 1: cv182xadac [cv182xa_dac], device 0: cviteka-dac 300a000.dac-0 [cviteka-dac 300a000.dac-0]
  Subdevices: 1/1
  Subdevice #0: subdevice #0

aplay -D hw:1,0 test_tone.wav returns:

Playing WAVE 'test_tone.wav' : [ 1369.311102] cvitek-i2s 4130000.i2s: Audio system clk=22579200, sample rate=44100
Signed 16 bit Little Endian, Rate 44100 Hz, Mono
aplay: pcm_write:2178: write error: I/O error
[ 1379.606286] cvi_i2s_shutdown not start *dai = 0000000063cbf505, *dai->playback_dma_data = 00000000e4cb5b13

dmesg is:

x_base(FO) cv180x_sys(FO) cv180x_pwm(FO)
[  359.398671] CPU: 0 PID: 1676 Comm: aplay Tainted: GF     D    O      5.10.4-tag- #1
[  359.406580] epc: ffffffe0005623e0 ra : ffffffe0005623de sp : ffffffe000fcbc80
[  359.413950]  gp : ffffffe000893158 tp : ffffffe001d2b5c0 t0 : 0000000000080000
[  359.421408]  t1 : 00000000003c0000 t2 : 0000000000000001 s0 : 0000000000000001
[  359.428867]  s1 : ffffffe0013f1490 a0 : fffffffffffffff4 a1 : 000000000000003f
[  359.436326]  a2 : 000000000040003f a3 : 0000000000000001 a4 : ffffffe000a331e0
[  359.443784]  a5 : fffffffffffffffe a6 : ffffffe00f8e9808 a7 : 0000000000080001
[  359.451243]  s2 : ffffffe00118be00 s3 : 0000000000000001 s4 : ffffffe001201018
[  359.458702]  s5 : ffffffe001210058 s6 : 0000003fe90147f0 s7 : ffffffe00118be00
[  359.466161]  s8 : ffffffe002866800 s9 : 0000000000000003 s10: 0000000000000002
[  359.473619]  s11: 0000000000005624 t3 : 000000000003c000 t4 : 840083c000000040
[  359.481077]  t5 : 800083c000000040 t6 : 0000000000000004
[  359.486563] status: 0000000200000100 badaddr: 000000000000000c cause: 000000000000000d
[  359.494737] Call Trace:
[  359.497282] [<ffffffe0005623e0>] snd_dmaengine_pcm_trigger+0x92/0xee
[  359.503856] [<ffffffe00056b06e>] snd_soc_pcm_component_trigger+0x48/0x72
[  359.510785] [<ffffffe00056b66a>] soc_pcm_trigger+0x30/0x78
[  359.516461] [<ffffffe00055b722>] snd_pcm_action_single+0x24/0x4c
[  359.522674] [<ffffffe00055ce1c>] snd_pcm_action+0x42/0x48
[  359.528260] [<ffffffe00055ea52>] snd_pcm_ioctl+0x56c/0xa1a
[  359.533936] [<ffffffe000296d44>] handle_mm_fault+0x702/0x758
[  359.539791] [<ffffffe0002bd188>] ioctl_file_clone+0x7c/0x80
[  359.545550] [<ffffffe0002bcda4>] vfs_ioctl+0xc/0x22
[  359.550593] [<ffffffe0002bd188>] ioctl_file_clone+0x7c/0x80
[  359.556352] [<ffffffe0002bd23a>] sys_ioctl+0xae/0x538
[  359.561583] [<ffffffe00022ace0>] do_page_fault+0x22c/0x2da
[  359.567257] [<ffffffe0002bd188>] ioctl_file_clone+0x7c/0x80
[  359.573024] [<ffffffe00022805e>] check_syscall_nr+0x1e/0x22
[  359.578872] ---[ end trace 4a526c7eb76383ac ]---
[  359.583676] note: aplay[1676] exited with preempt_count 1
[  359.593464] cvi_i2s_shutdown not start *dai = 0000000063cbf505, *dai->playback_dma_data = 00000000e4cb5b13
[  521.680865] cvitekadac 300a000.dac: dac_reg_read reg:0,ret:0x0.
[  521.687079] cvitekadac 300a000.dac: dac_reg_read reg:0,ret:0x0.
[  521.693313] cvitekadac 300a000.dac: dac_reg_read reg:0,ret:0x0.
[  521.699487] cvitekadac 300a000.dac: dac_reg_read reg:0,ret:0x0.
[  528.792196] cvitekadac 300a000.dac: Get DAC Vol reg:16,ret:0xff00ff temp_lval=16.
[  528.800020] cvitekadac 300a000.dac: dac_reg_read reg:16,ret:0x100010.
[  528.806738] cvitekadac 300a000.dac: Get DAC Vol reg:16,ret:0xff00ff temp_lval=16.
[  528.814509] cvitekadac 300a000.dac: dac_reg_read reg:16,ret:0x100010.
[  528.821256] cvitekadac 300a000.dac: Get DAC Vol reg:16,ret:0xff00ff temp_lval=16.
[  528.829026] cvitekadac 300a000.dac: dac_reg_read reg:16,ret:0x100010.
[  528.835709] cvitekadac 300a000.dac: Get DAC Vol reg:16,ret:0xff00ff temp_lval=16.
[  528.843465] cvitekadac 300a000.dac: dac_reg_read reg:16,ret:0x100010.
[  537.687570] cvitekadac 300a000.dac: dac_reg_read reg:40,ret:0x0.
[  537.693875] cvitekadac 300a000.dac: dac_reg_read reg:40,ret:0x0.
[  537.700198] cvitekadac 300a000.dac: dac_reg_read reg:40,ret:0x0.
[  537.706461] cvitekadac 300a000.dac: dac_reg_read reg:40,ret:0x0.
[  754.509236] cvi_i2s_shutdown not start *dai = 0000000063cbf505, *dai->playback_dma_data = 00000000e4cb5b13
[  774.239169] cvi_i2s_shutdown not start *dai = 0000000063cbf505, *dai->playback_dma_data = 00000000e4cb5b13
[  783.802985] cvitek-i2s 4130000.i2s: Audio system clk=22579200, sample rate=44100
[  794.185975] cvi_i2s_shutdown not start *dai = 0000000063cbf505, *dai->playback_dma_data = 00000000e4cb5b13
[  811.608496] cvitek-i2s 4130000.i2s: Audio system clk=22579200, sample rate=44100
[  821.830351] cvi_i2s_shutdown not start *dai = 0000000063cbf505, *dai->playback_dma_data = 00000000e4cb5b13
[  921.467628] cvitek-i2s 4130000.i2s: Audio system clk=22579200, sample rate=44100
[  931.644619] cvi_i2s_shutdown not start *dai = 0000000063cbf505, *dai->playback_dma_data = 00000000e4cb5b13
[ 1124.479101] cvitek-i2s 4130000.i2s: Audio system clk=22579200, sample rate=44100
[ 1134.633809] cvi_i2s_shutdown not start *dai = 0000000063cbf505, *dai->playback_dma_data = 00000000e4cb5b13```

I’ve seen that kind of failure sometimes on my Duo 64 when using aplay. It’s not consistent - mostly it works fine, sometimes it fails like that.

@emeb hmm I have only seen it fail so far.
Looking at the logs, does it seems like the DAC is initialized right?
Is there any external circuitry needed? I am just going directly into an amplifier.
Looking at the output pin with my logic analyzer, it is just high, and doesn’t move.

The logs don’t look wrong - they’re very similar to what I see on my Duo 64 when playing audio files. I can’t speak to the details initializing the audio output pin on the Duo 256 - on the 64 I haven’t had to do anything in particular except to prevent the GPIO blink script from running.

@emeb thanks.
I added a series cap, and the audio is a bit clearer, I can hear things kindof change when I run aplay.
There is a constant loud pop about 2x per second, and a tiny bit of noise between that modulates a little when I run the script, sometimes the timing of the pops changes a little with the script as well.
On my board, the LED is not flashing, and the script doesn’t exist (I’m using an Alpine image that another user posted). It certainly “sounds” like an LED blink script … around the same speed as the LED blink. I wonder is something weird is going on with that GPIO and the script is running somehow, but for the wrong GPIO?

@Spiritdude @cwt any ideas what might be affecting the DAC output, in this Alpine image?