Fix for laser incorrectly enabled in laser mode when M3S<n> commanded in G0 and G80 modal states. Ref. issue #644.

Added optional support for 3rd order acceleration (jerk) and G187 gcode. Ref. pull request #593.
This commit is contained in:
Terje Io
2024-12-31 08:48:33 +01:00
parent b0322fd72c
commit e8a0aeea26
14 changed files with 143 additions and 99 deletions
+2 -2
View File
@@ -1,6 +1,6 @@
## grblHAL ##
Latest build date is 20241222, see the [changelog](changelog.md) for details.
Latest build date is 20241230, see the [changelog](changelog.md) for details.
> [!NOTE]
> A settings reset will be performed on an update of builds prior to 20241208. Backup and restore of settings is recommended.
@@ -93,4 +93,4 @@ G/M-codes not supported by [legacy Grbl](https://github.com/gnea/grbl/wiki) are
Some [plugins](https://github.com/grblHAL/plugins) implements additional M-codes.
---
20241222
20241230
+24 -1
View File
@@ -1,10 +1,33 @@
## grblHAL changelog
<a name="20241226">Build 20241230
Core:
* Fix for laser incorrectly enabled in laser mode when `M3S<n>` commanded in `G0` and `G80` modal states. Ref. issue [#644](https://github.com/grblHAL/core/issues/644).
* Added support for 3rd order acceleration \(jerk\) and G187 gcode. Ref. pull request [#593](https://github.com/grblHAL/core/pull/593).
Drivers:
* STM32F4xx: updated ST framework to latest version, added support for ethernet via DP83848 PHY.
* STM32F4xx, STM32F7xx: Improved SD card mount/dismount handling and added support for card detect signal.
Now flags RTC as set if date >= grblHAL build date.
* LPC176x: added function required for Modbus support. Renamed bootloader build option to avoid confusion.
Plugins:
* SD card: improved mount/dismount handling.
---
<a name="20241226">20241226
Drivers:
* STM32F4xx: fix for not enabling steppers after clearing E-stop alarm. Ref. issue [#203](https://github.com/grblHAL/STM32F4xx/issues/203).
* STM32F4xx: SuperLongBoard - fix for not enabling steppers after clearing E-stop alarm. Ref. issue [#203](https://github.com/grblHAL/STM32F4xx/issues/203).
Plugins:
+10 -3
View File
@@ -190,9 +190,18 @@ or EMI triggering the related interrupt falsely or too many times.
// ADVANCED CONFIGURATION OPTIONS:
// EXPERIMENTAL OPTIONS
#define ENABLE_PATH_BLENDING Off // Do NOT enable unless working on adding this feature!
#if !defined ENABLE_ACCELERATION_PROFILES || defined __DOXYGEN__
#define ENABLE_ACCELERATION_PROFILES Off // Enable to allow G-Code changeable acceleration profiles.
#define ENABLE_JERK_ACCELERATION Off // Enable to use 3rd order Acceleration calculations. May need more processing power, tiny chips beware.
#endif
#if !defined ENABLE_JERK_ACCELERATION || defined __DOXYGEN__
#define ENABLE_JERK_ACCELERATION Off // Enable to use 3rd order acceleration calculations. May need more processing power, a FPU will help.
#endif
// -
// Enables code for debugging purposes. Not for general use and always in constant flux.
//#define DEBUG // Uncomment to enable. Default disabled.
@@ -2022,7 +2031,6 @@ G90
/*! @name 22x - Setting_AxisJerk
*/
///@{
#if ENABLE_JERK_ACCELERATION
#if !defined DEFAULT_X_JERK|| defined __DOXYGEN__
#define DEFAULT_X_JERK 100.0f // mm/sec^3
#endif
@@ -2047,7 +2055,6 @@ G90
#if (defined V_AXIS && !defined DEFAULT_V_JERK) || defined __DOXYGEN__
#define DEFAULT_V_JERK 100.0f // mm/sec^3
#endif
#endif
///@}
/*! @name 13x - Setting_AxisMaxTravel
+2 -2
View File
@@ -445,7 +445,6 @@ typedef enum {
PinGroup_AuxOutput,
PinGroup_AuxInputAnalog,
PinGroup_AuxOutputAnalog,
PinGroup_SdCard,
PinGroup_MotorChipSelect,
PinGroup_MotorUART,
PinGroup_I2C,
@@ -471,7 +470,8 @@ typedef enum {
PinGroup_QEI_Index = (1<<16),
PinGroup_Motor_Warning = (1<<17),
PinGroup_Motor_Fault = (1<<18),
PinGroup_AuxInput = (1<<19)
PinGroup_SdCard = (1<<19),
PinGroup_AuxInput = (1<<20)
} pin_group_t;
//! Pin interrupt modes, may be or'ed when reporting pin capability.
+33 -15
View File
@@ -288,6 +288,24 @@ plane_t *gc_get_plane_data (plane_t *plane, plane_select_t select)
return plane;
}
#if ENABLE_ACCELERATION_PROFILES
//Acceleration Profiles for G187 P[x] in percent of maximum machine acceleration.
float gc_get_accel_factor (uint8_t profile)
{
static const float lookup[] = {
1.0f, // 100% - Roughing - Max Acceleration Default
0.8f, // 80% - Semi Roughing
0.6f, // 60% - Semi Finish
0.4f, // 40% - Finish
0.2f // 20% - Slow AF Mode
};
return lookup[profile >= (sizeof(lookup) / sizeof(float)) ? 0 : profile];
}
#endif // ENABLE_ACCELERATION_PROFILES
void gc_init (bool stop)
{
#if COMPATIBILITY_LEVEL > 1
@@ -362,7 +380,7 @@ void gc_init (bool stop)
ngc_modal_state_invalidate();
#endif
#if ENABLE_ACCELERATION_PROFILES
gc_state.modal.acceleration_factor = 1.0f; // Initialize machine with 100% Profile
gc_state.modal.acceleration_factor = gc_get_accel_factor(0); // Initialize machine with default
#endif
// if(settings.flags.lathe_mode)
@@ -2379,7 +2397,7 @@ status_code_t gc_execute_block (char *block)
if(gc_block.words.p && (gc_block.values.p < 1.0f || gc_block.values.p > 5.0f))
FAIL(Status_GcodeValueOutOfRange);
gc_state.modal.acceleration_factor = lookupfactor(gc_block.words.p ? (uint8_t)gc_block.values.p - 1 : 0);
gc_state.modal.acceleration_factor = gc_get_accel_factor(gc_block.words.p ? (uint8_t)gc_block.values.p - 1 : 0);
gc_block.words.p = Off;
break;
#endif
@@ -3163,6 +3181,10 @@ status_code_t gc_execute_block (char *block)
}
sspindle->rpm = gc_block.values.s; // Update spindle speed state.
}
// NOTE: Pass zero spindle speed for all restricted laser motions.
plan_data.spindle.rpm = gc_parser_flags.laser_disable ? 0.0f : gc_block.values.s;
#if N_SYS_SPINDLE > 1
}
#endif
@@ -3331,28 +3353,24 @@ status_code_t gc_execute_block (char *block)
if((spindle_ok = sspindle->state.value != gc_block.spindle_modal.state.value)) {
if(grbl.on_spindle_programmed)
grbl.on_spindle_programmed(sspindle->hal, gc_block.spindle_modal.state, sspindle->rpm, sspindle->rpm_mode);
grbl.on_spindle_programmed(sspindle->hal, gc_block.spindle_modal.state, plan_data.spindle.rpm, sspindle->rpm_mode);
if((spindle_ok = spindle_sync(sspindle->hal, gc_block.spindle_modal.state, sspindle->rpm)))
if((spindle_ok = spindle_sync(sspindle->hal, gc_block.spindle_modal.state, plan_data.spindle.rpm)))
sspindle->state = sspindle->hal->param->state = gc_block.spindle_modal.state;
spindle_event = !spindle_ok;
}
if(spindle_event && grbl.on_spindle_programmed)
grbl.on_spindle_programmed(sspindle->hal, sspindle->state, sspindle->rpm, sspindle->rpm_mode);
grbl.on_spindle_programmed(sspindle->hal, sspindle->state, plan_data.spindle.rpm, sspindle->rpm_mode);
}
if(sspindle != NULL)
gc_state.spindle = sspindle; // for now
// NOTE: Pass zero spindle speed for all restricted laser motions.
if(!gc_parser_flags.laser_disable)
memcpy(&plan_data.spindle, gc_state.spindle, sizeof(spindle_t)); // Record data for planner use.
else {
plan_data.spindle.hal = gc_state.spindle->hal;
// plan_data.spindle.speed = 0.0f; // Initialized as zero already.
}
plan_data.spindle.hal = gc_state.spindle->hal;
memcpy(&plan_data.spindle, gc_state.spindle, offsetof(spindle_t, rpm)); // Record data for planner use.
// TODO: Recheck spindle running in CCS mode (is_rpm_pos_adjusted == On)?
plan_data.spindle.state = gc_state.spindle->state; // Set condition flag for planner use.
@@ -3846,9 +3864,9 @@ status_code_t gc_execute_block (char *block)
gc_state.modal.coolant = (coolant_state_t){0};
gc_state.modal.override_ctrl.feed_rate_disable = Off;
gc_state.modal.override_ctrl.spindle_rpm_disable = Off;
#if ENABLE_ACCELERATION_PROFILES
gc_state.modal.acceleration_factor = 1.0f;
#endif
#if ENABLE_ACCELERATION_PROFILES
gc_state.modal.acceleration_factor = gc_get_accel_factor(0);
#endif
#if N_SYS_SPINDLE > 1
+16 -1
View File
@@ -502,11 +502,22 @@ typedef struct {
const gc_value_type_t type;
} gc_value_ptr_t;
typedef union {
uint8_t value;
struct {
uint8_t is_rpm_rate_adjusted :1,
is_laser_ppi_mode :1,
unassigned :6;
};
} spindle_cond_t;
typedef struct {
float rpm; //!< Spindle speed
spindle_state_t state; //!< {M3,M4,M5}
spindle_rpm_mode_t rpm_mode; //!< {G96,G97}
spindle_css_data_t *css; //!< Data used for Constant Surface Speed Mode calculations
spindle_cond_t condition; //!< TODO: move data from planner_cond_t here
float rpm; //!< Spindle speed. Must be second last!
spindle_ptrs_t *hal; //!< Spindle function pointers etc. Must be last!
} spindle_t;
@@ -701,4 +712,8 @@ parameter_words_t gc_get_g65_arguments (void);
bool gc_modal_state_restore (gc_modal_t *copy);
#endif
#if ENABLE_ACCELERATION_PROFILES
float gc_get_accel_factor (uint8_t profile);
#endif
#endif // _GCODE_H_
+1 -1
View File
@@ -42,7 +42,7 @@
#else
#define GRBL_VERSION "1.1f"
#endif
#define GRBL_BUILD 20241222
#define GRBL_BUILD 20241230
#define GRBL_URL "https://github.com/grblHAL"
+12 -4
View File
@@ -127,6 +127,14 @@
#endif
#endif
#ifndef SD_DETECT_BIT
#ifdef SD_DETECT_PIN
#define SD_DETECT_BIT (1<<SD_DETECT_PIN)
#else
#define SD_DETECT_BIT 0
#endif
#endif
// Optional control signals
#ifndef SAFETY_DOOR_BIT
@@ -633,11 +641,11 @@ static inline void aux_ctrl_claim_out_ports (aux_claim_explicit_out_ptr aux_clai
#ifndef DEVICES_IRQ_MASK
#ifdef AUX_DEVICES
#define DEVICES_IRQ_MASK (SPI_IRQ_BIT|SPINDLE_INDEX_BIT|QEI_A_BIT|QEI_B_BIT)
#define DEVICES_IRQ_MASK_SUM (SPI_IRQ_BIT+SPINDLE_INDEX_BIT+QEI_A_BIT+QEI_B_BIT)
#define DEVICES_IRQ_MASK (SPI_IRQ_BIT|SPINDLE_INDEX_BIT|QEI_A_BIT|QEI_B_BIT|SD_DETECT_BIT)
#define DEVICES_IRQ_MASK_SUM (SPI_IRQ_BIT+SPINDLE_INDEX_BIT+QEI_A_BIT+QEI_B_BIT+SD_DETECT_BIT)
#else
#define DEVICES_IRQ_MASK (MPG_MODE_BIT|I2C_STROBE_BIT|QEI_SELECT_BIT|SPI_IRQ_BIT|SPINDLE_INDEX_BIT|QEI_A_BIT|QEI_B_BIT)
#define DEVICES_IRQ_MASK_SUM (MPG_MODE_BIT+I2C_STROBE_BIT+QEI_SELECT_BIT+SPI_IRQ_BIT+SPINDLE_INDEX_BIT+QEI_A_BIT+QEI_B_BIT)
#define DEVICES_IRQ_MASK (MPG_MODE_BIT|I2C_STROBE_BIT|QEI_SELECT_BIT|SPI_IRQ_BIT|SPINDLE_INDEX_BIT|QEI_A_BIT|QEI_B_BIT|SD_DETECT_BIT)
#define DEVICES_IRQ_MASK_SUM (MPG_MODE_BIT+I2C_STROBE_BIT+QEI_SELECT_BIT+SPI_IRQ_BIT+SPINDLE_INDEX_BIT+QEI_A_BIT+QEI_B_BIT+SD_DETECT_BIT)
#endif
#endif
+5 -2
View File
@@ -336,6 +336,7 @@ inline static float plan_compute_profile_parameters (plan_block_t *block, float
block->max_entry_speed_sqr = nominal_speed > prev_nominal_speed ? (prev_nominal_speed * prev_nominal_speed) : (nominal_speed * nominal_speed);
if (block->max_entry_speed_sqr > block->max_junction_speed_sqr)
block->max_entry_speed_sqr = block->max_junction_speed_sqr;
return nominal_speed;
}
@@ -348,6 +349,7 @@ static inline float limit_acceleration_by_axis_maximum (float *unit_vec)
if (unit_vec[--idx] != 0.0f) // Avoid divide by zero.
limit_value = min(limit_value, fabsf(settings.axis[idx].acceleration / unit_vec[idx]));
} while(idx);
return limit_value;
}
@@ -361,6 +363,7 @@ static inline float limit_jerk_by_axis_maximum (float *unit_vec)
if (unit_vec[--idx] != 0.0f) // Avoid divide by zero.
limit_value = min(limit_value, fabsf(settings.axis[idx].jerk / unit_vec[idx]));
} while(idx);
return limit_value;
}
#endif
@@ -738,7 +741,7 @@ void plan_data_init (plan_line_data_t *plan_data)
#ifdef KINEMATICS_API
plan_data->rate_multiplier = 1.0f;
#endif
#ifdef ENABLE_ACCELERATION_PROFILES
plan_data->acceleration_factor = 1.0f;
#if ENABLE_ACCELERATION_PROFILES
plan_data->acceleration_factor = gc_get_accel_factor(0);
#endif
}
+2 -2
View File
@@ -78,7 +78,7 @@ typedef struct plan_block {
#ifdef KINEMATICS_API
float rate_multiplier; // Rate multiplier of this block.
#endif
#ifdef ENABLE_ACCELERATION_PROFILES
#if ENABLE_ACCELERATION_PROFILES
float acceleration_factor; // Stores the currently used acceleration factor.
#endif
// Stored spindle speed data used by spindle overrides and resuming methods.
@@ -96,7 +96,7 @@ typedef struct {
#ifdef KINEMATICS_API
float rate_multiplier; // Feed rate multiplier.
#endif
#ifdef ENABLE_ACCELERATION_PROFILES
#if ENABLE_ACCELERATION_PROFILES
float acceleration_factor; // Stores the currently used acceleration factor.
#endif
#if ENABLE_PATH_BLENDING
+17 -51
View File
@@ -210,9 +210,7 @@ PROGMEM const settings_t defaults = {
.axis[X_AXIS].steps_per_mm = DEFAULT_X_STEPS_PER_MM,
.axis[X_AXIS].max_rate = DEFAULT_X_MAX_RATE,
.axis[X_AXIS].acceleration = (DEFAULT_X_ACCELERATION * 60.0f * 60.0f),
#if ENABLE_JERK_ACCELERATION
.axis[X_AXIS].jerk = (DEFAULT_X_JERK * 60.0f * 60.0f * 60.0f),
#endif
.axis[X_AXIS].max_travel = (-DEFAULT_X_MAX_TRAVEL),
.axis[X_AXIS].dual_axis_offset = 0.0f,
.axis[X_AXIS].homing_feed_rate = DEFAULT_HOMING_FEED_RATE,
@@ -225,9 +223,7 @@ PROGMEM const settings_t defaults = {
.axis[Y_AXIS].max_rate = DEFAULT_Y_MAX_RATE,
.axis[Y_AXIS].max_travel = (-DEFAULT_Y_MAX_TRAVEL),
.axis[Y_AXIS].acceleration = (DEFAULT_Y_ACCELERATION * 60.0f * 60.0f),
#if ENABLE_JERK_ACCELERATION
.axis[Y_AXIS].jerk = (DEFAULT_Y_JERK * 60.0f * 60.0f * 60.0f),
#endif
.axis[Y_AXIS].dual_axis_offset = 0.0f,
.axis[Y_AXIS].homing_feed_rate = DEFAULT_HOMING_FEED_RATE,
.axis[Y_AXIS].homing_seek_rate = DEFAULT_HOMING_SEEK_RATE,
@@ -238,9 +234,7 @@ PROGMEM const settings_t defaults = {
.axis[Z_AXIS].steps_per_mm = DEFAULT_Z_STEPS_PER_MM,
.axis[Z_AXIS].max_rate = DEFAULT_Z_MAX_RATE,
.axis[Z_AXIS].acceleration = (DEFAULT_Z_ACCELERATION * 60.0f * 60.0f),
#if ENABLE_JERK_ACCELERATION
.axis[Z_AXIS].jerk = (DEFAULT_Z_JERK * 60.0f * 60.0f * 60.0f),
#endif
.axis[Z_AXIS].max_travel = (-DEFAULT_Z_MAX_TRAVEL),
.axis[Z_AXIS].dual_axis_offset = 0.0f,
.axis[Z_AXIS].homing_feed_rate = DEFAULT_HOMING_FEED_RATE,
@@ -253,9 +247,7 @@ PROGMEM const settings_t defaults = {
.axis[A_AXIS].steps_per_mm = DEFAULT_A_STEPS_PER_MM,
.axis[A_AXIS].max_rate = DEFAULT_A_MAX_RATE,
.axis[A_AXIS].acceleration =(DEFAULT_A_ACCELERATION * 60.0f * 60.0f),
#if ENABLE_JERK_ACCELERATION
.axis[A_AXIS].jerk = (DEFAULT_A_JERK * 60.0f * 60.0f * 60.0f),
#endif
.axis[A_AXIS].max_travel = (-DEFAULT_A_MAX_TRAVEL),
.axis[A_AXIS].dual_axis_offset = 0.0f,
.axis[A_AXIS].homing_feed_rate = DEFAULT_HOMING_FEED_RATE,
@@ -270,9 +262,7 @@ PROGMEM const settings_t defaults = {
.axis[B_AXIS].steps_per_mm = DEFAULT_B_STEPS_PER_MM,
.axis[B_AXIS].max_rate = DEFAULT_B_MAX_RATE,
.axis[B_AXIS].acceleration = (DEFAULT_B_ACCELERATION * 60.0f * 60.0f),
#if ENABLE_JERK_ACCELERATION
.axis[B_AXIS].jerk = (DEFAULT_B_JERK * 60.0f * 60.0f * 60.0f),
#endif
.axis[B_AXIS].max_travel = (-DEFAULT_B_MAX_TRAVEL),
.axis[B_AXIS].dual_axis_offset = 0.0f,
.axis[B_AXIS].homing_feed_rate = DEFAULT_HOMING_FEED_RATE,
@@ -286,9 +276,7 @@ PROGMEM const settings_t defaults = {
#ifdef C_AXIS
.axis[C_AXIS].steps_per_mm = DEFAULT_C_STEPS_PER_MM,
.axis[C_AXIS].acceleration = (DEFAULT_C_ACCELERATION * 60.0f * 60.0f),
#if ENABLE_JERK_ACCELERATION
.axis[C_AXIS].jerk = (DEFAULT_C_JERK * 60.0f * 60.0f * 60.0f),
#endif
.axis[C_AXIS].max_rate = DEFAULT_C_MAX_RATE,
.axis[C_AXIS].max_travel = (-DEFAULT_C_MAX_TRAVEL),
.axis[C_AXIS].dual_axis_offset = 0.0f,
@@ -303,9 +291,7 @@ PROGMEM const settings_t defaults = {
#ifdef U_AXIS
.axis[U_AXIS].steps_per_mm = DEFAULT_U_STEPS_PER_MM,
.axis[U_AXIS].acceleration = (DEFAULT_U_ACCELERATION * 60.0f * 60.0f),
#if ENABLE_JERK_ACCELERATION
.axis[U_AXIS].jerk = (DEFAULT_U_JERK * 60.0f * 60.0f * 60.0f),
#endif
.axis[U_AXIS].max_rate = DEFAULT_U_MAX_RATE,
.axis[U_AXIS].max_travel = (-DEFAULT_U_MAX_TRAVEL),
.axis[U_AXIS].dual_axis_offset = 0.0f,
@@ -319,9 +305,7 @@ PROGMEM const settings_t defaults = {
#ifdef V_AXIS
.axis[V_AXIS].steps_per_mm = DEFAULT_V_STEPS_PER_MM,
.axis[V_AXIS].acceleration = (DEFAULT_V_ACCELERATION * 60.0f * 60.0f),
#if ENABLE_JERK_ACCELERATION
.axis[V_AXIS].jerk = (DEFAULT_V_JERK * 60.0f * 60.0f * 60.0f),
#endif
.axis[V_AXIS].max_rate = DEFAULT_V_MAX_RATE,
.axis[V_AXIS].max_travel = (-DEFAULT_V_MAX_TRAVEL),
.axis[V_AXIS].dual_axis_offset = 0.0f,
@@ -446,7 +430,7 @@ static char axis_dist[4] = "mm";
static char axis_rate[8] = "mm/min";
static char axis_accel[10] = "mm/sec^2";
#if ENABLE_JERK_ACCELERATION
static char axis_jerk[15] = "mm/sec^3";
static char axis_jerk[10] = "mm/sec^3";
#endif
#if DELTA_ROBOT
static char axis_steps[9] = "step/rev";
@@ -499,29 +483,12 @@ bool settings_override_acceleration (uint8_t axis, float acceleration)
} else {
if(!override_backup.valid)
save_override_backup();
settings.axis[axis].acceleration = (override_backup.acceleration[axis] >= (acceleration * 60.0f * 60.0f)) ? (acceleration * 60.0f * 60.0f) : override_backup.acceleration[axis]; // Limited to max setting value
settings.axis[axis].acceleration = acceleration * 60.0f * 60.0f; // Limit max to setting value?
}
return true;
}
#if ENABLE_ACCELERATION_PROFILES
//Acceleration Profiles for G187 P[x] in percent of maximum machine acceleration.
float lookupfactor(uint8_t profile) {
static const float lookup[5] = {
1.0f, // 100% - Roughing - Max Acceleration Default
0.8f, // 80% - Semi Roughing
0.6f, // 60% - Semi Finish
0.4f, // 40% - Finish
0.2f, // 20% - Slow AF Mode
};
if (profile >= sizeof(lookup) / sizeof(lookup[0])) {
profile = 0;
}
return lookup[profile];
}
#endif
// ---
static void homing_pulloff_init (float pulloff)
@@ -1194,12 +1161,12 @@ static status_code_t set_axis_setting (setting_id_t setting, float value)
break;
case Setting_AxisAcceleration:
settings.axis[idx].acceleration = override_backup.acceleration[idx] = value * 60.0f * 60.0f; // Convert to mm/min^2 for grbl internal use.
settings.axis[idx].acceleration = override_backup.acceleration[idx] = value * 60.0f * 60.0f; // Convert to mm/min^2 for internal use.
break;
#if ENABLE_JERK_ACCELERATION
case Setting_AxisJerk:
settings.axis[idx].jerk = value * 60.0f * 60.0f * 60.0f; // Convert to mm/min^3 for grbl internal use.
settings.axis[idx].jerk = value * 60.0f * 60.0f * 60.0f; // Convert to mm/min^3 for internal use.
break;
#endif
@@ -1208,7 +1175,7 @@ static status_code_t set_axis_setting (setting_id_t setting, float value)
bit_false(sys.homed.mask, bit(idx));
system_add_rt_report(Report_Homed);
}
settings.axis[idx].max_travel = -value; // Store as negative for grbl internal use.
settings.axis[idx].max_travel = -value; // Store as negative for internal use.
if(settings.homing.flags.init_lock && (sys.homing.mask & sys.homed.mask) != sys.homing.mask) {
system_raise_alarm(Alarm_HomingRequired);
grbl.report.feedback_message(Message_HomingCycleRequired);
@@ -1262,7 +1229,8 @@ static float get_float (setting_id_t setting)
{
float value = 0.0f;
if(setting >= Setting_AxisSettingsBase && setting <= Setting_AxisSettingsMax) {
if((setting >= Setting_AxisSettingsBase && setting <= Setting_AxisSettingsMax) ||
(setting >= Setting_AxisSettingsBase1 && setting <= Setting_AxisSettingsMax1)) {
uint_fast8_t idx;
@@ -1281,7 +1249,7 @@ static float get_float (setting_id_t setting)
break;
case Setting_AxisMaxTravel:
value = -settings.axis[idx].max_travel; // Store as negative for grbl internal use.
value = -settings.axis[idx].max_travel; // Store as negative for internal use.
break;
#if ENABLE_BACKLASH_COMPENSATION
@@ -1302,25 +1270,15 @@ static float get_float (setting_id_t setting)
value = settings.axis[idx].homing_seek_rate;
break;
default:
break;
}
} else if(setting >= Setting_AxisSettingsBase1 && setting <= Setting_AxisSettingsMax1) {
uint_fast8_t idx;
switch(settings_get_axis_base(setting, &idx)) {
#if ENABLE_JERK_ACCELERATION
case Setting_AxisJerk:
value = settings.axis[idx].jerk / (60.0f * 60.0f * 60.0f); // Convert from mm/min^3 to mm/sec^3.
break;
#endif
default:
break;
}
} else switch(setting) {
} else switch(setting) {
case Setting_HomingFeedRate:
value = settings.axis[0].homing_feed_rate;
@@ -3246,6 +3204,14 @@ void settings_init (void)
}
#endif
#if ENABLE_JERK_ACCELERATION
uint_fast8_t idx = N_AXIS;
do {
if(settings.axis[--idx].jerk == 0.0f)
settings.axis[idx].jerk = settings.axis[idx].acceleration * 60.0f * 10.0f;
} while(idx);
#endif
setting_details_t *details = setting_details.next;
if(details) do {
-4
View File
@@ -1081,10 +1081,6 @@ bool settings_read_coord_data(coord_system_id_t id, float (*coord_data)[N_AXIS])
// Temporarily override acceleration, if 0 restore to configured setting value
bool settings_override_acceleration (uint8_t axis, float acceleration);
#if ENABLE_ACCELERATION_PROFILES
float lookupfactor (uint8_t profile);
#endif
void settings_register (setting_details_t *details);
setting_details_t *settings_get_details (void);
bool settings_is_group_available (setting_group_t group);
+10 -2
View File
@@ -76,14 +76,20 @@ static parking_data_t park = {0};
static void state_spindle_restore (spindle_t *spindle)
{
if(spindle->hal)
if(spindle->hal) {
if(grbl.on_spindle_programmed)
grbl.on_spindle_programmed(spindle->hal, spindle->state, spindle->rpm, spindle->rpm_mode);
spindle_restore(spindle->hal, spindle->state, spindle->rpm);
}
}
static void state_spindle_set_state (spindle_t *spindle)
{
if(spindle->hal)
if(spindle->hal) {
if(grbl.on_spindle_programmed)
grbl.on_spindle_programmed(spindle->hal, spindle->state, spindle->rpm, spindle->rpm_mode);
spindle_set_state(spindle->hal, spindle->state, spindle->rpm);
}
}
static void state_restore_conditions (restore_condition_t *condition)
@@ -360,6 +366,8 @@ void state_suspend_manager (void)
// Handles beginning of spindle stop
if (sys.override.spindle_stop.initiate) {
sys.override.spindle_stop.value = 0; // Clear stop override state
if(grbl.on_spindle_programmed)
grbl.on_spindle_programmed(restore_condition.spindle[restore_condition.spindle_num].hal, (spindle_state_t){0}, 0.0f, 0);
spindle_set_state(restore_condition.spindle[restore_condition.spindle_num].hal, (spindle_state_t){0}, 0.0f); // De-energize
sys.override.spindle_stop.enabled = On; // Set stop override state to enabled, if de-energized.
if(grbl.on_override_changed)
+9 -9
View File
@@ -223,7 +223,7 @@ ISR_CODE void ISR_FUNC(st_go_idle)(void)
}
/* "The Stepper Driver Interrupt" - This timer interrupt is the workhorse of Grbl. Grbl employs
/* "The Stepper Driver Interrupt" - This timer interrupt is the workhorse of grblHAL. grblHAL employs
the venerable Bresenham line algorithm to manage and exactly synchronize multi-axis moves.
Unlike the popular DDA algorithm, the Bresenham algorithm is not susceptible to numerical
round-off errors and only requires fast integer counters, meaning low computational overhead
@@ -232,7 +232,7 @@ ISR_CODE void ISR_FUNC(st_go_idle)(void)
pulse trains, or aliasing, which can lead to strange audible noises or shaking. This is
particularly noticeable or may cause motion issues at low step frequencies (0-5kHz), but
is usually not a physical problem at higher frequencies, although audible.
To improve Bresenham multi-axis performance, Grbl uses what we call an Adaptive Multi-Axis
To improve Bresenham multi-axis performance, grblHAL uses what we call an Adaptive Multi-Axis
Step Smoothing (AMASS) algorithm, which does what the name implies. At lower step frequencies,
AMASS artificially increases the Bresenham resolution without effecting the algorithm's
innate exactness. AMASS adapts its resolution levels automatically depending on the step
@@ -246,7 +246,7 @@ ISR_CODE void ISR_FUNC(st_go_idle)(void)
Level 2, we simply bit-shift again, so the non-dominant Bresenham axes can step within any
of the four ISR ticks, the dominant axis steps every four ISR ticks, and quadruple the
stepper ISR frequency. And so on. This, in effect, virtually eliminates multi-axis aliasing
issues with the Bresenham algorithm and does not significantly alter Grbl's performance, but
issues with the Bresenham algorithm and does not significantly alter grblHAL's performance, but
in fact, more efficiently utilizes unused CPU cycles overall throughout all configurations.
AMASS retains the Bresenham algorithm exactness by requiring that it always executes a full
Bresenham step, regardless of AMASS Level. Meaning that for an AMASS Level 2, all four
@@ -263,9 +263,7 @@ ISR_CODE void ISR_FUNC(st_go_idle)(void)
after each pulse. The bresenham line tracer algorithm controls all stepper outputs
simultaneously with these two interrupts.
NOTE: This interrupt must be as efficient as possible and complete before the next ISR tick,
which for Grbl must be less than 33.3usec (@30kHz ISR rate). Oscilloscope measured time in
ISR is 5usec typical and 25usec maximum, well below requirement.
NOTE: This interrupt must be as efficient as possible and complete before the next ISR tick.
NOTE: This ISR expects at least one step to be executed per segment.
*/
@@ -393,8 +391,10 @@ ISR_CODE void ISR_FUNC(stepper_driver_interrupt_handler)(void)
st_go_idle();
// Ensure pwm is set properly upon completion of rate-controlled motion.
if (st.exec_block->dynamic_rpm && st.exec_block->spindle->cap.laser)
if(st.exec_block->dynamic_rpm && st.exec_block->spindle->cap.laser) {
prep.current_spindle_rpm = 0.0f;
st.exec_block->spindle->update_pwm(st.exec_block->spindle, st.exec_block->spindle->pwm_off_value);
}
st.exec_block = NULL;
system_set_exec_state_flag(EXEC_CYCLE_COMPLETE); // Flag main program for cycle complete
@@ -1033,7 +1033,7 @@ void st_prep_buffer (void)
However, since floats have only 7.2 significant digits, long moves with extremely
high step counts can exceed the precision of floats, which can lead to lost steps.
Fortunately, this scenario is highly unlikely and unrealistic in CNC machines
supported by Grbl (i.e. exceeding 10 meters axis travel at 200 step/mm).
supported by grblHAL (i.e. exceeding 10 meters axis travel at 200 step/mm).
*/
float step_dist_remaining = prep.steps_per_mm * mm_remaining; // Convert mm_remaining to steps
uint32_t n_steps_remaining = (uint32_t)ceilf(step_dist_remaining); // Round-up current steps remaining
@@ -1056,7 +1056,7 @@ void st_prep_buffer (void)
// compensate, we track the time to execute the previous segment's partial step and simply
// apply it with the partial step distance to the current segment, so that it minutely
// adjusts the whole segment rate to keep step output exact. These rate adjustments are
// typically very small and do not adversely effect performance, but ensures that Grbl
// typically very small and do not adversely effect performance, but ensures that grblHAL
// outputs the exact acceleration and velocity profiles as computed by the planner.
dt += prep.dt_remainder; // Apply previous segment partial step execute time
float inv_rate = dt / ((float)prep.steps_remaining - step_dist_remaining); // Compute adjusted step rate inverse