From 466e4ad84a8f795ef83873a0631b32dc3f32ce00 Mon Sep 17 00:00:00 2001 From: "Yukihiro \"Matz\" Matsumoto" Date: Mon, 23 Mar 2026 10:22:44 +0900 Subject: [PATCH] mruby-regexp: defer pool_copy until character actually matches Move pool_copy inside each match condition so captures are only copied for threads that advance to the next step, skipping the copy for non-matching threads. Co-authored-by: Claude --- mrbgems/mruby-regexp/src/re_exec.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/mrbgems/mruby-regexp/src/re_exec.c b/mrbgems/mruby-regexp/src/re_exec.c index 965e22daa..98252bc6f 100644 --- a/mrbgems/mruby-regexp/src/re_exec.c +++ b/mrbgems/mruby-regexp/src/re_exec.c @@ -288,32 +288,38 @@ pike_vm(mrb_state *mrb, const mrb_regexp_pattern *pat, if (th->pc >= pat->code_len) continue; re_inst inst = pat->code[th->pc]; - int cp = match_only ? 0 : pool_copy(&s, th->cap_slot); switch (inst.op) { case RE_CHAR: if (ch == inst.a) { + int cp = match_only ? 0 : pool_copy(&s, th->cap_slot); add_thread(&s, &next, th->pc + 1, cp, sp + 1); } break; case RE_ANY: if (ch != '\n') { + int cp = match_only ? 0 : pool_copy(&s, th->cap_slot); add_thread(&s, &next, th->pc + 1, cp, sp + advance); } break; case RE_ANY_NL: - add_thread(&s, &next, th->pc + 1, cp, sp + advance); + { + int cp = match_only ? 0 : pool_copy(&s, th->cap_slot); + add_thread(&s, &next, th->pc + 1, cp, sp + advance); + } break; case RE_CLASS: if (class_match(&pat->classes[inst.a], (uint8_t)ch)) { + int cp = match_only ? 0 : pool_copy(&s, th->cap_slot); add_thread(&s, &next, th->pc + 1, cp, sp + advance); } break; case RE_NCLASS: if (!class_match(&pat->classes[inst.a], (uint8_t)ch)) { + int cp = match_only ? 0 : pool_copy(&s, th->cap_slot); add_thread(&s, &next, th->pc + 1, cp, sp + advance); } break;