Multiple multiplexer (4051) sharing the same address, but diferent analog input pin

Hello,
I’m still learning the software and hardware aspect around the daisy. Sorry if it’s an obvious question, but I did not find example of hardware using multiple 4051 mux.

Is it possible to have multiple multiplexer sharing the same 3 pin for the address, and connect the output to different analog input pin?

for the board definition initialisation, will something like this works ?
// POT MUX
adc_cfg[0].InitMux(seed.GetPin(PIN_ADC_POT_MUX1),
8,
seed.GetPin(PIN_MUX_SEL_0),
seed.GetPin(PIN_MUX_SEL_1),
seed.GetPin(PIN_MUX_SEL_2));
adc_cfg[1].InitMux(seed.GetPin(PIN_ADC_POT_MUX2),
8,
seed.GetPin(PIN_MUX_SEL_0),
seed.GetPin(PIN_MUX_SEL_1),
seed.GetPin(PIN_MUX_SEL_2));
adc_cfg[2].InitMux(seed.GetPin(PIN_ADC_POT_MUX3),
8,
seed.GetPin(PIN_MUX_SEL_0),
seed.GetPin(PIN_MUX_SEL_1),
seed.GetPin(PIN_MUX_SEL_2));
seed.adc.Init(adc_cfg, 3);

// Order of pots on the hardware connected to mux.
for(size_t i = 0; i < 24; i+=3)
{
    knob_[i    ].Init(seed.adc.GetMuxPtr(0, i    ), AudioCallbackRate());
    knob_[i+1].Init(seed.adc.GetMuxPtr(1, i+1), AudioCallbackRate());
    knob_[i+2].Init(seed.adc.GetMuxPtr(2, i+2), AudioCallbackRate());
}

thanks

This totally looks like it should work.

For reference, in case you didn’t already see it, here is the ADC Init for the DaisyField (which uses a Mux for the 8 knobs, and has the 4 CVs connected to other inputs). Note that “4” in the Pot Mux Init is hard coded since the first four adc inputs are the CVs.

I have definitely done exactly this on other STM32 hardware before, but I can’t remember off the top of my head if I’ve done it with libdaisy yet. So if something doesn’t work as expect chime back here and I’ll help you get it sorted.

hello @shensley,
thanks for your reply,

I also did this using various µC, but my question was specifically about libdaisy implementation.
it will work if libdaisy is doing something like :
while true {
set mux address for 1st conversion on analog input 1
convert analog value on input 1
set mux address for 1st conversion on analog input 2
process analog value on input 2
etc …
}

but if there is 1 loop for every analog input
while true {
set mux address for 1st conversion on analog input 1
convert analog value on input 1
set mux address for 2st conversion on analog input 1
process analog value on input 1
etc …
} // using interruption on adc1 for the timing

and on the same time
while true {
set mux address for 1st conversion on analog input 2
convert analog value on input 1
set mux address for 2st conversion on analog input 2
process analog value on input 1
etc …
} using interruption on adc2
if the 2 loops are sync, then everything are OK. But if the 2 loop synchronize a bit, then the mux address can change during a conversion and result will be weird.
You can have illusion that it’s working, until it’s gives strange result.

So I want to be 100% sure before making a prototype PCB!

There is no explicit syncing, but the way it’s set up all channels are always processed in the same callback.

It does process the GPIO for each, but advancements are done all at once between conversions.

I actually want to rework the internal callback to work a bit more succinctly and be more efficient when dealing with mux’d channels. Currently when using a mux half of the reads for each channel are thrown away so that the channels can swap without having stop/start the DMA every time.

Here’s the internal callback that happens after the conversion (including all hardware oversampling conversions, etc.)

1 Like

thanks for pointing me the code
ok, I think I understand the way it works. my conclusions are (for future reference):

  • the declaration order of the analog input is not a problem.
  • The mux address will be set 3 times during this callback (if 3 mux are declared). The 1st 2 time will then not be used. That’s not a problem, but if one use something likethis (like in the field) :
    size_t pot_order[KNOB_LAST] = {0, 3, 1, 4, 2, 5, 6, 7};
    then the order will not be the one expected (except for the last channel)
  • Having multiples mux will work as long as all mux have the same amount of input, in order to keep all loop together.

Oh yeah, good catch. In the case of different index-sequences within the ADC there would be a conflict.

I don’t believe it’s possible to configure it that way, though since it increments through the addresses sequentially.

In the case of the field, the reading still happens sequentially (from 0-7). It’s the data organization in the user API that is reordered to be in the expected order.