Closed jmdodd95682 closed 4 months ago
Dear @jmdodd95682, Thanks for the useful analysis and measurements! Could you please create a PR with your proposed solution? I'll take a look at it. Thanks
Sure. I can do this.
okay I submitted a PR. I renamed the functions to ready()
and start()
. I also added a function called clear()
to the AdvancedADC
. I found cases where when starting the ADC capture the DMA would (for some unknown reason) think it already had DMA Buffers in the read queue. Running clear()
after ready()
and before start()
fixes this issue.
AdvancedADC
gives you two options for capturing two analog signals simultaneously. The first is to bind both analog input pins to the sameAdvancedADC
instance. This works great, but sadly, means your sample rate is cut in half. Thesample_rate
provided applies to the sampling of both inputs. So a 1M Samp./sec rate really means each is sampled at 500K Samp./sec. If you trying to push the limits of sample rate, this is not a great solution.The second way is to bind each analog input to a different
AdvancedADC
. The library will automatically assign the two pins to two different ADC blocks. The sample rate of each will be maximum. Very nice. However, this creates another problem. Thebegin()
routine takes approximately 100 us on GIGA R1 to initialize and start the ADC capture. So if I say something like:What happens is that the second ADC input capture is delayed by about 100us. So the two signals are not synchronized. If you're trying to capture two signals with reasonable synchronization, that is not going to work. I analyzed the timing of each line of code in the
begin()
routine and found that two lines are causing almost all the delay:https://github.com/arduino-libraries/Arduino_AdvancedAnalog/blob/f7d081c4a56f1a87f8b4a9f027f2efb2b4174b7c/src/AdvancedADC.cpp#L187
and
https://github.com/arduino-libraries/Arduino_AdvancedAnalog/blob/f7d081c4a56f1a87f8b4a9f027f2efb2b4174b7c/src/AdvancedADC.cpp#L200-L202
I have a solution. I created two new routines in
AdvancedADC.cpp
I callload()
andfire()
.load()
is identical to thebegin()
routine up to a point, including the long-delay lines above. It then returns. Essentiallyload()
allocates the DMA and ADC etc, but does not start the capture. Thefire()
routine (which only takes about 4 us) does the rest of what was inbegin()
and starts the capture. This is working and providing a synchronization error of about 4-6 us. Not bad.This is probably NOT the solution that someone else would prefer, but it works for me. Now I have full sample-rate and okay synchronization between two or three analog inputs.
I guess I would say the issue I have is that
begin()
takes too long (106 us!). Either this needs to be shortened significantly or the idea of theload()
andfire()
would also work.