diff --git a/core/src/linuxcnc_canon_bridge.cpp b/core/src/linuxcnc_canon_bridge.cpp index 81f6291..070b8f0 100644 --- a/core/src/linuxcnc_canon_bridge.cpp +++ b/core/src/linuxcnc_canon_bridge.cpp @@ -402,6 +402,15 @@ void SET_MOTION_CONTROL_MODE(CANON_MOTION_MODE mode, double tolerance) { void SET_NAIVECAM_TOLERANCE(double tolerance) { naivecam_tolerance = tolerance; + if (active_sink) { + CncSimEvent event{}; + event.version = 1; + event.type = CNC_SIM_EVENT_COMMENT; + event.line = event_line(); + event.feed = tolerance; + event.reserved = 641; + active_sink->emit_raw(event); + } } void SET_CUTTER_RADIUS_COMPENSATION(double) { diff --git a/docs/linuxcnc-porting.md b/docs/linuxcnc-porting.md index 3c8c06b..2729895 100644 --- a/docs/linuxcnc-porting.md +++ b/docs/linuxcnc-porting.md @@ -209,7 +209,7 @@ This matrix tracks LinuxCNC feature coverage for the web/WASM simulator. A featu | Modal state save/restore `M70`-`M73` | covered for main-program save/invalidate/restore plus O-word subroutine autorestore in smoke parser, with native/source regressions checking restored distance mode, units, and XY plane motion | `tests/gcode/linuxcnc_modal_state.ngc`, `tests/gcode/linuxcnc_modal_autorestore.ngc` | | LinuxCNC read-only named parameters | common modal/unit/feed/spindle reads and additional ccomp/spindle-mode readonly reads are covered through LinuxCNC native/source backends | `tests/gcode/linuxcnc_readonly_named_parameters.ngc`, `tests/gcode/linuxcnc_readonly_named_parameters_extra.ngc`, `tests/gcode/linuxcnc_lathe_diameter_mode.ngc` | | LinuxCNC numbered parameters | native/source coverage checks readonly numbered-parameter rejection plus probe, tool, G28/G30, G52/G92, G5X/G59.3, debug/M66 result, tool-offset, current-position, `restore_parameters()`/`save_parameters()` persistence, and volatile global numbered parameters from LinuxCNC source state | `tests/gcode/linuxcnc_numbered_parameters.ngc`, `tests/gcode/linuxcnc_rotary_probe_numbered_parameters.ngc`, `tests/gcode/linuxcnc_multi_rotary_probe_numbered_parameters.ngc`, `tests/gcode/linuxcnc_tool_info_zero_parameter.ngc`, `tests/gcode/linuxcnc_spindle_tool_info_parameter.ngc`, `tests/gcode/linuxcnc_readonly_numbered_parameter_assign_error.ngc`, `tests/gcode/linuxcnc_g28_g30_numbered_parameters.ngc`, `tests/gcode/linuxcnc_rotary_g28_g30_numbered_parameters.ngc`, `tests/gcode/linuxcnc_g92_numbered_parameters.ngc`, `tests/gcode/linuxcnc_rotary_g92_numbered_parameters.ngc`, `tests/gcode/linuxcnc_g52_g92_numbered_interaction.ngc`, `tests/gcode/linuxcnc_g5x_numbered_parameters.ngc`, `tests/gcode/linuxcnc_g59_3_numbered_parameters.ngc`, `tests/gcode/linuxcnc_g59_3_rotary_numbered_parameters.ngc`, `tests/gcode/linuxcnc_g5x_rotary_numbered_parameters.ngc`, `tests/gcode/linuxcnc_g54_rotary_numbered_parameters.ngc`, `tests/gcode/linuxcnc_debug_level_parameter.ngc`, `tests/gcode/linuxcnc_m66_result_parameter.ngc`, `tests/gcode/linuxcnc_tool_offset_numbered_parameters.ngc`, `tests/gcode/linuxcnc_rotary_tool_offset_numbered_parameters.ngc`, `tests/gcode/linuxcnc_current_position_numbered_parameters.ngc`, `tests/gcode/linuxcnc_persistent_parameters_set.ngc`, `tests/gcode/linuxcnc_persistent_parameters_check.ngc`, `tests/gcode/linuxcnc_rotary_persistent_parameters_set.ngc`, `tests/gcode/linuxcnc_rotary_persistent_parameters_check.ngc`, `tests/gcode/linuxcnc_g54_persistent_parameters_set.ngc`, `tests/gcode/linuxcnc_g54_persistent_parameters_check.ngc`, `tests/gcode/linuxcnc_user_persistent_parameter_set.ngc`, `tests/gcode/linuxcnc_user_persistent_parameter_check.ngc`, `tests/gcode/linuxcnc_user_persistent_parameter_existing_check.ngc`, `tests/gcode/linuxcnc_user_persistent_parameter_boundary_set.ngc`, `tests/gcode/linuxcnc_user_persistent_parameter_boundary_check.ngc`, `tests/gcode/linuxcnc_volatile_global_parameter_set.ngc`, `tests/gcode/linuxcnc_volatile_global_parameter_check.ngc` | -| Feed and motion control modes `G93/G94/G95`, `G61/G61.1/G64` | covered through LinuxCNC native/source backends | `tests/gcode/linuxcnc_feed_modes.ngc`, `tests/gcode/linuxcnc_motion_modes.ngc` | +| Feed and motion control modes `G93/G94/G95`, `G61/G61.1/G64` | covered through LinuxCNC native/source backends, including `G64 P` path tolerance and `G64 Q` naivecam tolerance from `convert_control_mode()` | `tests/gcode/linuxcnc_feed_modes.ngc`, `tests/gcode/linuxcnc_motion_modes.ngc`, `tests/gcode/linuxcnc_control_mode_tolerances.ngc` | | Dwell `G4 P...` | covered through LinuxCNC native/source backends for missing-P rejection and boundary values around LinuxCNC's exact `P-1.0` missing-value sentinel; neighboring negative P values are passed through to `DWELL` by `convert_dwell()` | `tests/gcode/linuxcnc_g4_missing_p_error.ngc`, `tests/gcode/linuxcnc_g4_negative_p_error.ngc`, `tests/gcode/linuxcnc_g4_dwell_boundaries.ngc` | | Canned cycle `G73`-`G89`/`G80` | covered for drilling expand-to-canon path, `G18/G19` plane-specific depth-axis mapping for representative drilling/boring cycles, `G17.1` extended-plane depth/retract mapping, and native/source LinuxCNC `interp_cycles.cc` validation of repeat counts, required R/depth words, invalid rotary axes including follow-up modal-cycle blocks, Q/P words, and spindle state | `tests/gcode/linuxcnc_canned_cycle.ngc`, `tests/gcode/linuxcnc_canned_cycles_extended.ngc`, `tests/gcode/linuxcnc_canned_cycle_planes.ngc`, `tests/gcode/linuxcnc_extended_plane_cycle.ngc`, `tests/gcode/linuxcnc_canned_cycle_l0_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_missing_r_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_missing_z_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g18_missing_y_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g19_missing_x_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_r_less_z_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g18_r_less_y_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g19_r_less_x_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_u_in_xy_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_a_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_b_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_c_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_reject_rotary_followup.ngc`, `tests/gcode/linuxcnc_canned_cycle_g73_missing_q_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g83_missing_q_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g73_q0_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g83_q0_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g82_missing_p_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g86_missing_p_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g88_missing_p_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g89_missing_p_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g74_clockwise_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g84_counterclockwise_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g74_stopped_spindle_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g84_stopped_spindle_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g86_stopped_spindle_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g88_stopped_spindle_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g87_stopped_spindle_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g87_missing_k_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g87_missing_i_error.ngc`, `tests/gcode/linuxcnc_canned_cycle_g87_missing_j_error.ngc` | | Coordinate offset Canon events `G10 L2`, `G10 L20`, `G10 P0 active-system targeting`, `G54`-`G59.3` selection, `G52`, `G92/G92.1/G92.2/G92.3` | covered through LinuxCNC native/source backends, including all nine G5X indices | `tests/gcode/linuxcnc_coordinate_offsets.ngc`, `tests/gcode/linuxcnc_coordinate_l20.ngc`, `tests/gcode/linuxcnc_coordinate_p0.ngc`, `tests/gcode/linuxcnc_coordinate_select_all.ngc`, `tests/gcode/linuxcnc_g92_restore.ngc`, `tests/gcode/linuxcnc_g52_offset.ngc` | diff --git a/test-linuxcnc-rs274-native.sh b/test-linuxcnc-rs274-native.sh index e4fe4e0..f30fb57 100755 --- a/test-linuxcnc-rs274-native.sh +++ b/test-linuxcnc-rs274-native.sh @@ -569,6 +569,10 @@ CNC_SIM_RS274_VAR="$var_file" "$build_dir/linuxcnc_rs274_dump" tests/gcode/linux CNC_SIM_RS274_VAR="$var_file" "$build_dir/linuxcnc_rs274_dump" tests/gcode/linuxcnc_coolant.ngc >"$output_dir/cnc_sim_linuxcnc_coolant.json" CNC_SIM_RS274_VAR="$var_file" "$build_dir/linuxcnc_rs274_dump" tests/gcode/linuxcnc_feed_modes.ngc >"$output_dir/cnc_sim_linuxcnc_feed_modes.json" CNC_SIM_RS274_VAR="$var_file" "$build_dir/linuxcnc_rs274_dump" tests/gcode/linuxcnc_motion_modes.ngc >"$output_dir/cnc_sim_linuxcnc_motion_modes.json" +# Source basis: LinuxCNC src/emc/rs274ngc/interp_convert.cc +# convert_control_mode() sends G64 P through SET_MOTION_CONTROL_MODE() +# and G64 Q through SET_NAIVECAM_TOLERANCE(), defaulting Q to P when Q is omitted. +CNC_SIM_RS274_VAR="$var_file" "$build_dir/linuxcnc_rs274_dump" tests/gcode/linuxcnc_control_mode_tolerances.ngc >"$output_dir/cnc_sim_linuxcnc_control_mode_tolerances.json" CNC_SIM_RS274_VAR="$var_file" "$build_dir/linuxcnc_rs274_dump" tests/gcode/linuxcnc_tool_length.ngc >"$output_dir/cnc_sim_linuxcnc_tool_length.json" CNC_SIM_RS274_VAR="$var_file" "$build_dir/linuxcnc_rs274_dump" tests/gcode/linuxcnc_dynamic_tool_length.ngc >"$output_dir/cnc_sim_linuxcnc_dynamic_tool_length.json" # Source basis: LinuxCNC src/emc/rs274ngc/interp_convert.cc @@ -1524,6 +1528,23 @@ for expected in [(2, 611, 0), (3, 612, 0), (4, 640, 0.05)]: if expected not in motion_mode_states: raise SystemExit(f"missing motion mode state {expected!r}") +control_mode_tolerances = load("cnc_sim_linuxcnc_control_mode_tolerances.json") +control_mode_tolerance_states = [ + (event["line"], event["reserved"], event["feed"]) + for event in control_mode_tolerances + if event["type"] == "comment" and event["reserved"] in {611, 612, 640, 641} +] +expected_control_mode_tolerance_states = [ + (2, 640, 0.05), + (2, 641, 0.02), + (3, 640, 0.03), + (3, 641, 0.03), + (4, 611, 0), + (5, 612, 0), +] +if control_mode_tolerance_states != expected_control_mode_tolerance_states: + raise SystemExit(f"unexpected G64 P/Q control mode tolerance states: {control_mode_tolerance_states!r}") + tool_length = load("cnc_sim_linuxcnc_tool_length.json") if not any( event["type"] == "comment" and diff --git a/test-linuxcnc-source-link.sh b/test-linuxcnc-source-link.sh index 69dc2fe..598f074 100755 --- a/test-linuxcnc-source-link.sh +++ b/test-linuxcnc-source-link.sh @@ -336,6 +336,12 @@ CNC_SIM_RS274_VAR="$var_file" \ CNC_SIM_RS274_VAR="$var_file" \ "$build_dir/linuxcnc_rs274_source_dump" tests/gcode/linuxcnc_motion_modes.ngc \ >"$output_dir/cnc_sim_linuxcnc_source_motion_modes.json" +# Source basis: LinuxCNC src/emc/rs274ngc/interp_convert.cc +# convert_control_mode() sends G64 P through SET_MOTION_CONTROL_MODE() +# and G64 Q through SET_NAIVECAM_TOLERANCE(), defaulting Q to P when Q is omitted. +CNC_SIM_RS274_VAR="$var_file" \ + "$build_dir/linuxcnc_rs274_source_dump" tests/gcode/linuxcnc_control_mode_tolerances.ngc \ + >"$output_dir/cnc_sim_linuxcnc_source_control_mode_tolerances.json" CNC_SIM_RS274_VAR="$var_file" \ "$build_dir/linuxcnc_rs274_source_dump" tests/gcode/linuxcnc_tool_length.ngc \ >"$output_dir/cnc_sim_linuxcnc_source_tool_length.json" @@ -1840,6 +1846,23 @@ expected_override_states = [ if override_states != expected_override_states: raise SystemExit(f"unexpected source-linked M48-M53 override states: {override_states!r}") +control_mode_tolerances = json.loads((OUTPUT_DIR / "cnc_sim_linuxcnc_source_control_mode_tolerances.json").read_text()) +control_mode_tolerance_states = [ + (event["line"], event["reserved"], event["feed"]) + for event in control_mode_tolerances + if event["type"] == "comment" and event["reserved"] in {611, 612, 640, 641} +] +expected_control_mode_tolerance_states = [ + (2, 640, 0.05), + (2, 641, 0.02), + (3, 640, 0.03), + (3, 641, 0.03), + (4, 611, 0), + (5, 612, 0), +] +if control_mode_tolerance_states != expected_control_mode_tolerance_states: + raise SystemExit(f"unexpected source-linked G64 P/Q control mode tolerance states: {control_mode_tolerance_states!r}") + modal_state = json.loads((OUTPUT_DIR / "cnc_sim_linuxcnc_source_modal_state.json").read_text()) if not any( event["type"] == "rapid" and diff --git a/tests/gcode/linuxcnc_control_mode_tolerances.ngc b/tests/gcode/linuxcnc_control_mode_tolerances.ngc new file mode 100644 index 0000000..01db3d0 --- /dev/null +++ b/tests/gcode/linuxcnc_control_mode_tolerances.ngc @@ -0,0 +1,6 @@ +G21 G90 G17 +G64 P0.05 Q0.02 +G64 P0.03 +G61 +G61.1 +M30