Skip to content

Commit

Permalink
Make waveform generator a NMI to run always, increase accuracy (#5578)
Browse files Browse the repository at this point in the history
* Make waveform generator a NMI to run always

Make the waveform generator an NMI using the same code as in 2.4.0.
Making it NMI will ensure it runs even when interrupts are disabled.

Fixes #5568

* Move to a lockless waveform generator

Make the waveform generator lockless by doing all dangerous structure
updates in the interrupt handler.  start/stopWaveform set a flag and
cause an interrupt.  They wait for the interrupt to complete and clear
those flags before returning.

Also rework the Waveform[] array to be lockless.

* Optimize IRAM and CPU usage in IRQ

Try and minimize the IRAM needed to run the IRQ while keeping performance at
or better than before.

* Avoid WDT errors, optimize pin scans

Calculate first and last pins to scan for PWM, significantly increasing
accuracy for pulses under 10us at 80MHz.  Now if you are using a single
PWM channel at 80MHz you can generate a 1.125us pulse (down from ~4us).

Rework the IRQ logic to avoid potential WDT errors.  When at 80MHz it
appears that interrupts occuring faster than 10us apart on the timer
cause WDT errors.  Avoid it by increasing the minimum delay between
IRQs on the timer accordingly.

* Clean up format/comment, remove delay() in stop

stopWaveform may be called from an interrupt (it's called by digitalWrite)
so we can't call delay().  Make it a busy wait for the IRQ to clear the
waveform.

Only set a new timeout of 10us when starting a new waveform when there
is no other event coming sooner than that.

Update formatting and comments per @devyte's requests.

Replace MicrosecondsToCycles() with standard Arduino call.
  • Loading branch information
earlephilhower authored Jan 11, 2019
1 parent 9515f46 commit 8a64a12
Showing 1 changed file with 180 additions and 194 deletions.
Loading

0 comments on commit 8a64a12

Please sign in to comment.