Go back to using software interrupt to load next move so that X axis still works
authorJoseph Coffland <joseph@cauldrondevelopment.com>
Wed, 23 Mar 2016 10:19:08 +0000 (03:19 -0700)
committerJoseph Coffland <joseph@cauldrondevelopment.com>
Wed, 23 Mar 2016 10:19:08 +0000 (03:19 -0700)
src/motor.c
src/stepper.c

index 51e92ec1282c3c55d36f837106b3f0eb05a1ae94..fa4ad17c17fbb397c65372b8827359ff8b8810da 100644 (file)
@@ -262,37 +262,36 @@ void motor_prep_move(int motor, uint32_t seg_clocks, float travel_steps,
   // a negative bias in the uint32_t conversion that results in long-term
   // negative drift.
   uint16_t steps = round(fabs(travel_steps));
-  uint32_t ticks_per_step = seg_clocks / (steps + 0.5);
+  // TODO why do we need to multiply by 2 here?
+  uint32_t ticks_per_step = seg_clocks / (steps + 0.5) * 2;
 
   // Find the clock rate that will fit the required number of steps
-  if (ticks_per_step & 0xffff8000UL) {
+  if (ticks_per_step & 0xffff0000UL) {
     ticks_per_step /= 2;
     seg_clocks /= 2;
 
-    if (ticks_per_step & 0xffff8000UL) {
+    if (ticks_per_step & 0xffff0000UL) {
       ticks_per_step /= 2;
       seg_clocks /= 2;
 
-      if (ticks_per_step & 0xffff8000UL) {
+      if (ticks_per_step & 0xffff0000UL) {
         ticks_per_step /= 2;
         seg_clocks /= 2;
 
-        if (ticks_per_step & 0xffff8000UL) m->timer_clock = 0; // Off
+        if (ticks_per_step & 0xffff0000UL) m->timer_clock = 0; // Off
         else m->timer_clock = TC_CLKSEL_DIV8_gc;
       } else m->timer_clock = TC_CLKSEL_DIV4_gc;
     } else m->timer_clock = TC_CLKSEL_DIV2_gc;
   } else m->timer_clock = TC_CLKSEL_DIV1_gc;
 
-  m->timer_period = ticks_per_step * 2;   // TODO why do we need x2 here?
+  m->timer_period = ticks_per_step;
   m->steps = seg_clocks / ticks_per_step; // Compute actual steps
 
   // Setup the direction, compensating for polarity.
-  if (0 <= travel_steps) // positive direction
-    m->direction = DIRECTION_CW ^ m->polarity;
-
+  if (0 <= travel_steps) m->direction = DIRECTION_CW ^ m->polarity;
   else {
     m->direction = DIRECTION_CCW ^ m->polarity;
-    m->steps = -m->steps;
+    m->steps *= -1;
   }
 }
 
index c7f49357e180a28b0c6a7bc3967ed45626335c5c..8d380bf68a47e2035b2685e4e0bb0cc08e9599e3 100644 (file)
@@ -68,6 +68,13 @@ void stepper_init() {
 uint8_t st_runtime_isbusy() {return st.busy;}
 
 
+/// Interrupt handler for calling move exec function.
+/// ADC channel 0 triggered by load ISR as a "software" interrupt.
+ISR(ADCB_CH0_vect) {
+  mp_exec_move();
+}
+
+
 /// Step timer interrupt routine
 /// Dequeue move and load into stepper struct
 ISR(STEP_TIMER_ISR) {
@@ -85,8 +92,6 @@ ISR(STEP_TIMER_ISR) {
   // If there are no more moves
   if (!st.move_ready) {
     TIMER_STEP.PER = STEP_TIMER_POLL;
-
-    sei(); // Enable interupts
     mp_exec_move();
     return;
   }
@@ -122,9 +127,9 @@ ISR(STEP_TIMER_ISR) {
   st.prep_dwell = 0; // clear dwell
   st.move_ready = false;  // flip the flag back
 
-  // Exec and prep next move
-  sei(); // Enable interupts
-  mp_exec_move();
+  // Use ADC as a "software" interrupt to prep next move
+  ADCB_CH0_INTCTRL = ADC_CH_INTLVL_LO_gc; // trigger LO interrupt
+  ADCB_CTRLA = ADC_ENABLE_bm | ADC_CH0START_bm;
 }