瀏覽代碼

Merge pull request #5829 from thinkyhead/rc_fix_isr_reentry

Combine fixes for LIN_ADVANCE and temperature ISR
Scott Lahteine 8 年之前
父節點
當前提交
c04d6b5aa6
共有 4 個檔案被更改,包括 62 行新增18 行删除
  1. 37
    6
      Marlin/planner.cpp
  2. 13
    11
      Marlin/stepper.cpp
  3. 10
    1
      Marlin/temperature.cpp
  4. 2
    0
      Marlin/temperature.h

+ 37
- 6
Marlin/planner.cpp 查看文件

672
   #endif
672
   #endif
673
 
673
 
674
   #if ENABLED(LIN_ADVANCE)
674
   #if ENABLED(LIN_ADVANCE)
675
-    const float target_float[XYZE] = { a, b, c, e },
676
-                de_float = target_float[E_AXIS] - position_float[E_AXIS],
677
-                mm_D_float = sqrt(sq(target_float[X_AXIS] - position_float[X_AXIS]) + sq(target_float[Y_AXIS] - position_float[Y_AXIS]));
678
-
679
-    memcpy(position_float, target_float, sizeof(position_float));
675
+    const float mm_D_float = sqrt(sq(a - position_float[X_AXIS]) + sq(b - position_float[Y_AXIS]));
680
   #endif
676
   #endif
681
 
677
 
682
   const long da = target[X_AXIS] - position[X_AXIS],
678
   const long da = target[X_AXIS] - position[X_AXIS],
707
   //*/
703
   //*/
708
 
704
 
709
   // DRYRUN ignores all temperature constraints and assures that the extruder is instantly satisfied
705
   // DRYRUN ignores all temperature constraints and assures that the extruder is instantly satisfied
710
-  if (DEBUGGING(DRYRUN)) position[E_AXIS] = target[E_AXIS];
706
+  if (DEBUGGING(DRYRUN)) {
707
+    position[E_AXIS] = target[E_AXIS];
708
+    #if ENABLED(LIN_ADVANCE)
709
+      position_float[E_AXIS] = e;
710
+    #endif
711
+  }
711
 
712
 
712
   long de = target[E_AXIS] - position[E_AXIS];
713
   long de = target[E_AXIS] - position[E_AXIS];
713
 
714
 
715
+  #if ENABLED(LIN_ADVANCE)
716
+    float de_float = e - position_float[E_AXIS];
717
+  #endif
718
+
714
   #if ENABLED(PREVENT_COLD_EXTRUSION)
719
   #if ENABLED(PREVENT_COLD_EXTRUSION)
715
     if (de) {
720
     if (de) {
716
       if (thermalManager.tooColdToExtrude(extruder)) {
721
       if (thermalManager.tooColdToExtrude(extruder)) {
717
         position[E_AXIS] = target[E_AXIS]; // Behave as if the move really took place, but ignore E part
722
         position[E_AXIS] = target[E_AXIS]; // Behave as if the move really took place, but ignore E part
718
         de = 0; // no difference
723
         de = 0; // no difference
724
+        #if ENABLED(LIN_ADVANCE)
725
+          position_float[E_AXIS] = e;
726
+          de_float = 0;
727
+        #endif
719
         SERIAL_ECHO_START;
728
         SERIAL_ECHO_START;
720
         SERIAL_ECHOLNPGM(MSG_ERR_COLD_EXTRUDE_STOP);
729
         SERIAL_ECHOLNPGM(MSG_ERR_COLD_EXTRUDE_STOP);
721
       }
730
       }
723
         if (labs(de) > (int32_t)axis_steps_per_mm[E_AXIS_N] * (EXTRUDE_MAXLENGTH)) { // It's not important to get max. extrusion length in a precision < 1mm, so save some cycles and cast to int
732
         if (labs(de) > (int32_t)axis_steps_per_mm[E_AXIS_N] * (EXTRUDE_MAXLENGTH)) { // It's not important to get max. extrusion length in a precision < 1mm, so save some cycles and cast to int
724
           position[E_AXIS] = target[E_AXIS]; // Behave as if the move really took place, but ignore E part
733
           position[E_AXIS] = target[E_AXIS]; // Behave as if the move really took place, but ignore E part
725
           de = 0; // no difference
734
           de = 0; // no difference
735
+          #if ENABLED(LIN_ADVANCE)
736
+            position_float[E_AXIS] = e;
737
+            de_float = 0;
738
+          #endif
726
           SERIAL_ECHO_START;
739
           SERIAL_ECHO_START;
727
           SERIAL_ECHOLNPGM(MSG_ERR_LONG_EXTRUDE_STOP);
740
           SERIAL_ECHOLNPGM(MSG_ERR_LONG_EXTRUDE_STOP);
728
         }
741
         }
1342
 
1355
 
1343
   // Update the position (only when a move was queued)
1356
   // Update the position (only when a move was queued)
1344
   memcpy(position, target, sizeof(position));
1357
   memcpy(position, target, sizeof(position));
1358
+  #if ENABLED(LIN_ADVANCE)
1359
+    position_float[X_AXIS] = a;
1360
+    position_float[Y_AXIS] = b;
1361
+    position_float[Z_AXIS] = c;
1362
+    position_float[E_AXIS] = e;
1363
+  #endif
1345
 
1364
 
1346
   recalculate();
1365
   recalculate();
1347
 
1366
 
1367
        nb = position[Y_AXIS] = lround(b * axis_steps_per_mm[Y_AXIS]),
1386
        nb = position[Y_AXIS] = lround(b * axis_steps_per_mm[Y_AXIS]),
1368
        nc = position[Z_AXIS] = lround(c * axis_steps_per_mm[Z_AXIS]),
1387
        nc = position[Z_AXIS] = lround(c * axis_steps_per_mm[Z_AXIS]),
1369
        ne = position[E_AXIS] = lround(e * axis_steps_per_mm[_EINDEX]);
1388
        ne = position[E_AXIS] = lround(e * axis_steps_per_mm[_EINDEX]);
1389
+  #if ENABLED(LIN_ADVANCE)
1390
+    position_float[X_AXIS] = a;
1391
+    position_float[Y_AXIS] = b;
1392
+    position_float[Z_AXIS] = c;
1393
+    position_float[E_AXIS] = e;
1394
+  #endif
1370
   stepper.set_position(na, nb, nc, ne);
1395
   stepper.set_position(na, nb, nc, ne);
1371
   previous_nominal_speed = 0.0; // Resets planner junction speeds. Assumes start from rest.
1396
   previous_nominal_speed = 0.0; // Resets planner junction speeds. Assumes start from rest.
1372
   ZERO(previous_speed);
1397
   ZERO(previous_speed);
1392
  */
1417
  */
1393
 void Planner::sync_from_steppers() {
1418
 void Planner::sync_from_steppers() {
1394
   LOOP_XYZE(i) position[i] = stepper.position((AxisEnum)i);
1419
   LOOP_XYZE(i) position[i] = stepper.position((AxisEnum)i);
1420
+  #if ENABLED(LIN_ADVANCE)
1421
+    LOOP_XYZE(i) position_float[i] = stepper.position((AxisEnum)i) * steps_to_mm[i];
1422
+  #endif
1395
 }
1423
 }
1396
 
1424
 
1397
 /**
1425
 /**
1405
     const uint8_t axis_index = axis;
1433
     const uint8_t axis_index = axis;
1406
   #endif
1434
   #endif
1407
   position[axis] = lround(v * axis_steps_per_mm[axis_index]);
1435
   position[axis] = lround(v * axis_steps_per_mm[axis_index]);
1436
+  #if ENABLED(LIN_ADVANCE)
1437
+    position_float[axis] = v;
1438
+  #endif
1408
   stepper.set_position(axis, v);
1439
   stepper.set_position(axis, v);
1409
   previous_speed[axis] = 0.0;
1440
   previous_speed[axis] = 0.0;
1410
 }
1441
 }

+ 13
- 11
Marlin/stepper.cpp 查看文件

342
   #endif
342
   #endif
343
 }
343
 }
344
 
344
 
345
-void Stepper::isr() {
346
-  #define _ENABLE_ISRs() cli(); SBI(TIMSK0, OCIE0B); ENABLE_STEPPER_DRIVER_INTERRUPT()
345
+#define _ENABLE_ISRs() do { cli(); if (thermalManager.in_temp_isr) CBI(TIMSK0, OCIE0B); else SBI(TIMSK0, OCIE0B); ENABLE_STEPPER_DRIVER_INTERRUPT(); } while(0)
347
 
346
 
348
-  uint16_t timer, remainder, ocr_val;
347
+void Stepper::isr() {
349
 
348
 
350
   static uint32_t step_remaining = 0;
349
   static uint32_t step_remaining = 0;
351
 
350
 
351
+  uint16_t ocr_val;
352
+
352
   #define ENDSTOP_NOMINAL_OCR_VAL 3000    // check endstops every 1.5ms to guarantee two stepper ISRs within 5ms for BLTouch
353
   #define ENDSTOP_NOMINAL_OCR_VAL 3000    // check endstops every 1.5ms to guarantee two stepper ISRs within 5ms for BLTouch
353
   #define OCR_VAL_TOLERANCE 1000          // First max delay is 2.0ms, last min delay is 0.5ms, all others 1.5ms
354
   #define OCR_VAL_TOLERANCE 1000          // First max delay is 2.0ms, last min delay is 0.5ms, all others 1.5ms
354
 
355
 
366
     #define SPLIT(L) do { \
367
     #define SPLIT(L) do { \
367
       _SPLIT(L); \
368
       _SPLIT(L); \
368
       if (ENDSTOPS_ENABLED && L > ENDSTOP_NOMINAL_OCR_VAL) { \
369
       if (ENDSTOPS_ENABLED && L > ENDSTOP_NOMINAL_OCR_VAL) { \
369
-        remainder = (uint16_t)L % (ENDSTOP_NOMINAL_OCR_VAL); \
370
+        uint16_t remainder = (uint16_t)L % (ENDSTOP_NOMINAL_OCR_VAL); \
370
         ocr_val = (remainder < OCR_VAL_TOLERANCE) ? ENDSTOP_NOMINAL_OCR_VAL + remainder : ENDSTOP_NOMINAL_OCR_VAL; \
371
         ocr_val = (remainder < OCR_VAL_TOLERANCE) ? ENDSTOP_NOMINAL_OCR_VAL + remainder : ENDSTOP_NOMINAL_OCR_VAL; \
371
         step_remaining = (uint16_t)L - ocr_val; \
372
         step_remaining = (uint16_t)L - ocr_val; \
372
       } \
373
       } \
374
 
375
 
375
     if (step_remaining && ENDSTOPS_ENABLED) {   // Just check endstops - not yet time for a step
376
     if (step_remaining && ENDSTOPS_ENABLED) {   // Just check endstops - not yet time for a step
376
       endstops.update();
377
       endstops.update();
377
-      ocr_val = step_remaining;
378
       if (step_remaining > ENDSTOP_NOMINAL_OCR_VAL) {
378
       if (step_remaining > ENDSTOP_NOMINAL_OCR_VAL) {
379
-        step_remaining = step_remaining - ENDSTOP_NOMINAL_OCR_VAL;
379
+        step_remaining -= ENDSTOP_NOMINAL_OCR_VAL;
380
         ocr_val = ENDSTOP_NOMINAL_OCR_VAL;
380
         ocr_val = ENDSTOP_NOMINAL_OCR_VAL;
381
       }
381
       }
382
-      else step_remaining = 0;  //  last one before the ISR that does the step
383
-      _NEXT_ISR(ocr_val);  //
382
+      else {
383
+        ocr_val = step_remaining;
384
+        step_remaining = 0;  //  last one before the ISR that does the step
385
+      }
386
+
387
+      _NEXT_ISR(ocr_val);
384
 
388
 
385
       NOLESS(OCR1A, TCNT1 + 16);
389
       NOLESS(OCR1A, TCNT1 + 16);
386
 
390
 
867
     NOLESS(OCR1A, TCNT1 + 16);
871
     NOLESS(OCR1A, TCNT1 + 16);
868
 
872
 
869
     // Restore original ISR settings
873
     // Restore original ISR settings
870
-    cli();
871
-    SBI(TIMSK0, OCIE0B);
872
-    ENABLE_STEPPER_DRIVER_INTERRUPT();
874
+    _ENABLE_ISRs();
873
   }
875
   }
874
 
876
 
875
 #endif // ADVANCE or LIN_ADVANCE
877
 #endif // ADVANCE or LIN_ADVANCE

+ 10
- 1
Marlin/temperature.cpp 查看文件

1483
  */
1483
  */
1484
 ISR(TIMER0_COMPB_vect) { Temperature::isr(); }
1484
 ISR(TIMER0_COMPB_vect) { Temperature::isr(); }
1485
 
1485
 
1486
+volatile bool Temperature::in_temp_isr = false;
1487
+
1486
 void Temperature::isr() {
1488
 void Temperature::isr() {
1487
-  //Allow UART and stepper ISRs
1489
+  // The stepper ISR can interrupt this ISR. When it does it re-enables this ISR
1490
+  // at the end of its run, potentially causing re-entry. This flag prevents it.
1491
+  if (in_temp_isr) return;
1492
+  in_temp_isr = true;
1493
+  
1494
+  // Allow UART and stepper ISRs
1488
   CBI(TIMSK0, OCIE0B); //Disable Temperature ISR
1495
   CBI(TIMSK0, OCIE0B); //Disable Temperature ISR
1489
   sei();
1496
   sei();
1490
 
1497
 
1949
     }
1956
     }
1950
   #endif
1957
   #endif
1951
 
1958
 
1959
+  cli();
1960
+  in_temp_isr = false;
1952
   SBI(TIMSK0, OCIE0B); //re-enable Temperature ISR
1961
   SBI(TIMSK0, OCIE0B); //re-enable Temperature ISR
1953
 }
1962
 }

+ 2
- 0
Marlin/temperature.h 查看文件

61
                  current_temperature_bed_raw,
61
                  current_temperature_bed_raw,
62
                  target_temperature_bed;
62
                  target_temperature_bed;
63
 
63
 
64
+    static volatile bool in_temp_isr;
65
+
64
     #if ENABLED(TEMP_SENSOR_1_AS_REDUNDANT)
66
     #if ENABLED(TEMP_SENSOR_1_AS_REDUNDANT)
65
       static float redundant_temperature;
67
       static float redundant_temperature;
66
     #endif
68
     #endif

Loading…
取消
儲存