diff --git a/src/regex_impl.hh b/src/regex_impl.hh index d7e7554cc..1e8296b53 100644 --- a/src/regex_impl.hh +++ b/src/regex_impl.hh @@ -233,12 +233,11 @@ public: ~ThreadedRegexVM() { - for (auto* saves : m_saves) + for (auto& saves : m_saves) { - for (size_t i = m_program.save_count-1; i > 0; --i) - saves->pos[i].~Iterator(); - saves->~Saves(); - operator delete(saves); + for (int i = m_program.save_count-1; i >= 0; --i) + saves.pos[i].~Iterator(); + operator delete(saves.pos, m_program.save_count * sizeof(Iterator)); } } @@ -289,16 +288,16 @@ public: ArrayView captures() const { if (m_captures >= 0) - return { m_saves[m_captures]->pos, m_program.save_count }; + return { m_saves[m_captures].pos, m_program.save_count }; return {}; } private: struct Saves { - int16_t refcount; - int16_t next_free; - Iterator pos[1]; + int32_t refcount; + int32_t next_free; + Iterator* pos; }; template @@ -309,7 +308,7 @@ private: if (m_first_free >= 0) { const int16_t res = m_first_free; - Saves& saves = *m_saves[res]; + Saves& saves = m_saves[res]; m_first_free = saves.next_free; kak_assert(saves.refcount == 1); if (copy) @@ -320,11 +319,10 @@ private: return res; } - void* ptr = operator new (sizeof(Saves) + (count-1) * sizeof(Iterator)); - Saves* saves = new (ptr) Saves{1, 0, {copy ? pos[0] : Iterator{}}}; - for (size_t i = 1; i < count; ++i) - new (&saves->pos[i]) Iterator{copy ? pos[i] : Iterator{}}; - m_saves.push_back(saves); + auto* new_pos = reinterpret_cast(operator new (count * sizeof(Iterator))); + for (size_t i = 0; i < count; ++i) + new (new_pos+i) Iterator{copy ? pos[i] : Iterator{}}; + m_saves.push_back({1, 0, new_pos}); return static_cast(m_saves.size() - 1); } @@ -332,7 +330,7 @@ private: { if (index < 0) return; - auto& saves = *m_saves[index]; + auto& saves = m_saves[index]; if (saves.refcount == 1) { saves.next_free = m_first_free; @@ -414,7 +412,7 @@ private: break; if (thread.saves >= 0) - ++m_saves[thread.saves]->refcount; + ++m_saves[thread.saves].refcount; if (inst.param.split.prioritize_parent) m_threads.push_current({inst.param.split.target, thread.saves}); @@ -429,12 +427,12 @@ private: break; if (thread.saves < 0) thread.saves = new_saves(nullptr); - else if (m_saves[thread.saves]->refcount > 1) + else if (m_saves[thread.saves].refcount > 1) { - --m_saves[thread.saves]->refcount; - thread.saves = new_saves(m_saves[thread.saves]->pos); + --m_saves[thread.saves].refcount; + thread.saves = new_saves(m_saves[thread.saves].pos); } - m_saves[thread.saves]->pos[inst.param.save_index] = pos; + m_saves[thread.saves].pos[inst.param.save_index] = pos; break; case CompiledRegex::CharClass: if (pos == config.end) @@ -709,7 +707,7 @@ private: static constexpr bool forward = mode & RegexMode::Forward; DualThreadStack m_threads; - Vector m_saves; + Vector m_saves; int16_t m_first_free = -1; int16_t m_captures = -1; bool m_found_match = false;