// Switch settings. See switch.c
#define SWITCH_INTLVL PORT_INT0LVL_MED_gc
-#define SW_LOCKOUT_TICKS 250 // ms
-#define SW_DEGLITCH_TICKS 30 // ms
// Motor ISRs
#define CHORDAL_TOLERANCE 0.01 // chordal accuracy for arcs
#define JUNCTION_DEVIATION 0.05 // default value, in mm
#define JUNCTION_ACCELERATION 100000 // centripetal corner accel
-#define JOG_JERK_MULT 1 // Jogging jerk multipler
#define JOG_MIN_VELOCITY 10 // mm/min
#define CAL_ACCELERATION 500000 // mm/min^2
#define CURRENT_SENSE_RESISTOR 0.05 // ohms
\******************************************************************************/
-/* Normally open switches (NO) trigger an interrupt on the
- * falling edge and lockout subsequent interrupts for the defined
- * lockout period. This approach beats doing debouncing as an
- * integration as switches fire immediately.
- *
- * Normally closed switches (NC) trigger an interrupt on the
- * rising edge and lockout subsequent interrupts for the defined
- * lockout period.
- *
- * These functions interact with each other to process switch closures
- * and firing. Each switch has a counter which is initially set to
- * negative SW_DEGLITCH_TICKS. When a switch closure is DETECTED the
- * count increments for each RTC tick. When the count reaches zero
- * the switch is tripped and action occurs. The counter continues to
- * increment positive until the lockout is exceeded.
- */
-
#include "switch.h"
#include "config.h"
#include <stdbool.h>
-typedef enum {
- SW_IDLE,
- SW_DEGLITCHING,
- SW_LOCKOUT
-} switch_debounce_t;
-
-
typedef struct {
uint8_t pin;
switch_type_t type;
switch_callback_t cb;
bool state;
- switch_debounce_t debounce;
- int16_t count;
+ bool triggered;
} switch_t;
};
-static bool _read_state(const switch_t *s) {
- return IN_PIN(s->pin);
-}
+static bool _read_state(const switch_t *s) {return IN_PIN(s->pin);}
static void _switch_isr() {
for (int i = 0; i < SWITCHES; i++) {
switch_t *s = &switches[i];
- bool state = _read_state(s);
-
- if (state == s->state || s->type == SW_DISABLED) continue;
-
- s->debounce = SW_DEGLITCHING;
- s->count = -SW_DEGLITCH_TICKS; // reset deglitch count
- s->state = state;
- PORT(s->pin)->INT0MASK &= ~BM(s->pin); // Disable INT0
+ if (s->type == SW_DISABLED || s->triggered) continue;
+ s->triggered = _read_state(s) != s->state;
+ if (s->triggered) PORT(s->pin)->INT0MASK &= ~BM(s->pin); // Disable INT0
}
}
void _switch_enable(switch_t *s, bool enable) {
if (enable) {
- PORT(s->pin)->INT0MASK |= BM(s->pin); // Enable INT0
+ s->triggered = false;
s->state = _read_state(s); // Initialize state
- s->debounce = SW_IDLE;
+ PORT(s->pin)->INT0MASK |= BM(s->pin); // Enable INT0
} else PORT(s->pin)->INT0MASK &= ~BM(s->pin); // Disable INT0
}
for (int i = 0; i < SWITCHES; i++) {
switch_t *s = &switches[i];
- if (s->type == SW_DISABLED || s->debounce == SW_IDLE) continue;
-
- // state is either lockout or deglitching
- if (++s->count == SW_LOCKOUT_TICKS) {
- PORT(s->pin)->INT0MASK |= BM(s->pin); // Reenable INT0
- bool state = _read_state(s);
- s->debounce = SW_IDLE;
+ if (s->type == SW_DISABLED || !s->triggered) continue;
- // check if the state has changed while we were in lockout
- if (s->state != state) {
- s->state = state;
- s->debounce = SW_DEGLITCHING;
- s->count = -SW_DEGLITCH_TICKS;
- }
-
- continue;
- }
+ bool state = _read_state(s);
+ s->triggered = false;
+ PORT(s->pin)->INT0MASK |= BM(s->pin); // Reenable INT0
- if (!s->count) { // switch triggered
- s->debounce = SW_LOCKOUT;
+ if (state != s->state) {
+ s->state = state;
if (s->cb) s->cb(i, switch_is_active(i));
}
}