Skip to content

Commit

Permalink
Fix crash due to cycles when replaying macros (helix-editor#2647)
Browse files Browse the repository at this point in the history
In certain circumstances it was possible to get into an infinite loop
when replaying macros such as when different macros attempt to replay
each other.

This commit adds changes to track which macros are currently being
replayed and prevent getting into infinite loops.
  • Loading branch information
gavynriebau authored Jun 5, 2022
1 parent 1c2aaf3 commit b2bd87d
Show file tree
Hide file tree
Showing 2 changed files with 15 additions and 0 deletions.
13 changes: 13 additions & 0 deletions helix-term/src/commands.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4617,6 +4617,17 @@ fn record_macro(cx: &mut Context) {

fn replay_macro(cx: &mut Context) {
let reg = cx.register.unwrap_or('@');

if cx.editor.macro_replaying.contains(&reg) {
cx.editor.set_error(format!(
"Cannot replay from register [{}] because already replaying from same register",
reg
));
return;
}

cx.editor.macro_replaying.push(reg);

let keys: Vec<KeyEvent> = if let Some([keys_str]) = cx.editor.registers.read(reg) {
match helix_view::input::parse_macro(keys_str) {
Ok(keys) => keys,
Expand All @@ -4638,4 +4649,6 @@ fn replay_macro(cx: &mut Context) {
}
}
}));

cx.editor.macro_replaying.pop();
}
2 changes: 2 additions & 0 deletions helix-view/src/editor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -433,6 +433,7 @@ pub struct Editor {
pub selected_register: Option<char>,
pub registers: Registers,
pub macro_recording: Option<(char, Vec<KeyEvent>)>,
pub macro_replaying: Vec<char>,
pub theme: Theme,
pub language_servers: helix_lsp::Registry,

Expand Down Expand Up @@ -503,6 +504,7 @@ impl Editor {
count: None,
selected_register: None,
macro_recording: None,
macro_replaying: Vec::new(),
theme: theme_loader.default(),
language_servers,
debugger: None,
Expand Down

0 comments on commit b2bd87d

Please sign in to comment.