Commit 5f8a8a59 by Alan Mishchenko

Upgrade to the circuit-based solver.

parent de71e5f6
...@@ -99,15 +99,16 @@ void glucose2_solver_setcallback(Gluco2::SimpSolver* S, void * pman, int(*pfunc) ...@@ -99,15 +99,16 @@ void glucose2_solver_setcallback(Gluco2::SimpSolver* S, void * pman, int(*pfunc)
int glucose2_solver_solve(Gluco2::SimpSolver* S, int * plits, int nlits) int glucose2_solver_solve(Gluco2::SimpSolver* S, int * plits, int nlits)
{ {
vec<Lit> lits; // vec<Lit> lits;
for (int i=0;i<nlits;i++,plits++) // for (int i=0;i<nlits;i++,plits++)
{ // {
Lit p; // Lit p;
p.x = *plits; // p.x = *plits;
lits.push(p); // lits.push(p);
} // }
Gluco2::lbool res = S->solveLimited(lits, 0); // Gluco2::lbool res = S->solveLimited(lits, 0);
return (res == l_True ? 1 : res == l_False ? -1 : 0); // return (res == l_True ? 1 : res == l_False ? -1 : 0);
return S->solveLimited(plits, nlits, 0);
} }
int glucose2_solver_addvar(Gluco2::SimpSolver* S) int glucose2_solver_addvar(Gluco2::SimpSolver* S)
...@@ -383,6 +384,10 @@ void bmcg2_sat_solver_mark_cone(bmcg2_sat_solver* s, int var) ...@@ -383,6 +384,10 @@ void bmcg2_sat_solver_mark_cone(bmcg2_sat_solver* s, int var)
((Gluco2::SimpSolver*)s)->sat_solver_mark_cone(var); ((Gluco2::SimpSolver*)s)->sat_solver_mark_cone(var);
} }
void bmcg2_sat_solver_prelocate( bmcg2_sat_solver * s, int var_num ){
((Gluco2::SimpSolver*)s)->prelocate(var_num);
}
#else #else
/**Function************************************************************* /**Function*************************************************************
...@@ -721,6 +726,10 @@ void bmcg2_sat_solver_mark_cone(bmcg2_sat_solver* s, int var) ...@@ -721,6 +726,10 @@ void bmcg2_sat_solver_mark_cone(bmcg2_sat_solver* s, int var)
((Gluco2::Solver*)s)->sat_solver_mark_cone(var); ((Gluco2::Solver*)s)->sat_solver_mark_cone(var);
} }
void bmcg2_sat_solver_prelocate( bmcg2_sat_solver * s, int var_num ){
((Gluco2::Solver*)s)->prelocate(var_num);
}
#endif #endif
......
...@@ -103,6 +103,7 @@ extern void bmcg2_sat_solver_set_jftr( bmcg2_sat_solver * s, int jf ...@@ -103,6 +103,7 @@ extern void bmcg2_sat_solver_set_jftr( bmcg2_sat_solver * s, int jf
extern void bmcg2_sat_solver_set_var_fanin_lit( bmcg2_sat_solver * s, int var, int lit0, int lit1 ); extern void bmcg2_sat_solver_set_var_fanin_lit( bmcg2_sat_solver * s, int var, int lit0, int lit1 );
extern void bmcg2_sat_solver_start_new_round( bmcg2_sat_solver * s ); extern void bmcg2_sat_solver_start_new_round( bmcg2_sat_solver * s );
extern void bmcg2_sat_solver_mark_cone( bmcg2_sat_solver * s, int var ); extern void bmcg2_sat_solver_mark_cone( bmcg2_sat_solver * s, int var );
extern void bmcg2_sat_solver_prelocate( bmcg2_sat_solver * s, int var_num );
extern void Glucose2_SolveCnf( char * pFilename, Glucose2_Pars * pPars ); extern void Glucose2_SolveCnf( char * pFilename, Glucose2_Pars * pPars );
extern int Glucose2_SolveAig( Gia_Man_t * p, Glucose2_Pars * pPars ); extern int Glucose2_SolveAig( Gia_Man_t * p, Glucose2_Pars * pPars );
......
...@@ -2,5 +2,6 @@ ...@@ -2,5 +2,6 @@
#define Glucose_CGlucose_h #define Glucose_CGlucose_h
#define CGLUCOSE_EXP 1 #define CGLUCOSE_EXP 1
#include "sat/glucose2/Heap2.h"
#endif #endif
\ No newline at end of file
...@@ -85,7 +85,7 @@ class Heap { ...@@ -85,7 +85,7 @@ class Heap {
void decrease (int n) { assert(inHeap(n)); percolateUp (indices[n]); } void decrease (int n) { assert(inHeap(n)); percolateUp (indices[n]); }
void increase (int n) { assert(inHeap(n)); percolateDown(indices[n]); } void increase (int n) { assert(inHeap(n)); percolateDown(indices[n]); }
void prelocate (int ext_cap){ indices.prelocate(ext_cap); }
// Safe variant of insert/decrease/increase: // Safe variant of insert/decrease/increase:
void update(int n) void update(int n)
...@@ -143,6 +143,15 @@ class Heap { ...@@ -143,6 +143,15 @@ class Heap {
indices[heap[i]] = -1; indices[heap[i]] = -1;
heap.clear(dealloc); heap.clear(dealloc);
} }
void clear_(bool dealloc = false)
{
int i;
for (i = 0; i < heap.size(); i++)
indices[heap[i]] = -1;
if( ! dealloc ) heap.shrink_( heap.size() );
else heap.clear(true);
}
}; };
......
/******************************************************************************************[Heap.h]
Copyright (c) 2003-2006, Niklas Een, Niklas Sorensson
Copyright (c) 2007-2010, Niklas Sorensson
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and
associated documentation files (the "Software"), to deal in the Software without restriction,
including without limitation the rights to use, copy, modify, merge, publish, distribute,
sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all copies or
substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT
NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
**************************************************************************************************/
#ifndef Glucose_Heap2_h
#define Glucose_Heap2_h
#include "sat/glucose2/Vec.h"
ABC_NAMESPACE_CXX_HEADER_START
namespace Gluco2 {
//=================================================================================================
// A heap implementation with support for decrease/increase key.
template<class Comp, class Obj>
class Heap2 {
Comp lt; // The heap is a minimum-heap with respect to this comparator
vec<Obj> heap; // Heap of integers
vec<int> indices; // Each integers position (index) in the Heap
// Index "traversal" functions
static inline int left (int i) { return i*2+1; }
static inline int right (int i) { return (i+1)*2; }
static inline int parent(int i) { return (i-1) >> 1; }
inline int data (int i) const { return heap[i].data();}
void percolateUp(int i)
{
Obj x = heap[i];
int p = parent(i);
while (i != 0 && lt(x, heap[p])){
heap[i] = heap[p];
indices[data(p)] = i;
i = p;
p = parent(p);
}
heap [i] = x;
indices[x.data()] = i;
}
void percolateDown(int i)
{
Obj x = heap[i];
while (left(i) < heap.size()){
int child = right(i) < heap.size() && lt(heap[right(i)], heap[left(i)]) ? right(i) : left(i);
if (!lt(heap[child], x)) break;
heap[i] = heap[child];
indices[data(i)] = i;
i = child;
}
heap [i] = x;
indices[x.data()] = i;
}
public:
Heap2(const Comp& c) : lt(c) { }
int size () const { return heap.size(); }
bool empty () const { return heap.size() == 0; }
bool inHeap (int n) const { return n < indices.size() && indices[n] >= 0; }
int operator[](int index) const { assert(index < heap.size()); return heap[index].data(); }
void decrease (int n) { assert(inHeap(n)); percolateUp (indices[n]); }
void increase (int n) { assert(inHeap(n)); percolateDown(indices[n]); }
void prelocate (int ext_cap){ indices.prelocate(ext_cap); }
int data_attr (int n) const { return heap[indices[n]].attr(); }
// Safe variant of insert/decrease/increase:
void update(const Obj& x)
{
int n = x.data();
if (!inHeap(n))
insert(x);
else {
heap[indices[x.data()]] = x;
percolateUp(indices[n]);
percolateDown(indices[n]); }
}
void insert(const Obj& x)
{
int n = x.data();
indices.growTo(n+1, -1);
assert(!inHeap(n));
indices[n] = heap.size();
heap.push(x);
percolateUp(indices[n]);
}
//Obj prev;
int removeMin(int& _attr)
{
Obj x = heap[0];
heap[0] = heap.last();
indices[heap[0].data()] = 0;
indices[x.data()]= -1;
heap.pop();
if (heap.size() > 1) percolateDown(0);
//prev = x;
_attr = x.attr();
return x.data();
}
// Rebuild the heap from scratch, using the elements in 'ns':
// void build(vec<int>& ns) {
// int i;
// for (i = 0; i < heap.size(); i++)
// indices[heap[i]] = -1;
// heap.clear();
//
// for (i = 0; i < ns.size(); i++){
// indices[ns[i]] = i;
// heap.push(ns[i]); }
//
// for (i = heap.size() / 2 - 1; i >= 0; i--)
// percolateDown(i);
// }
void clear(bool dealloc = false)
{
int i;
for (i = 0; i < heap.size(); i++)
indices[heap[i].data()] = -1;
heap.clear(dealloc);
}
void clear_(bool dealloc = false)
{
int i;
for (i = 0; i < heap.size(); i++)
indices[heap[i].data()] = -1;
if( ! dealloc ) heap.shrink_( heap.size() );
else heap.clear(true);
}
};
//=================================================================================================
}
ABC_NAMESPACE_CXX_HEADER_END
#endif
...@@ -61,12 +61,25 @@ class SimpSolver : public Solver { ...@@ -61,12 +61,25 @@ class SimpSolver : public Solver {
// //
bool solve (const vec<Lit>& assumps, bool do_simp = true, bool turn_off_simp = false); bool solve (const vec<Lit>& assumps, bool do_simp = true, bool turn_off_simp = false);
lbool solveLimited(const vec<Lit>& assumps, bool do_simp = true, bool turn_off_simp = false); lbool solveLimited(const vec<Lit>& assumps, bool do_simp = true, bool turn_off_simp = false);
int solveLimited(int * lit0, int nlits, bool do_simp = false, bool turn_off_simp = false);
bool solve ( bool do_simp = true, bool turn_off_simp = false); bool solve ( bool do_simp = true, bool turn_off_simp = false);
bool solve (Lit p , bool do_simp = true, bool turn_off_simp = false); bool solve (Lit p , bool do_simp = true, bool turn_off_simp = false);
bool solve (Lit p, Lit q, bool do_simp = true, bool turn_off_simp = false); bool solve (Lit p, Lit q, bool do_simp = true, bool turn_off_simp = false);
bool solve (Lit p, Lit q, Lit r, bool do_simp = true, bool turn_off_simp = false); bool solve (Lit p, Lit q, Lit r, bool do_simp = true, bool turn_off_simp = false);
bool eliminate (bool turn_off_elim = false); // Perform variable elimination based simplification. bool eliminate (bool turn_off_elim = false); // Perform variable elimination based simplification.
void prelocate(int base_var_num){
Solver::prelocate(base_var_num);
frozen .prelocate( base_var_num );
eliminated.prelocate( base_var_num );
if (use_simplification){
n_occ .prelocate( base_var_num << 1 );
occurs .prelocate( base_var_num );
touched .prelocate( base_var_num );
elim_heap .prelocate( base_var_num );
}
}
// Memory managment: // Memory managment:
// //
virtual void reset(); virtual void reset();
...@@ -199,6 +212,14 @@ inline bool SimpSolver::solve (const vec<Lit>& assumps, bool do_simp, boo ...@@ -199,6 +212,14 @@ inline bool SimpSolver::solve (const vec<Lit>& assumps, bool do_simp, boo
inline lbool SimpSolver::solveLimited (const vec<Lit>& assumps, bool do_simp, bool turn_off_simp){ inline lbool SimpSolver::solveLimited (const vec<Lit>& assumps, bool do_simp, bool turn_off_simp){
assumps.copyTo(assumptions); return solve_(do_simp, turn_off_simp); } assumps.copyTo(assumptions); return solve_(do_simp, turn_off_simp); }
inline int SimpSolver::solveLimited(int * lit0, int nlits, bool do_simp, bool turn_off_simp){
assumptions.clear();
for(int i = 0; i < nlits; i ++)
assumptions.push(toLit(lit0[i]));
lbool res = solve_(do_simp, turn_off_simp);
return res == l_True ? 1 : (res == l_False ? -1 : 0);
}
inline void SimpSolver::addVar(Var v) { while (v >= nVars()) newVar(); } inline void SimpSolver::addVar(Var v) { while (v >= nVars()) newVar(); }
//================================================================================================= //=================================================================================================
......
...@@ -707,7 +707,7 @@ void SimpSolver::cleanUpClauses() ...@@ -707,7 +707,7 @@ void SimpSolver::cleanUpClauses()
for (i = j = 0; i < clauses.size(); i++) for (i = j = 0; i < clauses.size(); i++)
if (ca[clauses[i]].mark() == 0) if (ca[clauses[i]].mark() == 0)
clauses[j++] = clauses[i]; clauses[j++] = clauses[i];
clauses.shrink(i - j); clauses.shrink_(i - j);
} }
...@@ -760,18 +760,22 @@ void SimpSolver::reset() ...@@ -760,18 +760,22 @@ void SimpSolver::reset()
Solver::reset(); Solver::reset();
grow = opt_grow; grow = opt_grow;
asymm_lits = eliminated_vars = bwdsub_assigns = n_touched = 0; asymm_lits = eliminated_vars = bwdsub_assigns = n_touched = 0;
elimclauses.clear(false);
touched.clear(false);
occurs.clear(false);
n_occ.clear(false);
elim_heap.clear(false);
subsumption_queue.clear(false); subsumption_queue.clear(false);
frozen.clear(false);
eliminated.clear(false);
vec<Lit> dummy(1,lit_Undef); vec<Lit> dummy(1,lit_Undef);
ca.extra_clause_field = true; // NOTE: must happen before allocating the dummy clause below. ca.extra_clause_field = true; // NOTE: must happen before allocating the dummy clause below.
bwdsub_tmpunit = ca.alloc(dummy); bwdsub_tmpunit = ca.alloc(dummy);
remove_satisfied = false; remove_satisfied = false;
occurs.clear(false);
touched .shrink_( touched .size() );
n_occ .shrink_( n_occ .size() );
eliminated .shrink_( eliminated .size() );
frozen .shrink_( frozen .size() );
elimclauses .shrink_( elimclauses .size() );
elim_heap .clear_(false);
} }
ABC_NAMESPACE_IMPL_END ABC_NAMESPACE_IMPL_END
...@@ -298,6 +298,7 @@ class OccLists ...@@ -298,6 +298,7 @@ class OccLists
OccLists(const Deleted& d) : deleted(d) {} OccLists(const Deleted& d) : deleted(d) {}
void init (const Idx& idx){ occs.growTo(toInt(idx)+1); dirty.growTo(toInt(idx)+1, 0); } void init (const Idx& idx){ occs.growTo(toInt(idx)+1); dirty.growTo(toInt(idx)+1, 0); }
void prelocate (const int num){ occs.prelocate(num); dirty.prelocate(num); }
// Vec& operator[](const Idx& idx){ return occs[toInt(idx)]; } // Vec& operator[](const Idx& idx){ return occs[toInt(idx)]; }
Vec& operator[](const Idx& idx){ return occs[toInt(idx)]; } Vec& operator[](const Idx& idx){ return occs[toInt(idx)]; }
Vec& lookup (const Idx& idx){ if (dirty[toInt(idx)]) clean(idx); return occs[toInt(idx)]; } Vec& lookup (const Idx& idx){ if (dirty[toInt(idx)]) clean(idx); return occs[toInt(idx)]; }
...@@ -332,7 +333,7 @@ void OccLists<Idx,Vec,Deleted>::cleanAll() ...@@ -332,7 +333,7 @@ void OccLists<Idx,Vec,Deleted>::cleanAll()
// Dirties may contain duplicates so check here if a variable is already cleaned: // Dirties may contain duplicates so check here if a variable is already cleaned:
if (dirty[toInt(dirties[i])]) if (dirty[toInt(dirties[i])])
clean(dirties[i]); clean(dirties[i]);
dirties.clear(); dirties.shrink_( dirties.size() );
} }
...@@ -344,7 +345,7 @@ void OccLists<Idx,Vec,Deleted>::clean(const Idx& idx) ...@@ -344,7 +345,7 @@ void OccLists<Idx,Vec,Deleted>::clean(const Idx& idx)
for (i = j = 0; i < vec.size(); i++) for (i = j = 0; i < vec.size(); i++)
if (!deleted(vec[i])) if (!deleted(vec[i]))
vec[j++] = vec[i]; vec[j++] = vec[i];
vec.shrink(i - j); vec.shrink_(i - j);
dirty[toInt(idx)] = 0; dirty[toInt(idx)] = 0;
} }
......
...@@ -67,7 +67,9 @@ public: ...@@ -67,7 +67,9 @@ public:
void shrink_ (int nelems) { assert(nelems <= sz); sz -= nelems; } void shrink_ (int nelems) { assert(nelems <= sz); sz -= nelems; }
int capacity (void) const { return cap; } int capacity (void) const { return cap; }
void capacity (int min_cap); void capacity (int min_cap);
void prelocate(int ext_cap);
void growTo (int size); void growTo (int size);
void growTo_ (int size);
void growTo (int size, const T& pad); void growTo (int size, const T& pad);
void clear (bool dealloc = false); void clear (bool dealloc = false);
...@@ -90,7 +92,7 @@ public: ...@@ -90,7 +92,7 @@ public:
// Duplicatation (preferred instead): // Duplicatation (preferred instead):
void copyTo (vec<T>& copy) const { copy.clear(); copy.growTo(sz); for (int i = 0; i < sz; i++) copy[i] = data[i]; } void copyTo (vec<T>& copy) const { copy.clear(); copy.growTo(sz); for (int i = 0; i < sz; i++) copy[i] = data[i]; }
void copyTo_(vec<T>& copy) const { copy.shrink_(copy.size()); copy.growTo(sz); for (int i = 0; i < sz; i++) copy[i] = data[i]; } void copyTo_(vec<T>& copy) const { copy.shrink_(copy.size()); copy.growTo_(sz); for (int i = 0; i < sz; i++) copy[i] = data[i]; }
void moveTo(vec<T>& dest) { dest.clear(true); dest.data = data; dest.sz = sz; dest.cap = cap; data = NULL; sz = 0; cap = 0; } void moveTo(vec<T>& dest) { dest.clear(true); dest.data = data; dest.sz = sz; dest.cap = cap; data = NULL; sz = 0; cap = 0; }
}; };
...@@ -103,6 +105,14 @@ void vec<T>::capacity(int min_cap) { ...@@ -103,6 +105,14 @@ void vec<T>::capacity(int min_cap) {
throw OutOfMemoryException(); throw OutOfMemoryException();
} }
template<class T>
void vec<T>::prelocate(int ext_cap) {
if (cap >= ext_cap) return;
if (ext_cap > INT_MAX || (((data = (T*)::realloc(data, ext_cap * sizeof(T))) == NULL) && errno == ENOMEM))
throw OutOfMemoryException();
cap = ext_cap;
}
template<class T> template<class T>
void vec<T>::growTo(int size, const T& pad) { void vec<T>::growTo(int size, const T& pad) {
...@@ -121,6 +131,13 @@ void vec<T>::growTo(int size) { ...@@ -121,6 +131,13 @@ void vec<T>::growTo(int size) {
template<class T> template<class T>
void vec<T>::growTo_(int size) {
if (sz >= size) return;
capacity(size);
sz = size; }
template<class T>
void vec<T>::clear(bool dealloc) { void vec<T>::clear(bool dealloc) {
if (data != NULL){ if (data != NULL){
for (int i = 0; i < sz; i++) data[i].~T(); for (int i = 0; i < sz; i++) data[i].~T();
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment