Before, endstops were checked on every step, wasting precious time.
Checking them 500 times a second should be more than sufficient.
Additionally, an endstop stop now properly decelerates the movement.
This is one important step towards handling accidental endstop hits
gracefully, as it avoids step losses in such situations.
This isn't the magic patch which suddenly allows us to run at
arbitrary high step rates, but can deal with short bursts of
very short delays only. Typical for a 45 deg move when using
ACCELERATION_TEMPORAL.
The implementation simply extends the impossible small delay.
To keep overall timing promises regardless, the extra is stored
and compensated for when a longer delay request comes in.
Wrapped all this in #ifdef ACCELERATION_TEMPORAL, as this adds
about 300 bytes of binary size, so it likely slows down the
setTimer() code a bit and non-temporal algorithms are expected to
never request an unreasonable short delay.
The implementation is slightly different this time, as it's not
using these famous bresenham algorithms. The intention is to
allow axis-independent movements, as it's required for
EMC-quality look-ahead.
This makes the code cleaner and the reduction of code
probably easily compensates for keeping global interrupts
enabled for a bit longer. Talked to macscifi about this.
Saves about 300 bytes of binary size.
if delay is not zero, otherwise the timer is not turned off when it
should be. Move the test and setting back inside the block that is only
executed if delay > 0.
Specifically, disable interrupts just before returning and then enable
the timer interrupt if appropriate. This means that the timer interrupt
cannot actually fire until after the RETI, so the function cannot be
entered recursively.
service routine in the case that the requested timer interval is too
small.
Calling the interrupt service routine at this point is likely to
recursively clobber the stack.
Setting a lower bounds on the interrupt delay will limit the upper
speed of pulse generation, but it should not change the relative
pulse rates, and will not recurvisely clobber the stack.
Note that the lower limit of 17 has not been researched, it is
simply the value below which the old code attempted to call
the interrupt service routine directly.
memory barriers since it is only touched inside a single interrupt
handler or while interrupts are disabled in setTimer().
This saves about 90 bytes since it no longer needs to be reloaded multiple
times.
This costs 2 bytes of ram, but saves 60 bytes of flash. Doing so
also eliminates the need to disable interrupts while clearing flags
in the ifclock macro.
Conflicts:
clock.c
timer.c
timer.h
Doing so adds most of the interrupt execution time to the
step time, see line 126 of the same file:
if (next_step_time == 0) {
// new move, take current time as start value
step_start = TCNT1;
}
The old implementation with an overflow interrupt for the clock and a comparator interrupt for stepping, had an unsolvable bug: If the comparator interrupt should happen very shortly after the overflow interrupt the comparator interrupt would miss. And with 2 comparators the implementation is more straightforward.
After lots of try and error the conclusion was, disabling this
interrupt makes the timer vulnerable to be messed up by
characters incoming over the serial line. So, now the
interrupt is enabled as a move starts and not disabled before
the move, and all subsequent moves are done.