3
0
Fork 0
mirror of https://github.com/Z3Prover/z3 synced 2026-05-18 16:09:30 +00:00

Make dep_mgr private in seq_nielsen; expose conflict sources vector (#9129)

* make dep_mgr private in seq_nielsen, expose conflict_sources vector

Co-authored-by: NikolajBjorner <3085284+NikolajBjorner@users.noreply.github.com>
Agent-Logs-Url: https://github.com/Z3Prover/z3/sessions/998d8021-4808-4feb-afc5-b2447c6a64e5

* move deps_to_lits to seq namespace in seq_nielsen

Co-authored-by: NikolajBjorner <3085284+NikolajBjorner@users.noreply.github.com>
Agent-Logs-Url: https://github.com/Z3Prover/z3/sessions/8d736478-8f9b-4451-8d1f-539ce72525c7

---------

Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
Co-authored-by: NikolajBjorner <3085284+NikolajBjorner@users.noreply.github.com>
This commit is contained in:
Copilot 2026-03-25 08:05:00 -07:00 committed by GitHub
parent 49f2eb0e49
commit 46c76d89e0
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
6 changed files with 51 additions and 31 deletions

View file

@ -41,6 +41,19 @@ NSB review:
namespace seq {
void deps_to_lits(dep_tracker const& deps,
svector<enode_pair>& eqs,
svector<sat::literal>& lits) {
vector<dep_source, false> vs;
dep_manager::s_linearize(deps, vs);
for (dep_source const& d : vs) {
if (std::holds_alternative<enode_pair>(d))
eqs.push_back(std::get<enode_pair>(d));
else
lits.push_back(std::get<sat::literal>(d));
}
}
// Normalize an arithmetic expression using th_rewriter.
// Simplifies e.g. (n - 1 + 1) to n, preventing unbounded growth
// of power exponents during unwind/merge cycles.
@ -1461,6 +1474,7 @@ namespace seq {
++m_stats.m_num_solve_calls;
m_sat_node = nullptr;
m_sat_path.reset();
m_conflict_sources.reset();
// Constraint.Shared: assert root-level length/Parikh constraints to the
// solver at the base level, so they are visible during all feasibility checks.
@ -1504,6 +1518,9 @@ namespace seq {
}
if (r == search_result::unsat) {
++m_stats.m_num_unsat;
dep_tracker deps = m_dep_mgr.mk_empty();
collect_conflict_deps(deps);
m_dep_mgr.linearize(deps, m_conflict_sources);
return r;
}
// depth limit hit double the bound and retry

View file

@ -329,6 +329,11 @@ namespace seq {
// nullptr represents the empty dependency set.
using dep_tracker = dep_manager::dependency*;
// partition dep_source leaves from deps into enode pairs and sat literals.
void deps_to_lits(dep_tracker const& deps,
svector<enode_pair>& eqs,
svector<sat::literal>& lits);
// -----------------------------------------------
// character-level substitution
// mirrors ZIPT's CharSubst
@ -820,9 +825,6 @@ namespace seq {
seq_util& seq() { return m_seq; }
seq_util const& seq() const { return m_seq; }
dep_manager& dep_mgr() { return m_dep_mgr; }
dep_manager const& dep_mgr() const { return m_dep_mgr; }
// node management
nielsen_node* mk_node();
nielsen_node* mk_child(nielsen_node* parent);
@ -907,8 +909,8 @@ namespace seq {
// returns true if at least one child was generated
bool generate_extensions(nielsen_node *node);
// collect dependency information from conflicting constraints
void collect_conflict_deps(dep_tracker& deps) const;
// conflict sources extracted after solve() returns unsat
vector<dep_source, false> const& conflict_sources() const { return m_conflict_sources; }
// explain a conflict: partition the dep_source leaves into str_eq indices
// (kind::eq) and str_mem indices (kind::mem).
@ -952,6 +954,14 @@ namespace seq {
private:
vector<dep_source, false> m_conflict_sources;
dep_manager& dep_mgr() { return m_dep_mgr; }
dep_manager const& dep_mgr() const { return m_dep_mgr; }
// collect dependency information from conflicting constraints
void collect_conflict_deps(dep_tracker& deps) const;
search_result search_dfs(nielsen_node *node, ptr_vector<nielsen_edge>& path);
// Regex widening: overapproximate `str` by replacing variables with