Quellcode durchsuchen

Merge pull request #8721 from thinkyhead/bf1_better_reverse_pass

[1.1.x] Improved Planner::reverse_pass
Scott Lahteine vor 7 Jahren
Ursprung
Commit
4f465c2d07
Es ist kein Account mit der E-Mail-Adresse des Committers verbunden
3 geänderte Dateien mit 47 neuen und 43 gelöschten Zeilen
  1. 23
    28
      Marlin/planner.cpp
  2. 22
    13
      Marlin/planner.h
  3. 2
    2
      Marlin/ubl.h

+ 23
- 28
Marlin/planner.cpp Datei anzeigen

@@ -247,7 +247,7 @@ void Planner::calculate_trapezoid_for_block(block_t* const block, const float &e
247 247
 
248 248
 
249 249
 // The kernel called by recalculate() when scanning the plan from last to first entry.
250
-void Planner::reverse_pass_kernel(block_t* const current, const block_t *next) {
250
+void Planner::reverse_pass_kernel(block_t* const current, const block_t * const next) {
251 251
   if (!current || !next) return;
252 252
   // If entry speed is already at the maximum entry speed, no need to recheck. Block is cruising.
253 253
   // If not, block in state of acceleration or deceleration. Reset entry speed to maximum and
@@ -268,31 +268,25 @@ void Planner::reverse_pass_kernel(block_t* const current, const block_t *next) {
268 268
  * Once in reverse and once forward. This implements the reverse pass.
269 269
  */
270 270
 void Planner::reverse_pass() {
271
-
272 271
   if (movesplanned() > 3) {
273
-
274
-    block_t* block[3] = { NULL, NULL, NULL };
275
-
276
-    // Make a local copy of block_buffer_tail, because the interrupt can alter it
277
-    // Is a critical section REALLY needed for a single byte change?
278
-    //CRITICAL_SECTION_START;
279
-    uint8_t tail = block_buffer_tail;
280
-    //CRITICAL_SECTION_END
281
-
282
-    uint8_t b = BLOCK_MOD(block_buffer_head - 3);
283
-    while (b != tail) {
284
-      if (block[0] && TEST(block[0]->flag, BLOCK_BIT_START_FROM_FULL_HALT)) break;
285
-      b = prev_block_index(b);
286
-      block[2] = block[1];
287
-      block[1] = block[0];
288
-      block[0] = &block_buffer[b];
289
-      reverse_pass_kernel(block[1], block[2]);
290
-    }
272
+    const uint8_t endnr = BLOCK_MOD(block_buffer_tail + 2); // tail is running. tail+1 shouldn't be altered because it's connected to the running block.
273
+                                                            // tail+2 because the index is not yet advanced when checked
274
+    uint8_t blocknr = prev_block_index(block_buffer_head);
275
+    block_t* current = &block_buffer[blocknr];
276
+
277
+    do {
278
+      const block_t * const next = current;
279
+      blocknr = prev_block_index(blocknr);
280
+      current = &block_buffer[blocknr];
281
+      if (TEST(current->flag, BLOCK_BIT_START_FROM_FULL_HALT)) // Up to this every block is already optimized.
282
+        break;
283
+      reverse_pass_kernel(current, next);
284
+    } while (blocknr != endnr);
291 285
   }
292 286
 }
293 287
 
294 288
 // The kernel called by recalculate() when scanning the plan from first to last entry.
295
-void Planner::forward_pass_kernel(const block_t* previous, block_t* const current) {
289
+void Planner::forward_pass_kernel(const block_t * const previous, block_t* const current) {
296 290
   if (!previous) return;
297 291
 
298 292
   // If the previous block is an acceleration block, but it is not long enough to complete the
@@ -344,8 +338,8 @@ void Planner::recalculate_trapezoids() {
344 338
       // Recalculate if current block entry or exit junction speed has changed.
345 339
       if (TEST(current->flag, BLOCK_BIT_RECALCULATE) || TEST(next->flag, BLOCK_BIT_RECALCULATE)) {
346 340
         // NOTE: Entry and exit factors always > 0 by all previous logic operations.
347
-        float nom = current->nominal_speed;
348
-        calculate_trapezoid_for_block(current, current->entry_speed / nom, next->entry_speed / nom);
341
+        const float nomr = 1.0 / current->nominal_speed;
342
+        calculate_trapezoid_for_block(current, current->entry_speed * nomr, next->entry_speed * nomr);
349 343
         CBI(current->flag, BLOCK_BIT_RECALCULATE); // Reset current only to ensure next trapezoid is computed
350 344
       }
351 345
     }
@@ -353,8 +347,8 @@ void Planner::recalculate_trapezoids() {
353 347
   }
354 348
   // Last/newest block in buffer. Exit speed is set with MINIMUM_PLANNER_SPEED. Always recalculated.
355 349
   if (next) {
356
-    float nom = next->nominal_speed;
357
-    calculate_trapezoid_for_block(next, next->entry_speed / nom, (MINIMUM_PLANNER_SPEED) / nom);
350
+    const float nomr = 1.0 / next->nominal_speed;
351
+    calculate_trapezoid_for_block(next, next->entry_speed * nomr, (MINIMUM_PLANNER_SPEED) * nomr);
358 352
     CBI(next->flag, BLOCK_BIT_RECALCULATE);
359 353
   }
360 354
 }
@@ -1009,7 +1003,7 @@ void Planner::_buffer_steps(const int32_t (&target)[XYZE], float fr_mm_s, const
1009 1003
       #endif
1010 1004
     );
1011 1005
   }
1012
-  float inverse_millimeters = 1.0 / block->millimeters;  // Inverse millimeters to remove multiple divides
1006
+  const float inverse_millimeters = 1.0 / block->millimeters;  // Inverse millimeters to remove multiple divides
1013 1007
 
1014 1008
   // Calculate inverse time for this move. No divide by zero due to previous checks.
1015 1009
   // Example: At 120mm/s a 60mm move takes 0.5s. So this will give 2.0.
@@ -1048,7 +1042,7 @@ void Planner::_buffer_steps(const int32_t (&target)[XYZE], float fr_mm_s, const
1048 1042
     //FMM update ring buffer used for delay with filament measurements
1049 1043
     if (extruder == FILAMENT_SENSOR_EXTRUDER_NUM && filwidth_delay_index[1] >= 0) {  //only for extruder with filament sensor and if ring buffer is initialized
1050 1044
 
1051
-      const int MMD_CM = MAX_MEASUREMENT_DELAY + 1, MMD_MM = MMD_CM * 10;
1045
+      constexpr int MMD_CM = MAX_MEASUREMENT_DELAY + 1, MMD_MM = MMD_CM * 10;
1052 1046
 
1053 1047
       // increment counters with next move in e axis
1054 1048
       filwidth_e_count += delta_mm[E_AXIS];
@@ -1345,7 +1339,8 @@ void Planner::_buffer_steps(const int32_t (&target)[XYZE], float fr_mm_s, const
1345 1339
 
1346 1340
   #endif // LIN_ADVANCE
1347 1341
 
1348
-  calculate_trapezoid_for_block(block, block->entry_speed / block->nominal_speed, safe_speed / block->nominal_speed);
1342
+  const float bnsr = 1.0 / block->nominal_speed;
1343
+  calculate_trapezoid_for_block(block, block->entry_speed * bnsr, safe_speed * bnsr);
1349 1344
 
1350 1345
   // Move buffer head
1351 1346
   block_buffer_head = next_buffer_head;

+ 22
- 13
Marlin/planner.h Datei anzeigen

@@ -130,21 +130,30 @@ typedef struct {
130 130
 #define BLOCK_MOD(n) ((n)&(BLOCK_BUFFER_SIZE-1))
131 131
 
132 132
 class Planner {
133
-
134 133
   public:
135 134
 
136 135
     /**
137
-     * A ring buffer of moves described in steps
136
+     * The move buffer, calculated in stepper steps
137
+     *
138
+     * block_buffer is a ring buffer...
139
+     *
140
+     *             head,tail : indexes for write,read
141
+     *            head==tail : the buffer is empty
142
+     *            head!=tail : blocks are in the buffer
143
+     *   head==(tail-1)%size : the buffer is full
144
+     *
145
+     *  Writer of head is Planner::_buffer_line().
146
+     *  Reader of tail is Stepper::isr(). Always consider tail busy / read-only
138 147
      */
139 148
     static block_t block_buffer[BLOCK_BUFFER_SIZE];
140
-    static volatile uint8_t block_buffer_head,  // Index of the next block to be pushed
141
-                            block_buffer_tail;
149
+    static volatile uint8_t block_buffer_head,      // Index of the next block to be pushed
150
+                            block_buffer_tail;      // Index of the busy block, if any
142 151
 
143 152
     #if ENABLED(DISTINCT_E_FACTORS)
144
-      static uint8_t last_extruder;             // Respond to extruder change
153
+      static uint8_t last_extruder;                 // Respond to extruder change
145 154
     #endif
146 155
 
147
-    static int16_t flow_percentage[EXTRUDERS]; // Extrusion factor for each extruder
156
+    static int16_t flow_percentage[EXTRUDERS];      // Extrusion factor for each extruder
148 157
 
149 158
     static float e_factor[EXTRUDERS],               // The flow percentage and volumetric multiplier combine to scale E movement
150 159
                  filament_size[EXTRUDERS],          // diameter of filament (in millimeters), typically around 1.75 or 2.85, 0 disables the volumetric calculations for the extruder
@@ -152,7 +161,7 @@ class Planner {
152 161
                  volumetric_multiplier[EXTRUDERS];  // Reciprocal of cross-sectional area of filament (in mm^2). Pre-calculated to reduce computation in the planner
153 162
                                                     // May be auto-adjusted by a filament width sensor
154 163
 
155
-    static float max_feedrate_mm_s[XYZE_N],     // Max speeds in mm per second
164
+    static float max_feedrate_mm_s[XYZE_N],         // Max speeds in mm per second
156 165
                  axis_steps_per_mm[XYZE_N],
157 166
                  steps_to_mm[XYZE_N];
158 167
     static uint32_t max_acceleration_steps_per_s2[XYZE_N],
@@ -273,9 +282,9 @@ class Planner {
273 282
     /**
274 283
      * Number of moves currently in the planner
275 284
      */
276
-    static uint8_t movesplanned() { return BLOCK_MOD(block_buffer_head - block_buffer_tail + BLOCK_BUFFER_SIZE); }
285
+    FORCE_INLINE static uint8_t movesplanned() { return BLOCK_MOD(block_buffer_head - block_buffer_tail + BLOCK_BUFFER_SIZE); }
277 286
 
278
-    static bool is_full() { return (block_buffer_tail == BLOCK_MOD(block_buffer_head + 1)); }
287
+    FORCE_INLINE static bool is_full() { return block_buffer_tail == next_block_index(block_buffer_head); }
279 288
 
280 289
     // Update multipliers based on new diameter measurements
281 290
     static void calculate_volumetric_multipliers();
@@ -529,8 +538,8 @@ class Planner {
529 538
     /**
530 539
      * Get the index of the next / previous block in the ring buffer
531 540
      */
532
-    static int8_t next_block_index(const int8_t block_index) { return BLOCK_MOD(block_index + 1); }
533
-    static int8_t prev_block_index(const int8_t block_index) { return BLOCK_MOD(block_index - 1); }
541
+    static constexpr int8_t next_block_index(const int8_t block_index) { return BLOCK_MOD(block_index + 1); }
542
+    static constexpr int8_t prev_block_index(const int8_t block_index) { return BLOCK_MOD(block_index - 1); }
534 543
 
535 544
     /**
536 545
      * Calculate the distance (not time) it takes to accelerate
@@ -565,8 +574,8 @@ class Planner {
565 574
 
566 575
     static void calculate_trapezoid_for_block(block_t* const block, const float &entry_factor, const float &exit_factor);
567 576
 
568
-    static void reverse_pass_kernel(block_t* const current, const block_t *next);
569
-    static void forward_pass_kernel(const block_t *previous, block_t* const current);
577
+    static void reverse_pass_kernel(block_t* const current, const block_t * const next);
578
+    static void forward_pass_kernel(const block_t * const previous, block_t* const current);
570 579
 
571 580
     static void reverse_pass();
572 581
     static void forward_pass();

+ 2
- 2
Marlin/ubl.h Datei anzeigen

@@ -222,7 +222,7 @@
222 222
                     z1 = z_values[x1_i][yi];
223 223
 
224 224
         return z1 + xratio * (z_values[min(x1_i, GRID_MAX_POINTS_X - 2) + 1][yi] - z1); // Don't allow x1_i+1 to be past the end of the array
225
-                                                                                        // If it is, it is clamped to the last element of the 
225
+                                                                                        // If it is, it is clamped to the last element of the
226 226
                                                                                         // z_values[][] array and no correction is applied.
227 227
       }
228 228
 
@@ -248,7 +248,7 @@
248 248
                     z1 = z_values[xi][y1_i];
249 249
 
250 250
         return z1 + yratio * (z_values[xi][min(y1_i, GRID_MAX_POINTS_Y - 2) + 1] - z1); // Don't allow y1_i+1 to be past the end of the array
251
-                                                                                        // If it is, it is clamped to the last element of the 
251
+                                                                                        // If it is, it is clamped to the last element of the
252 252
                                                                                         // z_values[][] array and no correction is applied.
253 253
       }
254 254
 

Laden…
Abbrechen
Speichern