]> git.unchartedbackwaters.co.uk Git - francis/stp.git/commitdiff
Importing CryptoMiniSat version 'Cluster56'.
authormsoos <msoos@e59a4935-1847-0410-ae03-e826735625c1>
Fri, 4 Jun 2010 17:56:12 +0000 (17:56 +0000)
committermsoos <msoos@e59a4935-1847-0410-ae03-e826735625c1>
Fri, 4 Jun 2010 17:56:12 +0000 (17:56 +0000)
git-svn-id: https://stp-fast-prover.svn.sourceforge.net/svnroot/stp-fast-prover/trunk/stp@812 e59a4935-1847-0410-ae03-e826735625c1

38 files changed:
src/sat/cryptominisat2/BitArray.h
src/sat/cryptominisat2/BoundedQueue.h
src/sat/cryptominisat2/CSet.h
src/sat/cryptominisat2/Clause.cpp
src/sat/cryptominisat2/Clause.h
src/sat/cryptominisat2/ClauseCleaner.cpp
src/sat/cryptominisat2/ClauseCleaner.h
src/sat/cryptominisat2/Conglomerate.cpp
src/sat/cryptominisat2/Conglomerate.h
src/sat/cryptominisat2/DoublePackedRow.h
src/sat/cryptominisat2/FailedVarSearcher.cpp
src/sat/cryptominisat2/FailedVarSearcher.h
src/sat/cryptominisat2/FindUndef.cpp
src/sat/cryptominisat2/FindUndef.h
src/sat/cryptominisat2/Gaussian.cpp
src/sat/cryptominisat2/Gaussian.h
src/sat/cryptominisat2/GaussianConfig.h
src/sat/cryptominisat2/Logger.cpp
src/sat/cryptominisat2/Logger.h
src/sat/cryptominisat2/Makefile
src/sat/cryptominisat2/MatrixFinder.cpp
src/sat/cryptominisat2/MatrixFinder.h
src/sat/cryptominisat2/MersenneTwister.h
src/sat/cryptominisat2/PartFinder.cpp
src/sat/cryptominisat2/PartHandler.cpp
src/sat/cryptominisat2/Solver.cpp
src/sat/cryptominisat2/Solver.h
src/sat/cryptominisat2/SolverTypes.h
src/sat/cryptominisat2/StateSaver.cpp [new file with mode: 0644]
src/sat/cryptominisat2/StateSaver.h [new file with mode: 0644]
src/sat/cryptominisat2/Subsumer.cpp
src/sat/cryptominisat2/Subsumer.h
src/sat/cryptominisat2/VarReplacer.cpp
src/sat/cryptominisat2/VarReplacer.h
src/sat/cryptominisat2/XorFinder.cpp
src/sat/cryptominisat2/XorSubsumer.cpp
src/sat/cryptominisat2/XorSubsumer.h
src/sat/cryptominisat2/constants.h

index 1e52009823c75de3aa820bcdcbc74774cf138d8b..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,141 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef BITARRAY_H
-#define BITARRAY_H
-
-//#define DEBUG_BITARRAY
-
-#include <string.h>
-#include <assert.h>
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class BitArray
-{
-public:
-    BitArray() :
-        size(0)
-        , mp(NULL)
-    {
-    }
-    
-    BitArray(const BitArray& b) :
-        size(b.size)
-    {
-        mp = new uint64_t[size];
-        memcpy(mp, b.mp, sizeof(uint64_t)*size);
-    }
-    
-    BitArray& operator=(const BitArray& b)
-    {
-        if (size != b.size) {
-            delete[] mp;
-            size = b.size;
-            mp = new uint64_t[size];
-        }
-        memcpy(mp, b.mp, sizeof(uint64_t)*size);
-        
-        return *this;
-    }
-    
-    void resize(uint _size, const bool fill)
-    {
-        _size = _size/64 + (bool)(_size%64);
-        if (size != _size) {
-            delete[] mp;
-            size = _size;
-            mp = new uint64_t[size];
-        }
-        if (fill) setOne();
-        else setZero();
-    }
-    
-    ~BitArray()
-    {
-        delete[] mp;
-    }
-
-    inline const bool isZero() const
-    {
-        const uint64_t*  mp2 = (const uint64_t*)mp;
-        
-        for (uint i = 0; i < size; i++) {
-            if (mp2[i]) return false;
-        }
-        return true;
-    }
-
-    inline void setZero()
-    {
-        memset(mp, 0, size*sizeof(uint64_t));
-    }
-    
-    inline void setOne()
-    {
-        memset(mp, 0, size*sizeof(uint64_t));
-    }
-
-    inline void clearBit(const uint i)
-    {
-        #ifdef DEBUG_BITARRAY
-        assert(size*64 > i);
-        #endif
-        
-        mp[i/64] &= ~((uint64_t)1 << (i%64));
-    }
-
-    inline void setBit(const uint i)
-    {
-        #ifdef DEBUG_BITARRAY
-        assert(size*64 > i);
-        #endif
-        
-        mp[i/64] |= ((uint64_t)1 << (i%64));
-    }
-
-    inline const bool operator[](const uint& i) const
-    {
-        #ifdef DEBUG_BITARRAY
-        assert(size*64 > i);
-        #endif
-        
-        return (mp[i/64] >> (i%64)) & 1;
-    }
-    
-    inline const uint getSize() const
-    {
-        return size*64;
-    }
-
-private:
-    
-    uint size;
-    uint64_t* mp;
-};
-
-}; //NAMESPACE MINISAT
-
-#endif //BITARRAY_H
-
index a705a6dc0fe41ce4863fa61e574f6e418583ddd5..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,88 +0,0 @@
-/*****************************************************************************************[Queue.h]
-MiniSat -- Copyright (c) 2003-2006, Niklas Een, Niklas Sorensson
-  2008 - Gilles Audemard, Laurent Simon
-
-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 BoundedQueue_h
-#define BoundedQueue_h
-
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-#include "Vec.h"
-
-//=================================================================================================
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-template <class T>
-class bqueue {
-    vec<T>  elems;
-    int     first;
-    int     last;
-    uint64_t sumofqueue;
-    int     maxsize;
-    int     queuesize; // Number of current elements (must be < maxsize !)
-    
-public:
-    bqueue(void) : first(0), last(0), sumofqueue(0), maxsize(0), queuesize(0) { } 
-    
-    void initSize(int size) {growTo(size);} // Init size of bounded size queue
-    
-    void push(T x) {
-        if (queuesize==maxsize) {
-            assert(last==first); // The queue is full, next value to enter will replace oldest one
-            sumofqueue -= elems[last];
-            if ((++last) == maxsize) last = 0;
-        } else 
-            queuesize++;
-        sumofqueue += x;
-        elems[first] = x;
-        if ((++first) == maxsize) first = 0;
-    }
-
-    T peek() { assert(queuesize>0); return elems[last]; }
-    void pop() {sumofqueue-=elems[last]; queuesize--; if ((++last) == maxsize) last = 0;}
-    
-    uint64_t getsum() const {return sumofqueue;}
-    uint32_t getavg() const {return (uint64_t)sumofqueue/(uint64_t)queuesize;}
-    int isvalid() const {return (queuesize==maxsize);}
-    
-    void growTo(int size) {
-        elems.growTo(size); 
-        first=0; maxsize=size; queuesize = 0;
-        for(int i=0;i<size;i++) elems[i]=0; 
-    }
-
-    void fastclear() {first = 0; last = 0; queuesize=0; sumofqueue=0;} // to be called after restarts... Discard the queue
-    
-    int  size(void)    { return queuesize; }
-
-    void clear(bool dealloc = false)   { elems.clear(dealloc); first = 0; maxsize=0; queuesize=0;sumofqueue=0;}
-};
-
-//=================================================================================================
-
-}; //namespace MINISAT
-
-#endif
index cf8661a0df70248fc08b96f8c50b074ccf21ce7d..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,136 +0,0 @@
-/**************************************************************************************************
-From: Solver.C -- (C) Niklas Een, Niklas Sorensson, 2004
-**************************************************************************************************/
-
-#ifndef CSET_H
-#define CSET_H
-
-#include "Vec.h"
-#include <limits>
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class Clause;
-
-template <class T>
-uint32_t calcAbstraction(const T& ps) {
-    uint32_t abstraction = 0;
-    for (uint32_t i = 0; i != ps.size(); i++)
-        abstraction |= 1 << (ps[i].toInt() & 31);
-    return abstraction;
-}
-
-//#pragma pack(push)
-//#pragma pack(1)
-class ClauseSimp
-{
-    public:
-        ClauseSimp(Clause* c, const uint32_t _index) :
-        clause(c)
-        , index(_index)
-        {}
-        
-        Clause* clause;
-        uint32_t index;
-};
-//#pragma pack(pop)
-
-class CSet {
-    vec<uint32_t>       where;  // Map clause ID to position in 'which'.
-    vec<ClauseSimp> which;  // List of clauses (for fast iteration). May contain 'Clause_NULL'.
-    vec<uint32_t>       free;   // List of positions holding 'Clause_NULL'.
-    
-    public:
-        //ClauseSimp& operator [] (uint32_t index) { return which[index]; }
-        void reserve(uint32_t size) { where.reserve(size);}
-        uint32_t size(void) const { return which.size(); }
-        uint32_t nElems(void) const { return which.size() - free.size(); }
-        
-        bool add(const ClauseSimp& c) {
-            assert(c.clause != NULL);
-            where.growTo(c.index+1, std::numeric_limits<uint32_t>::max());
-            if (where[c.index] != std::numeric_limits<uint32_t>::max()) {
-                return true;
-            }
-            if (free.size() > 0){
-                where[c.index] = free.last();
-                which[free.last()] = c;
-                free.pop();
-            }else{
-                where[c.index] = which.size();
-                which.push(c);
-            }
-            return false;
-        }
-        
-        bool exclude(const ClauseSimp& c) {
-            assert(c.clause != NULL);
-            if (c.index >= where.size() || where[c.index] == std::numeric_limits<uint32_t>::max()) {
-                //not inside
-                return false;
-            }
-            free.push(where[c.index]);
-            which[where[c.index]].clause = NULL;
-            where[c.index] = std::numeric_limits<uint32_t>::max();
-            return true;
-        }
-        
-        void clear(void) {
-            for (uint32_t i = 0; i < which.size(); i++)  {
-                if (which[i].clause != NULL) {
-                    where[which[i].index] = std::numeric_limits<uint32_t>::max();
-                }
-            }
-            which.clear();
-            free.clear();
-        }
-        
-        class iterator
-        {
-            public:
-                iterator(ClauseSimp* _it) :
-                it(_it)
-                {}
-                
-                void operator++()
-                {
-                    it++;
-                }
-                
-                const bool operator!=(const iterator& iter) const
-                {
-                    return (it != iter.it);;
-                }
-                
-                ClauseSimp& operator*() {
-                    return *it;
-                }
-                
-                ClauseSimp*& operator->() {
-                    return it;
-                }
-            private:
-                ClauseSimp* it;
-        };
-        
-        iterator begin()
-        {
-            return iterator(which.getData());
-        }
-        
-        iterator end()
-        {
-            return iterator(which.getData() + which.size());
-        }
-};
-
-}; //NAMESPACE MINISAT
-
-#endif //CSET_H
\ No newline at end of file
index b2bc8bc781ac19880763375a480b24c0ab002b54..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,3 +0,0 @@
-#include "Clause.h"
-
-//boost::pool<> binaryClausePool(sizeof(Clause)+2*sizeof(Lit));
index 5969fd3ac67393a2cb4afa143317b63242ff0b96..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,415 +0,0 @@
-/***********************************************************************************[SolverTypes.h]
-MiniSat -- Copyright (c) 2003-2006, Niklas Een, Niklas Sorensson
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-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 CLAUSE_H
-#define CLAUSE_H
-
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include "SmallPtr.h"
-#include <stdint.h>
-#endif //_MSC_VER
-#include <cstdio>
-#include <vector>
-#include <sys/types.h>
-#include "Vec.h"
-#include "SolverTypes.h"
-#include "PackedRow.h"
-#include "constants.h"
-//#include "pool.hpp"
-#ifndef uint
-#define uint unsigned int
-#endif
-
-using std::vector;
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-//=================================================================================================
-// Clause -- a simple class for representing a clause:
-
-class MatrixFinder;
-
-class Clause
-{
-protected:
-    
-    #ifdef STATS_NEEDED
-    uint group;
-    #endif
-    
-    uint32_t isLearnt:1;
-    uint32_t strenghtened:1;
-    uint32_t varChanged:1;
-    uint32_t sorted:1;
-    uint32_t invertedXor:1;
-    uint32_t isXorClause:1;
-    uint32_t subsume0Done:1;
-    uint32_t mySize:20;
-    
-    union  {int32_t act; uint32_t abst;} extra;
-    float oldActivityInter;
-    #ifdef _MSC_VER
-    Lit     data[1];
-    #else
-    Lit     data[0];
-    #endif //_MSC_VER
-
-#ifdef _MSC_VER
-public:
-#endif //_MSC_VER
-    template<class V>
-    Clause(const V& ps, const uint _group, const bool learnt)
-    {
-        isXorClause = false;
-        strenghtened = false;
-        sorted = false;
-        varChanged = true;
-        subsume0Done = false;
-        mySize = ps.size();
-        isLearnt = learnt;
-        setGroup(_group);
-        for (uint i = 0; i < ps.size(); i++) data[i] = ps[i];
-        if (learnt) {
-            extra.act = 0;
-            oldActivityInter = 0;
-        } else
-            calcAbstraction();
-    }
-
-public:
-    #ifndef _MSC_VER
-    // -- use this function instead:
-    template<class T>
-    friend Clause* Clause_new(const T& ps, const uint group, const bool learnt = false);
-    #endif //_MSC_VER
-
-    const uint   size        ()      const {
-        return mySize;
-    }
-    void         resize      (const uint size) {
-        mySize = size;
-    }
-    void         shrink      (const uint i) {
-        assert(i <= size());
-        mySize -= i;
-    }
-    void         pop         () {
-        shrink(1);
-    }
-    const bool   isXor       () {
-        return isXorClause;
-    }
-    const bool   learnt      ()      const {
-        return isLearnt;
-    }
-    float&       oldActivity    () {
-        return oldActivityInter;
-    }
-    
-    const float&       oldActivity    () const {
-        return oldActivityInter;
-    }
-    
-    
-    const bool getStrenghtened() const {
-        return strenghtened;
-    }
-    void setStrenghtened() {
-        strenghtened = true;
-        sorted = false;
-        subsume0Done = false;
-    }
-    void unsetStrenghtened() {
-        strenghtened = false;
-    }
-    const bool getVarChanged() const {
-        return varChanged;
-    }
-    void setVarChanged() {
-        varChanged = true;
-        sorted = false;
-        subsume0Done = false;
-    }
-    void unsetVarChanged() {
-        varChanged = false;
-    }
-    const bool getSorted() const {
-        return sorted;
-    }
-    void setSorted() {
-        sorted = true;
-    }
-    void setUnsorted() {
-        sorted = false;
-    }
-    void subsume0Finished() {
-        subsume0Done = 1;
-    }
-    const bool subsume0IsFinished() {
-        return subsume0Done;
-    }
-
-    Lit&         operator [] (uint32_t i) {
-        return data[i];
-    }
-    const Lit&   operator [] (uint32_t i) const {
-        return data[i];
-    }
-
-    void         setActivity(int i)  {
-        extra.act = i;
-    }
-    
-    const int&   activity   () const {
-        return extra.act;
-    }
-    
-    void         makeNonLearnt()  {
-        assert(isLearnt);
-        isLearnt = false;
-        calcAbstraction();
-    }
-    
-    void         makeLearnt(const uint32_t newActivity)  {
-        extra.act = newActivity;
-        isLearnt = true;
-    }
-    
-    inline void  strengthen(const Lit p)
-    {
-        remove(*this, p);
-        sorted = false;
-        calcAbstraction();
-    }
-    
-    void calcAbstraction() {
-        extra.abst = 0;
-        for (uint32_t i = 0; i != size(); i++)
-            extra.abst |= 1 << (data[i].toInt() & 31);
-    }
-    
-    uint32_t getAbst()
-    {
-        return extra.abst;
-    }
-
-    const Lit*     getData     () const {
-        return data;
-    }
-    Lit*    getData     () {
-        return data;
-    }
-    const Lit*     getDataEnd     () const {
-        return data+size();
-    }
-    Lit*    getDataEnd     () {
-        return data+size();
-    }
-    void print() {
-        printf("Clause   group: %d, size: %d, learnt:%d, lits: ", getGroup(), size(), learnt());
-        plainPrint();
-    }
-    void plainPrint(FILE* to = stdout) const {
-        for (uint i = 0; i < size(); i++) {
-            if (data[i].sign()) fprintf(to, "-");
-            fprintf(to, "%d ", data[i].var() + 1);
-        }
-        fprintf(to, "0\n");
-    }
-    #ifdef STATS_NEEDED
-    const uint32_t getGroup() const
-    {
-        return group;
-    }
-    void setGroup(const uint32_t _group)
-    {
-        group = _group;
-    }
-    #else
-    const uint getGroup() const
-    {
-        return 0;
-    }
-    void setGroup(const uint32_t _group)
-    {
-        return;
-    }
-    #endif //STATS_NEEDED
-};
-
-class XorClause : public Clause
-{
-    
-#ifdef _MSC_VER
-public:
-#else //_MSC_VER
-protected:
-#endif //_MSC_VER
-
-    // NOTE: This constructor cannot be used directly (doesn't allocate enough memory).
-    template<class V>
-    XorClause(const V& ps, const bool inverted, const uint _group) :
-        Clause(ps, _group, false)
-    {
-        invertedXor = inverted;
-        isXorClause = true;
-        calcXorAbstraction();
-    }
-
-public:
-    #ifndef _MSC_VER
-    // -- use this function instead:
-    template<class V>
-    friend XorClause* XorClause_new(const V& ps, const bool inverted, const uint group);
-    #endif //_MSC_VER
-
-    inline bool xor_clause_inverted() const
-    {
-        return invertedXor;
-    }
-    inline void invert(bool b)
-    {
-        invertedXor ^= b;
-    }
-    void calcXorAbstraction() {
-        extra.abst = 0;
-        for (uint32_t i = 0; i != size(); i++)
-            extra.abst |= 1 << (data[i].var() & 31);
-    }
-
-    void print() {
-        printf("XOR Clause   group: %d, size: %d, learnt:%d, lits:\"", getGroup(), size(), learnt());
-        plainPrint();
-    }
-    
-    void plainPrint(FILE* to = stdout) const {
-        fprintf(to, "x");
-        if (xor_clause_inverted())
-            printf("-");
-        for (uint i = 0; i < size(); i++) {
-            fprintf(to, "%d ", data[i].var() + 1);
-        }
-        fprintf(to, "0\n");
-    }
-    
-    friend class MatrixFinder;
-};
-
-//extern boost::pool<> binaryClausePool;
-
-template<class T>
-Clause* Clause_new(const T& ps, const uint group, const bool learnt = false)
-{
-    void* mem;
-    //if (ps.size() != 2)
-        mem = malloc(sizeof(Clause) + sizeof(Lit)*(ps.size()));
-    //else
-    //    mem = binaryClausePool.malloc();
-    Clause* real= new (mem) Clause(ps, group, learnt);
-    return real;
-}
-
-template<class T>
-XorClause* XorClause_new(const T& ps, const bool inverted, const uint group)
-{
-    void* mem = malloc(sizeof(XorClause) + sizeof(Lit)*(ps.size()));
-    XorClause* real= new (mem) XorClause(ps, inverted, group);
-    return real;
-}
-
-inline void clauseFree(Clause* c)
-{
-    //if (binaryClausePool.is_from(c)) binaryClausePool.free(c);
-    //else 
-    free(c);
-}
-
-/*_________________________________________________________________________________________________
-|
-|  subsumes : (other : const Clause&)  ->  Lit
-|
-|  Description:
-|       Checks if clause subsumes 'other', and at the same time, if it can be used to simplify 'other'
-|       by subsumption resolution.
-|
-|    Result:
-|       lit_Error  - No subsumption or simplification
-|       lit_Undef  - Clause subsumes 'other'
-|       p          - The literal p can be deleted from 'other'
-|________________________________________________________________________________________________@*/
-/*inline Lit Clause::subsumes(const Clause& other) const
-{
-    if (other.size() < size() || (extra.abst & ~other.extra.abst) != 0)
-        return lit_Error;
-    
-    Lit        ret = lit_Undef;
-    const Lit* c  = this->getData();
-    const Lit* d  = other.getData();
-    
-    for (uint32_t i = 0; i != size(); i++) {
-        // search for c[i] or ~c[i]
-        for (uint32_t j = 0; j != other.size(); j++)
-            if (c[i] == d[j])
-                goto ok;
-            else if (ret == lit_Undef && c[i] == ~d[j]){
-                ret = c[i];
-                goto ok;
-            }
-            
-            // did not find it
-            return lit_Error;
-        ok:;
-    }
-    
-    return ret;
-}*/
-
-#ifdef _MSC_VER
-typedef Clause* ClausePtr;
-typedef XorClause* XorClausePtr;
-#else
-typedef sptr<Clause> ClausePtr;
-typedef sptr<XorClause> XorClausePtr;
-#endif //_MSC_VER
-
-#pragma pack(push)
-#pragma pack(1)
-class WatchedBin {
-    public:
-        WatchedBin(Clause *_clause, Lit _impliedLit) : clause(_clause), impliedLit(_impliedLit) {};
-        ClausePtr clause;
-        Lit impliedLit;
-};
-
-class Watched {
-    public:
-        Watched(Clause *_clause, Lit _blockedLit) : clause(_clause), blockedLit(_blockedLit) {};
-        ClausePtr clause;
-        Lit blockedLit;
-};
-#pragma pack(pop)
-
-}; //NAMESPACE MINISAT
-
-#endif //CLAUSE_H
index 7f4610b2030ac5d59cdb5e01ca753f184e18ece7..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,369 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#include "ClauseCleaner.h"
-#include "VarReplacer.h"
-
-#ifdef _MSC_VER
-#define __builtin_prefetch(a,b,c)
-#endif //_MSC_VER
-
-//#define DEBUG_CLEAN
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-ClauseCleaner::ClauseCleaner(Solver& _solver) :
-    solver(_solver)
-{
-    for (uint i = 0; i < 6; i++) {
-        lastNumUnitarySat[i] = solver.get_unitary_learnts_num();
-        lastNumUnitaryClean[i] = solver.get_unitary_learnts_num();
-    }
-}
-
-void ClauseCleaner::removeSatisfied(vec<XorClause*>& cs, ClauseSetType type, const uint limit)
-{
-    #ifdef DEBUG_CLEAN
-    assert(solver.decisionLevel() == 0);
-    #endif
-    
-    if (lastNumUnitarySat[type] + limit >= solver.get_unitary_learnts_num())
-        return;
-    
-    uint32_t i,j;
-    for (i = j = 0; i < cs.size(); i++) {
-        if (satisfied(*cs[i]))
-            solver.removeClause(*cs[i]);
-        else
-            cs[j++] = cs[i];
-    }
-    cs.shrink(i - j);
-    
-    lastNumUnitarySat[type] = solver.get_unitary_learnts_num();
-}
-
-void ClauseCleaner::removeSatisfied(vec<Clause*>& cs, ClauseSetType type, const uint limit)
-{
-    #ifdef DEBUG_CLEAN
-    assert(solver.decisionLevel() == 0);
-    #endif
-    
-    if (lastNumUnitarySat[type] + limit >= solver.get_unitary_learnts_num())
-        return;
-    
-    Clause **i,**j, **end;
-    for (i = j = cs.getData(), end = i + cs.size(); i != end; i++) {
-        if (i+1 != end)
-            __builtin_prefetch(*(i+1), 0, 0);
-        if (satisfied(**i))
-            solver.removeClause(**i);
-        else
-            *j++ = *i;
-    }
-    cs.shrink(i - j);
-    
-    lastNumUnitarySat[type] = solver.get_unitary_learnts_num();
-}
-
-void ClauseCleaner::cleanClauses(vec<Clause*>& cs, ClauseSetType type, const uint limit)
-{
-    assert(solver.decisionLevel() == 0);
-    assert(solver.qhead == solver.trail.size());
-    
-    if (lastNumUnitaryClean[type] + limit >= solver.get_unitary_learnts_num())
-        return;
-    
-    Clause **s, **ss, **end;
-    for (s = ss = cs.getData(), end = s + cs.size();  s != end;) {
-        if (s+1 != end)
-            __builtin_prefetch(*(s+1), 1, 0);
-        if (cleanClause(**s)) {
-            clauseFree(*s);
-            s++;
-        } else if (type != ClauseCleaner::binaryClauses && (*s)->size() == 2) {
-            solver.binaryClauses.push(*s);
-            solver.becameBinary++;
-            s++;
-        } else {
-            *ss++ = *s++;
-        }
-    }
-    cs.shrink(s-ss);
-    
-    lastNumUnitaryClean[type] = solver.get_unitary_learnts_num();
-    
-    #ifdef VERBOSE_DEBUG
-    cout << "cleanClauses(Clause) useful ?? Removed: " << s-ss << endl;
-    #endif
-}
-
-inline const bool ClauseCleaner::cleanClause(Clause& c)
-{
-    Lit origLit1 = c[0];
-    Lit origLit2 = c[1];
-    uint32_t origSize = c.size();
-    
-    Lit *i, *j, *end;
-    for (i = j = c.getData(), end = i + c.size();  i != end; i++) {
-        lbool val = solver.value(*i);
-        if (val == l_Undef) {
-            *j++ = *i;
-            continue;
-        }
-        
-        if (val == l_True) {
-            solver.detachModifiedClause(origLit1, origLit2, origSize, &c);
-            return true;
-        }
-    }
-    
-    if ((c.size() > 2) && (c.size() - (i-j) == 2)) {
-        solver.detachModifiedClause(origLit1, origLit2, c.size(), &c);
-        c.shrink(i-j);
-        c.setStrenghtened();
-        solver.attachClause(c);
-    } else if (i != j) {
-        c.setStrenghtened();
-        c.shrink(i-j);
-        if (c.learnt())
-            solver.learnts_literals -= i-j;
-        else
-            solver.clauses_literals -= i-j;
-    }
-    
-    return false;
-}
-
-void ClauseCleaner::cleanClauses(vec<XorClause*>& cs, ClauseSetType type, const uint limit)
-{
-    assert(solver.decisionLevel() == 0);
-    assert(solver.qhead == solver.trail.size());
-    
-    if (lastNumUnitaryClean[type] + limit >= solver.get_unitary_learnts_num())
-        return;
-    
-    XorClause **s, **ss, **end;
-    for (s = ss = cs.getData(), end = s + cs.size();  s != end;) {
-        if (s+1 != end)
-            __builtin_prefetch(*(s+1), 1, 0);
-        if (cleanClause(**s)) {
-            free(*s);
-            s++;
-        } else {
-            *ss++ = *s++;
-        }
-    }
-    cs.shrink(s-ss);
-    
-    lastNumUnitaryClean[type] = solver.get_unitary_learnts_num();
-    
-    #ifdef VERBOSE_DEBUG
-    cout << "cleanClauses(XorClause) useful: ?? Removed: " << s-ss << endl;
-    #endif
-}
-
-inline const bool ClauseCleaner::cleanClause(XorClause& c)
-{
-    Lit *i, *j, *end;
-    Var origVar1 = c[0].var();
-    Var origVar2 = c[1].var();
-    uint32_t origSize = c.size();
-    for (i = j = c.getData(), end = i + c.size();  i != end; i++) {
-        const lbool& val = solver.assigns[i->var()];
-        if (val.isUndef()) {
-            *j = *i;
-            j++;
-        } else c.invert(val.getBool());
-    }
-    c.shrink(i-j);
-    
-    switch (c.size()) {
-        case 0: {
-            solver.detachModifiedClause(origVar1, origVar2, origSize, &c);
-            return true;
-        }
-        case 2: {
-            vec<Lit> ps(2);
-            ps[0] = c[0].unsign();
-            ps[1] = c[1].unsign();
-            solver.varReplacer->replace(ps, c.xor_clause_inverted(), c.getGroup());
-            solver.detachModifiedClause(origVar1, origVar2, origSize, &c);
-            return true;
-        }
-        default:
-            if (i-j > 0) {
-                c.setStrenghtened();
-                solver.clauses_literals -= i-j;
-            }
-            return false;
-    }
-}
-
-void ClauseCleaner::cleanClausesBewareNULL(vec<ClauseSimp>& cs, ClauseCleaner::ClauseSetType type, Subsumer& subs, const uint limit)
-{
-    assert(solver.decisionLevel() == 0);
-    assert(solver.qhead == solver.trail.size());
-    
-    if (lastNumUnitaryClean[type] + limit >= solver.get_unitary_learnts_num())
-        return;
-    
-    ClauseSimp *s, *end;
-    for (s = cs.getData(), end = s + cs.size();  s != end; s++) {
-        if (s+1 != end)
-            __builtin_prefetch((s+1)->clause, 1, 0);
-        if (s->clause == NULL)
-            continue;
-        
-        if (cleanClauseBewareNULL(*s, subs)) {
-            continue;
-        } else if (s->clause->size() == 2)
-            solver.becameBinary++;
-    }
-    
-    lastNumUnitaryClean[type] = solver.get_unitary_learnts_num();
-}
-
-inline const bool ClauseCleaner::cleanClauseBewareNULL(ClauseSimp cc, Subsumer& subs)
-{
-    Clause& c = *cc.clause;
-    vec<Lit> origClause(c.size());
-    memcpy(origClause.getData(), c.getData(), sizeof(Lit)*c.size());
-    
-    Lit *i, *j, *end;
-    for (i = j = c.getData(), end = i + c.size();  i != end; i++) {
-        lbool val = solver.value(*i);
-        if (val == l_Undef) {
-            *j++ = *i;
-            continue;
-        }
-        
-        if (val == l_True) {
-            subs.unlinkModifiedClause(origClause, cc);
-            free(cc.clause);
-            return true;
-        }
-    }
-    
-    if (i != j) {
-        c.setStrenghtened();
-        if (origClause.size() > 2 && origClause.size()-(i-j) == 2) {
-            subs.unlinkModifiedClause(origClause, cc);
-            subs.clauses[cc.index] = cc;
-            c.shrink(i-j);
-            solver.attachClause(c);
-            subs.linkInAlreadyClause(cc);
-        } else {
-            c.shrink(i-j);
-            subs.unlinkModifiedClauseNoDetachNoNULL(origClause, cc);
-            subs.linkInAlreadyClause(cc);
-            if (c.learnt())
-                solver.learnts_literals -= i-j;
-            else
-                solver.clauses_literals -= i-j;
-        }
-        c.calcAbstraction();
-        subs.updateClause(cc);
-    }
-    
-    return false;
-}
-
-void ClauseCleaner::cleanXorClausesBewareNULL(vec<XorClauseSimp>& cs, ClauseCleaner::ClauseSetType type, XorSubsumer& subs, const uint limit)
-{
-    assert(solver.decisionLevel() == 0);
-    assert(solver.qhead == solver.trail.size());
-    
-    if (lastNumUnitaryClean[type] + limit >= solver.get_unitary_learnts_num())
-        return;
-    
-    XorClauseSimp *s, *end;
-    for (s = cs.getData(), end = s + cs.size();  s != end; s++) {
-        if (s+1 != end)
-            __builtin_prefetch((s+1)->clause, 1, 0);
-        if (s->clause == NULL)
-            continue;
-        
-        cleanXorClauseBewareNULL(*s, subs);
-    }
-    
-    lastNumUnitaryClean[type] = solver.get_unitary_learnts_num();
-}
-
-inline const bool ClauseCleaner::cleanXorClauseBewareNULL(XorClauseSimp cc, XorSubsumer& subs)
-{
-    XorClause& c = *cc.clause;
-    vec<Lit> origClause(c.size());
-    memcpy(origClause.getData(), c.getData(), sizeof(Lit)*c.size());
-    
-    Lit *i, *j, *end;
-    for (i = j = c.getData(), end = i + c.size();  i != end; i++) {
-        const lbool& val = solver.assigns[i->var()];
-        if (val.isUndef()) {
-            *j = *i;
-            j++;
-        } else c.invert(val.getBool());
-    }
-    c.shrink(i-j);
-    
-    switch(c.size()) {
-        case 0: {
-            subs.unlinkModifiedClause(origClause, cc);
-            free(cc.clause);
-            return true;
-        }
-        case 2: {
-            vec<Lit> ps(2);
-            ps[0] = c[0].unsign();
-            ps[1] = c[1].unsign();
-            solver.varReplacer->replace(ps, c.xor_clause_inverted(), c.getGroup());
-            subs.unlinkModifiedClause(origClause, cc);
-            free(cc.clause);
-            return true;
-        }
-        default:
-            if (i-j > 0) {
-                subs.unlinkModifiedClauseNoDetachNoNULL(origClause, cc);
-                subs.linkInAlreadyClause(cc);
-                c.calcXorAbstraction();
-            }
-    }
-    
-    return false;
-}
-
-bool ClauseCleaner::satisfied(const Clause& c) const
-{
-    for (uint i = 0; i != c.size(); i++)
-        if (solver.value(c[i]) == l_True)
-            return true;
-        return false;
-}
-
-bool ClauseCleaner::satisfied(const XorClause& c) const
-{
-    bool final = c.xor_clause_inverted();
-    for (uint k = 0; k != c.size(); k++ ) {
-        const lbool& val = solver.assigns[c[k].var()];
-        if (val.isUndef()) return false;
-        final ^= val.getBool();
-    }
-    return final;
-}
-
-}; //NAMESPACE MINISAT
index c099ae2f039c7d2dec8a54546515765f351c6c61..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,79 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef CLAUSECLEANER_H
-#define CLAUSECLEANER_H
-
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-#include "Solver.h"
-#include "Subsumer.h"
-#include "XorSubsumer.h"
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class ClauseCleaner
-{
-    public:
-        ClauseCleaner(Solver& solver);
-        
-        enum ClauseSetType {clauses, xorclauses, learnts, binaryClauses, simpClauses, xorSimpClauses};
-        
-        void cleanClauses(vec<Clause*>& cs, ClauseSetType type, const uint limit = 0);
-        void cleanClausesBewareNULL(vec<ClauseSimp>& cs, ClauseSetType type, Subsumer& subs, const uint limit = 0);
-        void cleanXorClausesBewareNULL(vec<XorClauseSimp>& cs, ClauseSetType type, XorSubsumer& subs, const uint limit = 0);
-        const bool cleanClauseBewareNULL(ClauseSimp c, Subsumer& subs);
-        const bool cleanXorClauseBewareNULL(XorClauseSimp c, XorSubsumer& subs);
-        
-        void cleanClauses(vec<XorClause*>& cs, ClauseSetType type, const uint limit = 0);
-        void removeSatisfied(vec<Clause*>& cs, ClauseSetType type, const uint limit = 0);
-        void removeSatisfied(vec<XorClause*>& cs, ClauseSetType type, const uint limit = 0);
-        void removeAndCleanAll(const bool nolimit = false);
-        bool satisfied(const Clause& c) const;
-        bool satisfied(const XorClause& c) const;
-        
-    private:
-        const bool cleanClause(XorClause& c);
-        const bool cleanClause(Clause& c);
-        
-        uint lastNumUnitarySat[6];
-        uint lastNumUnitaryClean[6];
-        
-        Solver& solver;
-};
-
-inline void ClauseCleaner::removeAndCleanAll(const bool nolimit)
-{
-    //uint limit = std::min((uint)((double)solver.order_heap.size() * PERCENTAGECLEANCLAUSES), FIXCLEANREPLACE);
-    uint limit = (double)solver.order_heap.size() * PERCENTAGECLEANCLAUSES;
-    if (nolimit) limit = 0;
-    
-    removeSatisfied(solver.binaryClauses, ClauseCleaner::binaryClauses, limit);
-    cleanClauses(solver.clauses, ClauseCleaner::clauses, limit);
-    cleanClauses(solver.xorclauses, ClauseCleaner::xorclauses, limit);
-    cleanClauses(solver.learnts, ClauseCleaner::learnts, limit);
-}
-
-}; //NAMESPACE MINISAT
-
-#endif //CLAUSECLEANER_H
index 96855d79a6b2aedc28d0266b78712478ddfd8e57..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,526 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#include "Conglomerate.h"
-#include "VarReplacer.h"
-#include "ClauseCleaner.h"
-
-#include <utility>
-#include <algorithm>
-#include <cstring>
-#include "time_mem.h"
-#include <iomanip>
-using std::make_pair;
-
-//#define VERBOSE_DEBUG
-
-#ifdef VERBOSE_DEBUG
-#include <iostream>
-using std::cout;
-using std::endl;
-#endif
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-Conglomerate::Conglomerate(Solver& _solver) :
-    found(0)
-    , solver(_solver)
-{}
-
-Conglomerate::~Conglomerate()
-{
-    for(uint i = 0; i < calcAtFinish.size(); i++)
-        free(calcAtFinish[i]);
-}
-
-void Conglomerate::blockVars()
-{
-    for (Clause *const*it = solver.clauses.getData(), *const*end = it + solver.clauses.size(); it != end; it++) {
-        const Clause& c = **it;
-        for (const Lit* a = &c[0], *end = a + c.size(); a != end; a++) {
-            blocked[a->var()] = true;
-        }
-    }
-    
-    for (Clause *const*it = solver.binaryClauses.getData(), *const*end = it + solver.binaryClauses.size(); it != end; it++) {
-        const Clause& c = **it;
-        blocked[c[0].var()] = true;
-        blocked[c[1].var()] = true;
-    }
-    
-    for (Lit* it = &(solver.trail[0]), *end = it + solver.trail.size(); it != end; it++)
-        blocked[it->var()] = true;
-    
-    const vec<Clause*>& clauses = solver.varReplacer->getClauses();
-    for (Clause *const*it = clauses.getData(), *const*end = it + clauses.size(); it != end; it++) {
-        const Clause& c = **it;
-        for (const Lit* a = &c[0], *end = a + c.size(); a != end; a++) {
-            blocked[a->var()] = true;
-        }
-    }
-}
-
-void Conglomerate::fillVarToXor()
-{
-    varToXor.clear();
-    
-    uint i = 0;
-    for (XorClause* const* it = solver.xorclauses.getData(), *const*end = it + solver.xorclauses.size(); it != end; it++, i++) {
-        const XorClause& c = **it;
-        for (const Lit * a = &c[0], *end = a + c.size(); a != end; a++) {
-            if (!blocked[a->var()])
-                varToXor[a->var()].push_back(make_pair(*it, i));
-        }
-    }
-}
-
-void Conglomerate::removeVar(const Var var)
-{
-    solver.activity[var] = 0.0;
-    solver.order_heap.update(var);
-    removedVars[var] = true;
-    if (solver.decision_var[var]) {
-        madeVarNonDecision.push(var);
-        solver.setDecisionVar(var, false);
-    }
-    found++;
-}
-
-void Conglomerate::processClause(XorClause& x, uint32_t num, Var remove_var)
-{
-    for (const Lit* a = &x[0], *end = a + x.size(); a != end; a++) {
-        Var var = a->var();
-        if (var != remove_var) {
-            varToXorMap::iterator finder = varToXor.find(var);
-            if (finder != varToXor.end()) {
-                vector<pair<XorClause*, uint32_t> >::iterator it =
-                std::find(finder->second.begin(), finder->second.end(), make_pair(&x, num));
-                finder->second.erase(it);
-            }
-        }
-    }
-}
-
-const bool Conglomerate::heuleProcessFull()
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "Heule XOR-ing started" << endl;
-    #endif
-    
-    double time = cpuTime();
-    found = 0;
-    uint oldToReplaceVars = solver.varReplacer->getNewToReplaceVars();
-    solver.clauseCleaner->cleanClauses(solver.xorclauses, ClauseCleaner::xorclauses);
-    if (solver.ok == false)
-        return false;
-    
-    toRemove.clear();
-    toRemove.resize(solver.xorclauses.size(), false);
-    blocked.clear();
-    blocked.resize(solver.nVars(), false);
-    fillVarToXor();
-    if (!heuleProcess())
-        goto end;
-    
-    if (solver.verbosity >=1) {
-        std::cout << "c |  Heule-processings XORs:" << std::setw(8) << std::setprecision(2) << std::fixed << cpuTime()-time
-        << "  Found smaller XOR-s: " << std::setw(6) << found
-        << "  New bin anti/eq-s: " << std::setw(3) << solver.varReplacer->getNewToReplaceVars() - oldToReplaceVars
-        << std::setw(0) << " |" << std::endl;
-    }
-
-end:
-    
-    clearToRemove();
-    
-    return solver.ok;
-}
-
-const bool Conglomerate::conglomerateXorsFull()
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "Finding conglomerate xors started" << endl;
-    #endif
-    
-    double time = cpuTime();
-    found = 0;
-    uint32_t origNumClauses = solver.xorclauses.size();
-    
-    solver.clauseCleaner->cleanClauses(solver.xorclauses, ClauseCleaner::xorclauses);
-    if (solver.ok == false)
-        return false;
-    
-    toRemove.clear();
-    toRemove.resize(solver.xorclauses.size(), false);
-    blocked.clear();
-    blocked.resize(solver.nVars(), false);
-    blockVars();
-    fillVarToXor();
-    if (conglomerateXors() == false)
-        goto end;
-    
-end:
-    
-    clearToRemove();
-    assert(origNumClauses >= solver.xorclauses.size());
-    if (solver.verbosity >=1) {
-        std::cout << "c |  Conglomerating XORs:" << std::setw(8) << std::setprecision(2) << std::fixed << cpuTime()-time << " s   "
-        << "   removed " << std::setw(8) << found << " vars"
-        << "   removed " << std::setw(8) << origNumClauses-solver.xorclauses.size() << " clauses"
-        << std::setw(0) << " |" << std::endl;
-    }
-    
-    clearLearntsFromToRemove();
-    solver.order_heap.filter(Solver::VarFilter(solver));
-    
-    return solver.ok;
-}
-
-void Conglomerate::fillNewSet(vector<vector<Lit> >& newSet, vector<pair<XorClause*, uint32_t> >& clauseSet) const
-{
-    newSet.clear();
-    newSet.resize(clauseSet.size());
-    
-    XorClause& firstXorClause = *(clauseSet[0].first);
-    newSet[0].resize(firstXorClause.size());
-    memcpy(&newSet[0][0], firstXorClause.getData(), sizeof(Lit)*firstXorClause.size());
-    
-    for (uint i = 1; i < clauseSet.size(); i++) {
-        XorClause& thisXorClause = *clauseSet[i].first;
-        newSet[i] = newSet[0];
-        newSet[i].resize(firstXorClause.size()+thisXorClause.size());
-        memcpy(&newSet[i][firstXorClause.size()], thisXorClause.getData(), sizeof(Lit)*thisXorClause.size());
-        clearDouble(newSet[i]);
-    }
-}
-
-const bool Conglomerate::heuleProcess()
-{
-    vector<vector<Lit> > newSet;
-    while(varToXor.begin() != varToXor.end()) {
-        varToXorMap::iterator it = varToXor.begin();
-        vector<pair<XorClause*, uint32_t> >& clauseSet = it->second;
-        const Var var = it->first;
-        
-        if (blocked[var] || clauseSet.size() == 1) {
-            varToXor.erase(it);
-            blocked[var] = true;
-            continue;
-        }
-        blocked[var] = true;
-        
-        std::sort(clauseSet.begin(), clauseSet.end(), ClauseSetSorter());
-        fillNewSet(newSet, clauseSet);
-        
-        for (uint i = 1; i < newSet.size(); i++) if (newSet[i].size() <= 2) {
-            found++;
-            XorClause& thisXorClause = *clauseSet[i].first;
-            const bool inverted = !clauseSet[0].first->xor_clause_inverted() ^ thisXorClause.xor_clause_inverted();
-            const uint old_group = thisXorClause.getGroup();
-
-            #ifdef VERBOSE_DEBUG
-            cout << "- XOR1:";
-            clauseSet[0].first->plainPrint();
-            cout << "- XOR2:";
-            thisXorClause.plainPrint();
-            #endif
-            
-            if (!dealWithNewClause(newSet[i], inverted, old_group))
-                return false;
-            assert(newSet.size() == clauseSet.size());
-        }
-        
-        varToXor.erase(it);
-    }
-    
-    return (solver.ok = (solver.propagate() == NULL));
-}
-
-const bool Conglomerate::conglomerateXors()
-{
-    vector<vector<Lit> > newSet;
-    while(varToXor.begin() != varToXor.end()) {
-        varToXorMap::iterator it = varToXor.begin();
-        vector<pair<XorClause*, uint32_t> >& clauseSet = it->second;
-        const Var var = it->first;
-        
-        //We blocked the var during dealWithNewClause (it was in a 2-long xor-clause)
-        if (blocked[var]) {
-            varToXor.erase(it);
-            continue;
-        }
-        
-        if (clauseSet.size() == 0) {
-            removeVar(var);
-            varToXor.erase(it);
-            continue;
-        }
-        
-        std::sort(clauseSet.begin(), clauseSet.end(), ClauseSetSorter());
-        fillNewSet(newSet, clauseSet);
-        
-        int diff = 0;
-        for (size_t i = 1; i < newSet.size(); i++)
-            diff += (int)newSet[i].size()-(int)clauseSet[i].first->size();
-        
-        if (newSet.size() > 2) {
-            blocked[var] = true;
-            varToXor.erase(it);
-            continue;
-        }
-        
-        XorClause& firstXorClause = *(clauseSet[0].first);
-        bool first_inverted = !firstXorClause.xor_clause_inverted();
-        removeVar(var);
-        
-        #ifdef VERBOSE_DEBUG
-        cout << "--- New conglomerate set ---" << endl;
-        cout << "- Removing: ";
-        firstXorClause.plainPrint();
-        cout << "Adding var " << var+1 << " to calcAtFinish" << endl;
-        #endif
-        
-        assert(!toRemove[clauseSet[0].second]);
-        toRemove[clauseSet[0].second] = true;
-        processClause(firstXorClause, clauseSet[0].second, var);
-        solver.detachClause(firstXorClause);
-        calcAtFinish.push(&firstXorClause);
-        
-        for (uint i = 1; i < clauseSet.size(); i++) {
-            XorClause& thisXorClause = *clauseSet[i].first;
-            #ifdef VERBOSE_DEBUG
-            cout << "- Removing: ";
-            thisXorClause.plainPrint();
-            #endif
-            
-            const uint old_group = thisXorClause.getGroup();
-            const bool inverted = first_inverted ^ thisXorClause.xor_clause_inverted();
-            assert(!toRemove[clauseSet[i].second]);
-            toRemove[clauseSet[i].second] = true;
-            processClause(thisXorClause, clauseSet[i].second, var);
-            solver.removeClause(thisXorClause);
-            
-            if (!dealWithNewClause(newSet[i], inverted, old_group))
-                return false;
-            assert(newSet.size() == clauseSet.size());
-        }
-        
-        varToXor.erase(it);
-    }
-    
-    return (solver.ok = (solver.propagate() == NULL));
-}
-
-bool Conglomerate::dealWithNewClause(vector<Lit>& ps, const bool inverted, const uint old_group)
-{
-    switch(ps.size()) {
-        case 0: {
-            #ifdef VERBOSE_DEBUG
-            cout << "--> xor is 0-long" << endl;
-            #endif
-            
-            if  (!inverted) {
-                solver.ok = false;
-                return false;
-            }
-            break;
-        }
-        case 1: {
-            #ifdef VERBOSE_DEBUG
-            cout << "--> xor is 1-long, attempting to set variable " << ps[0].var()+1 << endl;
-            #endif
-            
-            if (solver.assigns[ps[0].var()] == l_Undef) {
-                assert(solver.decisionLevel() == 0);
-                blocked[ps[0].var()] = true;
-                solver.uncheckedEnqueue(Lit(ps[0].var(), inverted));
-            } else if (solver.assigns[ps[0].var()] != boolToLBool(!inverted)) {
-                #ifdef VERBOSE_DEBUG
-                cout << "Conflict. Aborting.";
-                #endif
-                solver.ok = false;
-                return false;
-            } else {
-                #ifdef VERBOSE_DEBUG
-                cout << "Variable already set to correct value";
-                #endif
-            }
-            break;
-        }
-        
-        case 2: {
-            #ifdef VERBOSE_DEBUG
-            cout << "--> xor is 2-long, must later replace variable" << endl;
-            XorClause* newX = XorClause_new(ps, inverted, old_group);
-            newX->plainPrint();
-            free(newX);
-            #endif
-            
-            vec<Lit> tmpPS(2);
-            tmpPS[0] = ps[0];
-            tmpPS[1] = ps[1];
-            if (solver.varReplacer->replace(tmpPS, inverted, old_group) == false)
-                return false;
-            blocked[ps[0].var()] = true;
-            blocked[ps[1].var()] = true;
-            break;
-        }
-        
-        default: {
-            XorClause* newX = XorClause_new(ps, inverted, old_group);
-            
-            #ifdef VERBOSE_DEBUG
-            cout << "- Adding: ";
-            newX->plainPrint();
-            #endif
-            
-            solver.xorclauses.push(newX);
-            toRemove.push_back(false);
-            solver.attachClause(*newX);
-            for (const Lit * a = &((*newX)[0]), *end = a + newX->size(); a != end; a++) {
-                if (!blocked[a->var()])
-                    varToXor[a->var()].push_back(make_pair(newX, (uint32_t)(toRemove.size()-1)));
-            }
-            break;
-        }
-    }
-    
-    return true;
-}
-
-void Conglomerate::clearDouble(vector<Lit>& ps) const
-{    
-    std::sort(ps.begin(), ps.end());
-    Lit p;
-    uint32_t i, j;
-    for (i = j = 0, p = lit_Undef; i != ps.size(); i++) {
-        ps[i] = ps[i].unsign();
-        if (ps[i] == p) {
-            //added, but easily removed
-            j--;
-            p = lit_Undef;
-        } else
-            ps[j++] = p = ps[i];
-    }
-    ps.resize(ps.size() - (i - j));
-}
-
-void Conglomerate::clearToRemove()
-{
-    assert(toRemove.size() == solver.xorclauses.size());
-    
-    XorClause **a = solver.xorclauses.getData();
-    XorClause **r = a;
-    XorClause **end = a + solver.xorclauses.size();
-    for (uint i = 0; r != end; i++) {
-        if (!toRemove[i])
-            *a++ = *r++;
-        else {
-            r++;
-        }
-    }
-    solver.xorclauses.shrink(r-a);
-}
-
-void Conglomerate::clearLearntsFromToRemove()
-{
-    Clause **a = solver.learnts.getData();
-    Clause **r = a;
-    Clause **end = a + solver.learnts.size();
-    for (; r != end;) {
-        const Clause& c = **r;
-        bool inside = false;
-        if (!solver.locked(c)) {
-            for (uint i = 0; i < c.size(); i++) {
-                if (removedVars[c[i].var()]) {
-                    inside = true;
-                    break;
-                }
-            }
-        }
-        if (!inside)
-            *a++ = *r++;
-        else {
-            solver.removeClause(**r);
-            r++;
-        }
-    }
-    solver.learnts.shrink(r-a);
-}
-
-void Conglomerate::extendModel(Solver& solver2)
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "Executing doCalcAtFinish" << endl;
-    #endif
-    
-    vec<Lit> ps;
-    for (int i = (int)(calcAtFinish.size())-1; i >= 0; i--) {
-        XorClause& c = *calcAtFinish[i];
-        assert(c.size() > 2);
-        
-        ps.clear();
-        for (Lit *l = c.getData(), *end = c.getDataEnd(); l != end; l++) {
-            ps.push(l->unsign());
-        }
-        
-        solver2.addXorClause(ps, c.xor_clause_inverted(), c.getGroup());
-        assert(solver2.ok);
-    }
-}
-
-const bool Conglomerate::addRemovedClauses()
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "Executing addRemovedClauses" << endl;
-    #endif
-    
-    for(XorClause **it = calcAtFinish.getData(), **end = calcAtFinish.getDataEnd(); it != end; it++)
-    {
-        XorClause& c = **it;
-        #ifdef VERBOSE_DEBUG
-        cout << "readding already removed (conglomerated) clause: ";
-        c.plainPrint();
-        #endif
-        
-        for(Lit *l = c.getData(), *end2 = c.getDataEnd(); l != end2 ; l++)
-            *l = l->unsign();
-        
-        FILE* backup_libraryCNFfile = solver.libraryCNFFile;
-        solver.libraryCNFFile = NULL;
-        if (!solver.addXorClause(c, c.xor_clause_inverted(), c.getGroup())) {
-            for (;it != end; it++) free(*it);
-            calcAtFinish.clear();
-            return false;
-        }
-        solver.libraryCNFFile = backup_libraryCNFfile;
-        free(&c);
-    }
-    calcAtFinish.clear();
-    
-    std::fill(removedVars.getData(), removedVars.getDataEnd(), false);
-    for (Var *v = madeVarNonDecision.getData(), *end =  madeVarNonDecision.getDataEnd(); v != end; v++) {
-        solver.setDecisionVar(*v, true);
-    }
-    madeVarNonDecision.clear();
-    
-    return true;
-}
-
-}; //NAMESPACE MINISAT
index 50972d464739a81ad2ae0870a68f076f425cce0b..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,125 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef CONGLOMERATE_H
-#define CONGLOMERATE_H
-
-#include <vector>
-#include <map>
-#include <set>
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-#include "Clause.h"
-#include "VarReplacer.h"
-#include "Solver.h"
-
-using std::vector;
-using std::pair;
-using std::map;
-using std::set;
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class Solver;
-
-class Conglomerate
-{
-public:
-    Conglomerate(Solver& solver);
-    ~Conglomerate();
-    const bool conglomerateXorsFull();
-    const bool heuleProcessFull();
-    const bool addRemovedClauses(); ///<Add clauses that have been removed. Used if solve() is called multiple times
-    void extendModel(Solver& solver2); ///<Calculate variables removed during conglomeration
-    
-    const vec<XorClause*>& getCalcAtFinish() const;
-    vec<XorClause*>& getCalcAtFinish();
-    const vec<bool>& getRemovedVars() const;
-    const bool needCalcAtFinish() const;
-    
-    void newVar();
-    
-private:
-    
-    struct ClauseSetSorter {
-        bool operator () (const pair<XorClause*, uint32_t>& a, const pair<XorClause*, uint32_t>& b) {
-            return a.first->size() < b.first->size();
-        }
-    };
-    
-    const bool conglomerateXors();
-    const bool heuleProcess();
-    
-    void fillNewSet(vector<vector<Lit> >& newSet, vector<pair<XorClause*, uint32_t> >& clauseSet) const;
-    
-    void removeVar(const Var var);
-    void processClause(XorClause& x, uint32_t num, Var remove_var);
-    void blockVars();
-    void fillVarToXor();
-    void clearDouble(vector<Lit>& ps) const;
-    void clearToRemove();
-    void clearLearntsFromToRemove();
-    bool dealWithNewClause(vector<Lit>& ps, const bool inverted, const uint old_group);
-    
-    typedef map<uint, vector<pair<XorClause*, uint32_t> > > varToXorMap;
-    varToXorMap varToXor; 
-    vector<bool> blocked;
-    vector<bool> toRemove;
-    
-    vec<bool> removedVars;
-    vec<Var> madeVarNonDecision;
-    
-    vec<XorClause*> calcAtFinish;
-    uint found;
-    
-    Solver& solver;
-};
-
-inline void Conglomerate::newVar()
-{
-    removedVars.push(false);
-}
-
-inline const vec<bool>& Conglomerate::getRemovedVars() const
-{
-    return removedVars;
-}
-
-inline const vec<XorClause*>& Conglomerate::getCalcAtFinish() const
-{
-    return calcAtFinish;
-}
-
-inline vec<XorClause*>& Conglomerate::getCalcAtFinish()
-{
-    return calcAtFinish;
-}
-
-inline const bool Conglomerate::needCalcAtFinish() const
-{
-    return calcAtFinish.size();
-}
-
-}; //NAMESPACE MINISAT
-
-#endif //CONGLOMERATE_H
index 50cfd8aee476f5b5f0de9c77b0d3ed5061628431..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,173 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef DOUBLEPACKEDROW_H
-#define DOUBLEPACKEDROW_H
-
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-#include <stdlib.h>
-
-#include "SolverTypes.h"
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class DoublePackedRow
-{
-    private:
-        class BitIter {
-            public:
-                inline void operator=(const lbool toSet)
-                {
-                    val &= ~((unsigned char)3 << offset);
-                    val |= toSet.value << offset;
-                }
-                
-                inline operator lbool() const
-                {
-                    return lbool((val >> offset) & 3);
-                }
-                
-                inline const bool isUndef() const {
-                    return ((lbool)*this).isUndef();
-                }
-                inline const bool isDef() const {
-                    return ((lbool)*this).isDef();
-                }
-                inline const bool getBool() const {
-                    return ((lbool)*this).getBool();
-                }
-                inline const bool operator==(lbool b) const {
-                    return ((lbool)*this) == b;
-                }
-                inline const bool operator!=(lbool b) const {
-                    return ((lbool)*this) != b;
-                }
-                const lbool operator^(const bool b) const {
-                    return ((lbool)*this) ^ b;
-                }
-                
-            private:
-                friend class DoublePackedRow;
-                inline BitIter(unsigned char& mp, const uint32_t _offset) :
-                val(mp)
-                , offset(_offset)
-                {}
-                
-                unsigned char& val;
-                const uint32_t offset;
-        };
-        
-        class BitIterConst {
-             public:
-                inline operator lbool() const
-                {
-                    return lbool((val >> offset) & 3);
-                }
-                
-                inline const bool isUndef() const {
-                    return ((lbool)*this).isUndef();
-                }
-                inline const bool isDef() const {
-                    return ((lbool)*this).isDef();
-                }
-                inline const bool getBool() const {
-                    return ((lbool)*this).getBool();
-                }
-                inline const bool operator==(lbool b) const {
-                    return ((lbool)*this) == b;
-                }
-                inline const bool operator!=(lbool b) const {
-                    return ((lbool)*this) != b;
-                }
-                const lbool operator^(const bool b) const {
-                    return ((lbool)*this) ^ b;
-                }
-                
-                
-            private:
-                friend class DoublePackedRow;
-                inline BitIterConst(unsigned char& mp, const uint32_t _offset) :
-                val(mp)
-                , offset(_offset)
-                {}
-                
-                const unsigned char& val;
-                const uint32_t offset;
-        };
-    
-    public:
-        DoublePackedRow() :
-            numElems(0)
-            , mp(NULL)
-        {}
-        
-        uint32_t size() const
-        {
-            return numElems;
-        }
-        
-        void growTo(const uint32_t newNumElems)
-        {
-            uint32_t oldSize = numElems/4 + (bool)(numElems % 4);
-            uint32_t newSize = newNumElems/4 + (bool)(newNumElems % 4);
-            
-            if (oldSize >= newSize) {
-                numElems = std::max(newNumElems, numElems);
-                return;
-            }
-            
-            mp = (unsigned char*)realloc(mp, newSize*sizeof(unsigned char));
-            numElems = newNumElems;
-        }
-        
-        inline BitIter operator[](const uint32_t at)
-        {
-            return BitIter(mp[at/4], (at%4)*2);
-        }
-        
-        inline const BitIterConst operator[](const uint32_t at) const
-        {
-            return BitIterConst(mp[at/4], (at%4)*2);
-        }
-        
-        inline void push(const lbool val)
-        {
-            growTo(numElems+1);
-            (*this)[numElems-1] = val;
-        }
-        
-        /*void clear(const uint32_t at)
-        {
-            mp[at/32] &= ~((uint64_t)3 << ((at%32)*2));
-        }*/
-        
-    private:
-        
-        Var numElems;
-        unsigned char *mp;
-};
-
-}; //NAMESPACE MINISAT
-
-#endif //DOUBLEPACKEDROW_H
index 3d0e86f551b909dcba4dcd2ac6bb030299fcc22f..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,412 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#include "FailedVarSearcher.h"
-
-#include <iomanip>
-#include <utility>
-#include <set>
-using std::make_pair;
-using std::set;
-
-#include "Solver.h"
-#include "ClauseCleaner.h"
-#include "time_mem.h"
-#include "VarReplacer.h"
-#include "ClauseCleaner.h"
-
-#ifdef _MSC_VER
-#define __builtin_prefetch(a,b,c)
-#endif //_MSC_VER
-
-//#define VERBOSE_DEUBUG
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-FailedVarSearcher::FailedVarSearcher(Solver& _solver):
-    solver(_solver)
-    , finishedLastTime(true)
-    , lastTimeWentUntil(0)
-    , numPropsMultiplier(1.0)
-    , lastTimeFoundTruths(0)
-{
-}
-
-void FailedVarSearcher::addFromSolver(const vec< XorClause* >& cs)
-{
-    xorClauseSizes.clear();
-    xorClauseSizes.growTo(cs.size());
-    occur.resize(solver.nVars());
-    for (Var var = 0; var < solver.nVars(); var++) {
-        occur[var].clear();
-    }
-    
-    uint32_t i = 0;
-    for (XorClause * const*it = cs.getData(), * const*end = it + cs.size(); it !=  end; it++, i++) {
-        if (it+1 != end)
-            __builtin_prefetch(*(it+1), 0, 0);
-        
-        const XorClause& cl = **it;
-        xorClauseSizes[i] = cl.size();
-        for (const Lit *l = cl.getData(), *end2 = l + cl.size(); l != end2; l++) {
-            occur[l->var()].push_back(i);
-        }
-    }
-}
-
-inline void FailedVarSearcher::removeVarFromXors(const Var var)
-{
-    vector<uint32_t>& occ = occur[var];
-    if (occ.empty()) return;
-    
-    for (uint32_t *it = &occ[0], *end = it + occ.size(); it != end; it++) {
-        xorClauseSizes[*it]--;
-        if (!xorClauseTouched[*it]) {
-            xorClauseTouched.setBit(*it);
-            investigateXor.push(*it);
-        }
-    }
-}
-
-inline void FailedVarSearcher::addVarFromXors(const Var var)
-{
-    vector<uint32_t>& occ = occur[var];
-    if (occ.empty()) return;
-    
-    for (uint32_t *it = &occ[0], *end = it + occ.size(); it != end; it++) {
-        xorClauseSizes[*it]++;
-    }
-}
-
-const TwoLongXor FailedVarSearcher::getTwoLongXor(const XorClause& c)
-{
-    TwoLongXor tmp;
-    uint32_t num = 0;
-    tmp.inverted = c.xor_clause_inverted();
-    
-    for(const Lit *l = c.getData(), *end = l + c.size(); l != end; l++) {
-        if (solver.assigns[l->var()] == l_Undef) {
-            assert(num < 2);
-            tmp.var[num] = l->var();
-            num++;
-        } else {
-            tmp.inverted ^= (solver.assigns[l->var()] == l_True);
-        }
-    }
-    
-    #ifdef VERBOSE_DEUBUG
-    if (num != 2) {
-        std::cout << "Num:" << num << std::endl;
-        c.plainPrint();
-    }
-    #endif
-    
-    std::sort(&tmp.var[0], &tmp.var[0]+2);
-    assert(num == 2);
-    return tmp;
-}
-
-const bool FailedVarSearcher::search(uint64_t numProps)
-{
-    assert(solver.decisionLevel() == 0);
-    
-    //Saving Solver state
-    Heap<Solver::VarOrderLt> backup_order_heap(solver.order_heap);
-    vector<bool> backup_polarities = solver.polarity;
-    vec<uint32_t> backup_activity(solver.activity.size());
-    std::copy(solver.activity.getData(), solver.activity.getDataEnd(), backup_activity.getData());
-    uint32_t backup_var_inc = solver.var_inc;
-    uint32_t origHeapSize = solver.order_heap.size();
-    
-    //General Stats
-    double time = cpuTime();
-    uint32_t numFailed = 0;
-    uint32_t goodBothSame = 0;
-    uint32_t from;
-    if (finishedLastTime || lastTimeWentUntil >= solver.nVars())
-        from = 0;
-    else
-        from = lastTimeWentUntil;
-    uint64_t origProps = solver.propagations;
-    
-    //If failed var searching is going good, do successively more and more of it
-    if (lastTimeFoundTruths > 500 || (double)lastTimeFoundTruths > (double)solver.order_heap.size() * 0.03) std::max(numPropsMultiplier*1.7, 5.0);
-    else numPropsMultiplier = 1.0;
-    numProps = (uint64_t) ((double)numProps * numPropsMultiplier);
-    
-    //For failure
-    bool failed;
-    
-    //For BothSame
-    BitArray propagated;
-    propagated.resize(solver.nVars(), 0);
-    BitArray propValue;
-    propValue.resize(solver.nVars(), 0);
-    vector<pair<Var, bool> > bothSame;
-    
-    //For calculating how many variables have really been set
-    uint32_t origTrailSize = solver.trail.size();
-    
-    //For 2-long xor (rule 6 of  Equivalent literal propagation in the DLL procedure by Chu-Min Li)
-    set<TwoLongXor> twoLongXors;
-    uint32_t toReplaceBefore = solver.varReplacer->getNewToReplaceVars();
-    uint32_t lastTrailSize = solver.trail.size();
-    bool binXorFind = true;
-    if (solver.xorclauses.size() < 5 ||
-        solver.xorclauses.size() > 30000 ||
-        solver.order_heap.size() > 30000 ||
-        solver.nClauses() > 100000)
-        binXorFind = false;
-    if (binXorFind) {
-        solver.clauseCleaner->cleanClauses(solver.xorclauses, ClauseCleaner::xorclauses);
-        addFromSolver(solver.xorclauses);
-    }
-    xorClauseTouched.resize(solver.xorclauses.size(), 0);
-    
-    finishedLastTime = true;
-    lastTimeWentUntil = solver.nVars();
-    for (Var var = from; var < solver.nVars(); var++) {
-        if (solver.assigns[var] == l_Undef && solver.order_heap.inHeap(var)) {
-            if ((int)solver.propagations - (int)origProps >= (int)numProps)  {
-                finishedLastTime = false;
-                lastTimeWentUntil = var;
-                break;
-            }
-            
-            if (binXorFind) {
-                if (lastTrailSize < solver.trail.size()) {
-                    for (uint32_t i = lastTrailSize; i != solver.trail.size(); i++) {
-                        removeVarFromXors(solver.trail[i].var());
-                    }
-                }
-                lastTrailSize = solver.trail.size();
-                xorClauseTouched.setZero();
-                investigateXor.clear();
-            }
-            
-            propagated.setZero();
-            twoLongXors.clear();
-            
-            solver.newDecisionLevel();
-            solver.uncheckedEnqueue(Lit(var, false));
-            failed = (solver.propagate(false) != NULL);
-            if (failed) {
-                solver.cancelUntil(0);
-                numFailed++;
-                solver.uncheckedEnqueue(Lit(var, true));
-                solver.ok = (solver.propagate(false) == NULL);
-                if (!solver.ok) goto end;
-                continue;
-            } else {
-                assert(solver.decisionLevel() > 0);
-                for (int c = solver.trail.size()-1; c >= (int)solver.trail_lim[0]; c--) {
-                    Var x = solver.trail[c].var();
-                    propagated.setBit(x);
-                    if (solver.assigns[x].getBool())
-                        propValue.setBit(x);
-                    else
-                        propValue.clearBit(x);
-                    
-                    if (binXorFind) removeVarFromXors(x);
-                }
-                
-                if (binXorFind) {
-                    for (uint32_t *it = investigateXor.getData(), *end = investigateXor.getDataEnd(); it != end; it++) {
-                        if (xorClauseSizes[*it] == 2)
-                            twoLongXors.insert(getTwoLongXor(*solver.xorclauses[*it]));
-                    }
-                    for (int c = solver.trail.size()-1; c >= (int)solver.trail_lim[0]; c--) {
-                        addVarFromXors(solver.trail[c].var());
-                    }
-                    xorClauseTouched.setZero();
-                    investigateXor.clear();
-                }
-                
-                solver.cancelUntil(0);
-            }
-            
-            solver.newDecisionLevel();
-            solver.uncheckedEnqueue(Lit(var, true));
-            failed = (solver.propagate(false) != NULL);
-            if (failed) {
-                solver.cancelUntil(0);
-                numFailed++;
-                solver.uncheckedEnqueue(Lit(var, false));
-                solver.ok = (solver.propagate(false) == NULL);
-                if (!solver.ok) goto end;
-                continue;
-            } else {
-                assert(solver.decisionLevel() > 0);
-                for (int c = solver.trail.size()-1; c >= (int)solver.trail_lim[0]; c--) {
-                    Var     x  = solver.trail[c].var();
-                    if (propagated[x] && propValue[x] == solver.assigns[x].getBool())
-                        bothSame.push_back(make_pair(x, !propValue[x]));
-                    if (binXorFind) removeVarFromXors(x);
-                }
-                
-                if (binXorFind) {
-                    if (twoLongXors.size() > 0) {
-                        for (uint32_t *it = investigateXor.getData(), *end = it + investigateXor.size(); it != end; it++) {
-                            if (xorClauseSizes[*it] == 2) {
-                                TwoLongXor tmp = getTwoLongXor(*solver.xorclauses[*it]);
-                                if (twoLongXors.find(tmp) != twoLongXors.end()) {
-                                    vec<Lit> ps(2);
-                                    ps[0] = Lit(tmp.var[0], false);
-                                    ps[1] = Lit(tmp.var[1], false);
-                                    if (!solver.varReplacer->replace(ps, tmp.inverted, 0))
-                                        goto end;
-                                }
-                            }
-                        }
-                    }
-                    for (int c = solver.trail.size()-1; c >= (int)solver.trail_lim[0]; c--) {
-                        addVarFromXors(solver.trail[c].var());
-                    }
-                }
-                
-                solver.cancelUntil(0);
-            }
-            
-            for(uint32_t i = 0; i != bothSame.size(); i++) {
-                solver.uncheckedEnqueue(Lit(bothSame[i].first, bothSame[i].second));
-            }
-            goodBothSame += bothSame.size();
-            bothSame.clear();
-            solver.ok = (solver.propagate(false) == NULL);
-            if (!solver.ok) goto end;
-        }
-    }
-
-end:
-    //Restoring Solver state
-    if (solver.verbosity >= 1) {
-        std::cout << "c |  Failvars: "<< std::setw(5) << numFailed <<
-        "     Bprop vars: " << std::setw(6) << goodBothSame <<
-        " Replaced: " << std::setw(3) << (solver.varReplacer->getNewToReplaceVars() - toReplaceBefore) <<
-        " Props: " << std::setw(8) << std::setprecision(2) << (int)solver.propagations - (int)origProps  <<
-        " Time: " << std::setw(6) << std::fixed << std::setprecision(2) << cpuTime() - time <<
-        std::setw(5) << " |" << std::endl;
-    }
-    
-    solver.order_heap.filter(Solver::VarFilter(solver));
-    
-    if (solver.ok && (numFailed || goodBothSame)) {
-        double time = cpuTime();
-        if ((int)origHeapSize - (int)solver.order_heap.size() >  (int)origHeapSize/15 && solver.nClauses() + solver.learnts.size() > 500000) {
-            solver.clauses_literals = 0;
-            solver.learnts_literals = 0;
-            for (uint32_t i = 0; i < solver.nVars(); i++) {
-                solver.binwatches[i*2].clear();
-                solver.binwatches[i*2+1].clear();
-                solver.watches[i*2].clear();
-                solver.watches[i*2+1].clear();
-                solver.xorwatches[i].clear();
-            }
-            solver.varReplacer->reattachInternalClauses();
-            cleanAndAttachClauses(solver.binaryClauses);
-            cleanAndAttachClauses(solver.clauses);
-            cleanAndAttachClauses(solver.learnts);
-            cleanAndAttachClauses(solver.xorclauses);
-        } else {
-            solver.clauseCleaner->removeAndCleanAll();
-        }
-        if (solver.verbosity >= 1 && numFailed + goodBothSame > 100) {
-            std::cout << "c |  Cleaning up after failed var search: " << std::setw(8) << std::fixed << std::setprecision(2) << cpuTime() - time << " s "
-            <<  std::setw(33) << " | " << std::endl;
-        }
-    }
-    
-    lastTimeFoundTruths = solver.trail.size() - origTrailSize;
-    
-    solver.var_inc = backup_var_inc;
-    std::copy(backup_activity.getData(), backup_activity.getDataEnd(), solver.activity.getData());
-    solver.order_heap = backup_order_heap;
-    solver.polarity = backup_polarities;
-    solver.order_heap.filter(Solver::VarFilter(solver));
-    
-    return solver.ok;
-}
-
-template<class T>
-inline void FailedVarSearcher::cleanAndAttachClauses(vec<T*>& cs)
-{
-    T **i = cs.getData();
-    T **j = i;
-    for (T **end = cs.getDataEnd(); i != end; i++) {
-        if (cleanClause(**i)) {
-            solver.attachClause(**i);
-            *j++ = *i;
-        } else {
-            free(*i);
-        }
-    }
-    cs.shrink(i-j);
-}
-
-inline const bool FailedVarSearcher::cleanClause(Clause& ps)
-{
-    uint32_t origSize = ps.size();
-    
-    Lit *i = ps.getData();
-    Lit *j = i;
-    for (Lit *end = ps.getDataEnd(); i != end; i++) {
-        if (solver.value(*i) == l_True) return false;
-        if (solver.value(*i) == l_Undef) {
-            *j++ = *i;
-        }
-    }
-    ps.shrink(i-j);
-    assert(ps.size() > 1);
-    
-    if (ps.size() != origSize) ps.setStrenghtened();
-    if (origSize != 2 && ps.size() == 2)
-        solver.becameBinary++;
-    
-    return true;
-}
-
-inline const bool FailedVarSearcher::cleanClause(XorClause& ps)
-{
-    uint32_t origSize = ps.size();
-    
-    Lit *i = ps.getData(), *j = i;
-    for (Lit *end = ps.getDataEnd(); i != end; i++) {
-        if (solver.assigns[i->var()] == l_True) ps.invert(true);
-        if (solver.assigns[i->var()] == l_Undef) {
-            *j++ = *i;
-        }
-    }
-    ps.shrink(i-j);
-    
-    if (ps.size() == 0) return false;
-    assert(ps.size() > 1);
-    
-    if (ps.size() != origSize) ps.setStrenghtened();
-    if (ps.size() == 2) {
-        vec<Lit> tmp(2);
-        tmp[0] = ps[0].unsign();
-        tmp[1] = ps[1].unsign();
-        solver.varReplacer->replace(tmp, ps.xor_clause_inverted(), ps.getGroup());
-        return false;
-    }
-    
-    return true;
-}
-
-}; //NAMESPACE MINISAT
index 79ed82ec3355d4a98638712dce19a5099ad3526f..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,90 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef FAILEDVARSEARCHER_H
-#define FAILEDVARSEARCHER_H
-
-#include "SolverTypes.h"
-#include "Clause.h"
-#include "BitArray.h"
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class Solver;
-
-class TwoLongXor
-{
-    public:
-        const bool operator==(const TwoLongXor& other) const
-        {
-            if (var[0] == other.var[0] && var[1] == other.var[1] && inverted == other.inverted)
-                return true;
-            return false;
-        }
-        const bool operator<(const TwoLongXor& other) const
-        {
-            if (var[0] < other.var[0]) return true;
-            if (var[0] > other.var[0]) return false;
-            
-            if (var[1] < other.var[1]) return true;
-            if (var[1] > other.var[1]) return false;
-            
-            if (inverted < other.inverted) return true;
-            if (inverted > other.inverted) return false;
-            
-            return false;
-        }
-        
-        Var var[2];
-        bool inverted;
-};
-
-class FailedVarSearcher {
-    public:
-        FailedVarSearcher(Solver& _solver);
-    
-        const bool search(uint64_t numProps);
-        
-    private:
-        const TwoLongXor getTwoLongXor(const XorClause& c);
-        void addFromSolver(const vec<XorClause*>& cs);
-        
-        template<class T>
-        void cleanAndAttachClauses(vec<T*>& cs);
-        const bool cleanClause(Clause& ps);
-        const bool cleanClause(XorClause& ps);
-        
-        Solver& solver;
-        
-        vec<uint32_t> xorClauseSizes;
-        vector<vector<uint32_t> > occur;
-        void removeVarFromXors(const Var var);
-        void addVarFromXors(const Var var);
-        BitArray xorClauseTouched;
-        vec<uint32_t> investigateXor;
-        
-        bool finishedLastTime;
-        uint32_t lastTimeWentUntil;
-        double numPropsMultiplier;
-        uint32_t lastTimeFoundTruths;
-};
-
-}; //NAMESPACE MINISAT
-
-#endif //FAILEDVARSEARCHER_H
\ No newline at end of file
index 836dc6b3740a7e0ff5b6358242a6493be7bc95f4..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,176 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#include "FindUndef.h"
-
-#include "Solver.h"
-#include "VarReplacer.h"
-#include <algorithm>
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-FindUndef::FindUndef(Solver& _solver) :
-    solver(_solver)
-    , isPotentialSum(0)
-{
-}
-
-void FindUndef::fillPotential()
-{
-    int trail = solver.decisionLevel()-1;
-    
-    while(trail > 0) {
-        assert(trail < (int)solver.trail_lim.size());
-        uint at = solver.trail_lim[trail];
-        
-        assert(at > 0);
-        Var v = solver.trail[at].var();
-        if (solver.assigns[v] != l_Undef) {
-            isPotential[v] = true;
-            isPotentialSum++;
-        }
-        
-        trail--;
-    }
-    
-    for (XorClause** it = solver.xorclauses.getData(), **end = it + solver.xorclauses.size(); it != end; it++) {
-        XorClause& c = **it;
-        for (Lit *l = c.getData(), *end = l + c.size(); l != end; l++) {
-            if (isPotential[l->var()]) {
-                isPotential[l->var()] = false;
-                isPotentialSum--;
-            }
-            assert(!solver.value(*l).isUndef());
-        }
-    }
-    
-    vector<Var> replacingVars = solver.varReplacer->getReplacingVars();
-    for (Var *it = &replacingVars[0], *end = it + replacingVars.size(); it != end; it++) {
-        if (isPotential[*it]) {
-            isPotential[*it] = false;
-            isPotentialSum--;
-        }
-    }
-}
-
-void FindUndef::unboundIsPotentials()
-{
-    for (uint i = 0; i < isPotential.size(); i++)
-        if (isPotential[i])
-            solver.assigns[i] = l_Undef;
-}
-
-void FindUndef::moveBinToNormal()
-{
-    binPosition = solver.clauses.size();
-    for (uint i = 0; i != solver.binaryClauses.size(); i++)
-        solver.clauses.push(solver.binaryClauses[i]);
-    solver.binaryClauses.clear();
-}
-
-void FindUndef::moveBinFromNormal()
-{
-    for (uint i = binPosition; i != solver.clauses.size(); i++)
-        solver.binaryClauses.push(solver.clauses[i]);
-    solver.clauses.shrink(solver.clauses.size() - binPosition);
-}
-
-const uint FindUndef::unRoll()
-{
-    if (solver.decisionLevel() == 0) return 0;
-    
-    moveBinToNormal();
-    
-    dontLookAtClause.resize(solver.clauses.size(), false);
-    isPotential.resize(solver.nVars(), false);
-    fillPotential();
-    satisfies.resize(solver.nVars(), 0);
-    
-    while(!updateTables()) {
-        assert(isPotentialSum > 0);
-        
-        uint32_t maximum = 0;
-        Var v;
-        for (uint i = 0; i < isPotential.size(); i++) {
-            if (isPotential[i] && satisfies[i] >= maximum) {
-                maximum = satisfies[i];
-                v = i;
-            }
-        }
-        
-        isPotential[v] = false;
-        isPotentialSum--;
-        
-        std::fill(satisfies.begin(), satisfies.end(), 0);
-    }
-    
-    unboundIsPotentials();
-    moveBinFromNormal();
-    
-    return isPotentialSum;
-}
-
-bool FindUndef::updateTables()
-{
-    bool allSat = true;
-    
-    uint i = 0;
-    for (Clause** it = solver.clauses.getData(), **end = it + solver.clauses.size(); it != end; it++, i++) {
-        if (dontLookAtClause[i])
-            continue;
-        
-        Clause& c = **it;
-        bool definitelyOK = false;
-        Var v = var_Undef;
-        uint numTrue = 0;
-        for (Lit *l = c.getData(), *end = l + c.size(); l != end; l++) {
-            if (solver.value(*l) == l_True) {
-                if (!isPotential[l->var()]) {
-                    dontLookAtClause[i] = true;
-                    definitelyOK = true;
-                    break;
-                } else {
-                    numTrue ++;
-                    v = l->var();
-                }
-            }
-        }
-        if (definitelyOK)
-            continue;
-        
-        if (numTrue == 1) {
-            assert(v != var_Undef);
-            isPotential[v] = false;
-            isPotentialSum--;
-            dontLookAtClause[i] = true;
-            continue;
-        }
-        
-        //numTrue > 1
-        allSat = false;
-        for (Lit *l = c.getData(), *end = l + c.size(); l != end; l++) {
-            if (solver.value(*l) == l_True)
-                satisfies[l->var()]++;
-        }
-    }
-    
-    return allSat;
-}
-
-}; //NAMESPACE MINISAT
index d3612ac6ff315030cd3ac0222dda70fc123f63f9..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,59 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef FINDUNDEF_H
-#define FINDUNDEF_H
-
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-#include <vector>
-using std::vector;
-
-#include "Solver.h"
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class FindUndef {
-    public:
-        FindUndef(Solver& _solver);
-        const uint unRoll();
-        
-    private:
-        Solver& solver;
-        
-        void moveBinToNormal();
-        void moveBinFromNormal();
-        bool updateTables();
-        void fillPotential();
-        void unboundIsPotentials();
-        
-        vector<bool> dontLookAtClause; //If set to TRUE, then that clause already has only 1 lit that is true, so it can be skipped during updateFixNeed()
-        vector<uint32_t> satisfies;
-        vector<bool> isPotential;
-        uint32_t isPotentialSum;
-        uint32_t binPosition;
-        
-};
-
-}; //NAMESPACE MINISAT
-
-#endif //
\ No newline at end of file
index e7c31ffb950b215ae22c9d0db33bb7db01b68cbf..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#include "Gaussian.h"
-
-#include <iostream>
-#include <iomanip>
-#include "Clause.h"
-#include <algorithm>
-#include "ClauseCleaner.h"
-
-using std::ostream;
-using std::cout;
-using std::endl;
-
-#ifdef VERBOSE_DEBUG
-#include <iterator>
-#endif
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-ostream& operator << (ostream& os, const vec<Lit>& v)
-{
-    for (uint32_t i = 0; i != v.size(); i++) {
-        if (v[i].sign()) os << "-";
-        os << v[i].var()+1 << " ";
-    }
-
-    return os;
-}
-
-Gaussian::Gaussian(Solver& _solver, const GaussianConfig& _config, const uint _matrix_no, const vector<XorClause*>& _xorclauses) :
-        solver(_solver)
-        , config(_config)
-        , matrix_no(_matrix_no)
-        , xorclauses(_xorclauses)
-        , messed_matrix_vars_since_reversal(true)
-        , gauss_last_level(0)
-        , disabled(false)
-        , useful_prop(0)
-        , useful_confl(0)
-        , called(0)
-{
-}
-
-Gaussian::~Gaussian()
-{
-    for (uint i = 0; i < clauses_toclear.size(); i++)
-        clauseFree(clauses_toclear[i].first);
-}
-
-inline void Gaussian::set_matrixset_to_cur()
-{
-    uint level = solver.decisionLevel() / config.only_nth_gauss_save;
-    assert(level <= matrix_sets.size());
-    
-    if (level == matrix_sets.size())
-        matrix_sets.push_back(cur_matrixset);
-    else
-        matrix_sets[level] = cur_matrixset;
-}
-
-llbool Gaussian::full_init()
-{
-    if (!should_init()) return l_Nothing;
-    reset_stats();
-    
-    bool do_again_gauss = true;
-    while (do_again_gauss) {
-        do_again_gauss = false;
-        solver.clauseCleaner->cleanClauses(solver.xorclauses, ClauseCleaner::xorclauses);
-        if (solver.ok == false)
-            return l_False;
-        init();
-        Clause* confl;
-        gaussian_ret g = gaussian(confl);
-        switch (g) {
-        case unit_conflict:
-        case conflict:
-            return l_False;
-        case unit_propagation:
-        case propagation:
-            do_again_gauss=true;
-            if (solver.propagate() != NULL) return l_False;
-            break;
-        case nothing:
-            break;
-        }
-    }
-
-    return l_Nothing;
-}
-
-void Gaussian::init()
-{
-    assert(solver.decisionLevel() == 0);
-
-    fill_matrix(cur_matrixset);
-    if (!cur_matrixset.num_rows || !cur_matrixset.num_cols) {
-        disabled = true;
-        badlevel = 0;
-        return;
-    }
-    
-    matrix_sets.clear();
-    matrix_sets.push_back(cur_matrixset);
-    gauss_last_level = solver.trail.size();
-    messed_matrix_vars_since_reversal = false;
-    badlevel = UINT_MAX;
-
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")Gaussian init finished." << endl;
-    #endif
-}
-
-uint Gaussian::select_columnorder(vector<uint16_t>& var_to_col, matrixset& origMat)
-{
-    var_to_col.resize(solver.nVars(), unassigned_col);
-
-    uint num_xorclauses  = 0;
-    for (uint32_t i = 0; i != xorclauses.size(); i++) {
-        num_xorclauses++;
-        XorClause& c = *xorclauses[i];
-        for (uint i2 = 0; i2 < c.size(); i2++) {
-            assert(solver.assigns[c[i2].var()].isUndef());
-            var_to_col[c[i2].var()] = unassigned_col - 1;
-        }
-    }
-    
-    uint largest_used_var = 0;
-    for (uint i = 0; i < var_to_col.size(); i++)
-        if (var_to_col[i] != unassigned_col)
-            largest_used_var = i;
-    var_to_col.resize(largest_used_var + 1);
-    
-    var_is_in.resize(var_to_col.size(), 0);
-    origMat.var_is_set.resize(var_to_col.size(), 0);
-
-    origMat.col_to_var.clear();
-    Heap<Solver::VarOrderLt> order_heap(solver.order_heap);
-    while (!order_heap.empty())
-    {
-        Var v = order_heap.removeMin();
-
-        if (var_to_col[v] == 1) {
-            #ifdef DEBUG_GAUSS
-            vector<uint>::iterator it =
-                std::find(origMat.col_to_var.begin(), origMat.col_to_var.end(), v);
-            assert(it == origMat.col_to_var.end());
-            #endif
-            
-            origMat.col_to_var.push_back(v);
-            var_to_col[v] = origMat.col_to_var.size()-1;
-            var_is_in.setBit(v);
-        }
-    }
-
-    //for the ones that were not in the order_heap, but are marked in var_to_col
-    for (uint v = 0; v != var_to_col.size(); v++) {
-        if (var_to_col[v] == unassigned_col - 1) {
-            origMat.col_to_var.push_back(v);
-            var_to_col[v] = origMat.col_to_var.size() -1;
-            var_is_in.setBit(v);
-        }
-    }
-
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")col_to_var:";
-    std::copy(origMat.col_to_var.begin(), origMat.col_to_var.end(), std::ostream_iterator<uint>(cout, ","));
-    cout << endl;
-    #endif
-
-    return num_xorclauses;
-}
-
-void Gaussian::fill_matrix(matrixset& origMat)
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")Filling matrix" << endl;
-    #endif
-
-    vector<uint16_t> var_to_col;
-    origMat.num_rows = select_columnorder(var_to_col, origMat);
-    origMat.num_cols = origMat.col_to_var.size();
-    col_to_var_original = origMat.col_to_var;
-    changed_rows.resize(origMat.num_rows);
-    memset(&changed_rows[0], 0, sizeof(char)*changed_rows.size());
-
-    origMat.last_one_in_col.resize(origMat.num_cols);
-    std::fill(origMat.last_one_in_col.begin(), origMat.last_one_in_col.end(), origMat.num_rows);
-    origMat.first_one_in_row.resize(origMat.num_rows);
-    
-    origMat.removeable_cols = 0;
-    origMat.least_column_changed = -1;
-    origMat.matrix.resize(origMat.num_rows, origMat.num_cols);
-
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")matrix size:" << origMat.num_rows << "," << origMat.num_cols << endl;
-    #endif
-
-    uint matrix_row = 0;
-    for (uint32_t i = 0; i != xorclauses.size(); i++) {
-        const XorClause& c = *xorclauses[i];
-
-        origMat.matrix.getVarsetAt(matrix_row).set(c, var_to_col, origMat.num_cols);
-        origMat.matrix.getMatrixAt(matrix_row).set(c, var_to_col, origMat.num_cols);
-        matrix_row++;
-    }
-    assert(origMat.num_rows == matrix_row);
-}
-
-void Gaussian::update_matrix_col(matrixset& m, const Var var, const uint col)
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")Updating matrix var " << var+1 << " (col " << col << ", m.last_one_in_col[col]: " << m.last_one_in_col[col] << ")" << endl;
-    cout << "m.num_rows:" << m.num_rows << endl;
-    #endif
-    
-    #ifdef DEBUG_GAUSS
-    assert(col < m.num_cols);
-    #endif
-    
-    m.least_column_changed = std::min(m.least_column_changed, (int)col);
-    PackedMatrix::iterator this_row = m.matrix.beginMatrix();
-    uint row_num = 0;
-
-    if (solver.assigns[var].getBool()) {
-        for (uint end = m.last_one_in_col[col];  row_num != end; ++this_row, row_num++) {
-            if ((*this_row)[col]) {
-                changed_rows[row_num] = true;
-                (*this_row).invert_is_true();
-                (*this_row).clearBit(col);
-            }
-        }
-    } else {
-        for (uint end = m.last_one_in_col[col];  row_num != end; ++this_row, row_num++) {
-            if ((*this_row)[col]) {
-                changed_rows[row_num] = true;
-                (*this_row).clearBit(col);
-            }
-        }
-    }
-
-    #ifdef DEBUG_GAUSS
-    bool c = false;
-    for(PackedMatrix::iterator r = m.matrix.beginMatrix(), end = r + m.matrix.getSize(); r != end; ++r)
-        c |= (*r)[col];
-    assert(!c);
-    #endif
-
-    m.removeable_cols++;
-    m.col_to_var[col] = unassigned_var;
-    m.var_is_set.setBit(var);
-}
-
-void Gaussian::update_matrix_by_col_all(matrixset& m)
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")Updating matrix." << endl;
-    print_matrix(m);
-    uint num_updated = 0;
-    #endif
-    
-    #ifdef DEBUG_GAUSS
-    assert(nothing_to_propagate(cur_matrixset));
-    assert(solver.decisionLevel() == 0 || check_last_one_in_cols(m));
-    #endif
-    
-    memset(&changed_rows[0], 0, sizeof(char)*changed_rows.size());
-
-    uint last = 0;
-    uint col = 0;
-    for (const Var *it = &m.col_to_var[0], *end = it + m.num_cols; it != end; col++, it++) {
-        if (*it != unassigned_var && solver.assigns[*it].isDef()) {
-            update_matrix_col(m, *it, col);
-            last++;
-            #ifdef VERBOSE_DEBUG
-            num_updated++;
-            #endif
-        } else
-            last = 0;
-    }
-    m.num_cols -= last;
-    
-    #ifdef DEBUG_GAUSS
-    check_matrix_against_varset(m.matrix, m);
-    #endif
-
-    #ifdef VERBOSE_DEBUG
-    cout << "Matrix update finished, updated " << num_updated << " cols" << endl;
-    print_matrix(m);
-    #endif
-    
-    /*cout << "num_rows:" << m.num_rows;
-    cout << " num_rows diff:" << origMat.num_rows - m.num_rows << endl;
-    cout << "num_cols:" << col_to_var_original.size();
-    cout << " num_cols diff:" << col_to_var_original.size() - m.col_to_var.size() << endl;
-    cout << "removeable cols:" << m.removeable_cols << endl;*/
-}
-
-inline void Gaussian::update_last_one_in_col(matrixset& m)
-{
-    for (uint16_t* i = &m.last_one_in_col[0]+m.last_one_in_col.size()-1, *end = &m.last_one_in_col[0]-1; i != end && *i >= m.num_rows; i--)
-        *i = m.num_rows;
-}
-
-Gaussian::gaussian_ret Gaussian::gaussian(Clause*& confl)
-{
-    if (solver.decisionLevel() >= badlevel)
-        return nothing;
-
-    if (messed_matrix_vars_since_reversal) {
-        #ifdef VERBOSE_DEBUG
-        cout << "(" << matrix_no << ")matrix needs copy before update" << endl;
-        #endif
-        
-        const uint level = solver.decisionLevel() / config.only_nth_gauss_save;
-        assert(level < matrix_sets.size());
-        cur_matrixset = matrix_sets[level];
-    }
-    update_last_one_in_col(cur_matrixset);
-    update_matrix_by_col_all(cur_matrixset);
-
-    messed_matrix_vars_since_reversal = false;
-    gauss_last_level = solver.trail.size();
-    badlevel = UINT_MAX;
-
-    propagatable_rows.clear();
-    uint conflict_row = UINT_MAX;
-    uint last_row = eliminate(cur_matrixset, conflict_row);
-    #ifdef DEBUG_GAUSS
-    check_matrix_against_varset(cur_matrixset.matrix, cur_matrixset);
-    #endif
-    
-    gaussian_ret ret;
-    //There is no early abort, so this is unneeded
-    /*if (conflict_row != UINT_MAX) {
-        uint maxlevel = UINT_MAX;
-        uint size = UINT_MAX;
-        uint best_row = UINT_MAX;
-        analyse_confl(cur_matrixset, conflict_row, maxlevel, size, best_row);
-        ret = handle_matrix_confl(confl, cur_matrixset, size, maxlevel, best_row);
-    } else {*/
-        ret = handle_matrix_prop_and_confl(cur_matrixset, last_row, confl);
-    //}
-    #ifdef DEBUG_GAUSS
-    assert(ret == conflict || nothing_to_propagate(cur_matrixset));
-    #endif
-    
-    if (!cur_matrixset.num_cols || !cur_matrixset.num_rows) {
-        badlevel = solver.decisionLevel();
-        return nothing;
-    }
-    
-    if (ret == nothing &&
-        solver.decisionLevel() % config.only_nth_gauss_save == 0)
-        set_matrixset_to_cur();
-
-    #ifdef VERBOSE_DEBUG
-    if (ret == nothing)
-        cout << "(" << matrix_no << ")Useless. ";
-    else
-        cout << "(" << matrix_no << ")Useful. ";
-    cout << "(" << matrix_no << ")Useful prop in " << ((double)useful_prop/(double)called)*100.0 << "%" << endl;
-    cout << "(" << matrix_no << ")Useful confl in " << ((double)useful_confl/(double)called)*100.0 << "%" << endl;
-    #endif
-
-    return ret;
-}
-
-uint Gaussian::eliminate(matrixset& m, uint& conflict_row)
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")";
-    cout << "Starting elimination" << endl;
-    cout << "m.least_column_changed:" << m.least_column_changed << endl;
-    print_last_one_in_cols(m);
-    
-    uint number_of_row_additions = 0;
-    uint no_exchanged = 0;
-    #endif
-    
-    if (m.least_column_changed == INT_MAX) {
-        #ifdef VERBOSE_DEBUG
-        cout << "Nothing to eliminate" << endl;
-        #endif
-        
-        return m.num_rows;
-    }
-    
-    
-    #ifdef DEBUG_GAUSS
-    assert(solver.decisionLevel() == 0 || check_last_one_in_cols(m));
-    #endif
-
-    uint i = 0;
-    uint j = m.least_column_changed + 1;
-    PackedMatrix::iterator beginIt = m.matrix.beginMatrix();
-    PackedMatrix::iterator rowIt = m.matrix.beginMatrix();
-
-    #ifdef DEBUG_GAUSS
-    check_first_one_in_row(m, j);
-    #endif
-    
-    if (j) {
-        uint16_t until = std::min(m.last_one_in_col[m.least_column_changed] - 1, (int)m.num_rows);
-        if (j-1 > m.first_one_in_row[m.num_rows-1])
-            until = m.num_rows;
-        for (;i != until; i++, ++rowIt) if (changed_rows[i] && (*rowIt).popcnt_is_one(m.first_one_in_row[i]))
-            propagatable_rows.push(i);
-    }
-    
-    #ifdef VERBOSE_DEBUG
-    cout << "At while() start: i,j = " << i << ", " << j << endl;
-    cout << "num_rows:" << m.num_rows << " num_cols:" << m.num_cols << endl;
-    #endif
-    
-    if (j > m.num_cols) {
-        #ifdef VERBOSE_DEBUG
-        cout << "Going straight to finish" << endl;
-        #endif
-        goto finish;
-    }
-    
-    #ifdef DEBUG_GAUSS
-    assert(i <= m.num_rows && j <= m.num_cols);
-    #endif
-
-    while (i != m.num_rows && j != m.num_cols) {
-        //Find pivot in column j, starting in row i:
-
-        if (m.col_to_var[j] == unassigned_var) {
-            j++;
-            continue;
-        }
-
-        PackedMatrix::iterator this_matrix_row = rowIt;
-        PackedMatrix::iterator end = beginIt + m.last_one_in_col[j];
-        for (; this_matrix_row != end; ++this_matrix_row) {
-            if ((*this_matrix_row)[j])
-                break;
-        }
-
-        if (this_matrix_row != end) {
-
-            //swap rows i and maxi, but do not change the value of i;
-            if (this_matrix_row != rowIt) {
-                #ifdef VERBOSE_DEBUG
-                no_exchanged++;
-                #endif
-                
-                //Would early abort, but would not find the best conflict (and would be expensive)
-                //if (matrix_row_i.is_true() && matrix_row_i.isZero()) {
-                //    conflict_row = i;
-                //    return 0;
-                //}
-                (*rowIt).swapBoth(*this_matrix_row);
-            }
-            #ifdef DEBUG_GAUSS
-            assert(m.matrix.getMatrixAt(i).popcnt(j) == m.matrix.getMatrixAt(i).popcnt());
-            assert(m.matrix.getMatrixAt(i)[j]);
-            #endif
-
-            if ((*rowIt).popcnt_is_one(j))
-                propagatable_rows.push(i);
-
-            //Now A[i,j] will contain the old value of A[maxi,j];
-            ++this_matrix_row;
-            for (; this_matrix_row != end; ++this_matrix_row) if ((*this_matrix_row)[j]) {
-                //subtract row i from row u;
-                //Now A[u,j] will be 0, since A[u,j] - A[i,j] = A[u,j] -1 = 0.
-                #ifdef VERBOSE_DEBUG
-                number_of_row_additions++;
-                #endif
-                
-                (*this_matrix_row).xorBoth(*rowIt);
-                //Would early abort, but would not find the best conflict (and would be expensive)
-                //if (it->is_true() &&it->isZero()) {
-                //    conflict_row = i2;
-                //    return 0;
-                //}
-            }
-            m.first_one_in_row[i] = j;
-            i++;
-            ++rowIt;
-            m.last_one_in_col[j] = i;
-        } else {
-            m.first_one_in_row[i] = j;
-            m.last_one_in_col[j] = i + 1;
-        }
-        j++;
-    }
-    
-    finish:
-
-    m.least_column_changed = INT_MAX;
-
-    #ifdef VERBOSE_DEBUG
-    cout << "Finished elimination" << endl;
-    cout << "Returning with i,j:" << i << ", " << j << "(" << m.num_rows << ", " << m.num_cols << ")" << endl;
-    print_matrix(m);
-    print_last_one_in_cols(m);
-    cout << "(" << matrix_no << ")Exchanged:" << no_exchanged << " row additions:" << number_of_row_additions << endl;
-    #endif
-    
-    #ifdef DEBUG_GAUSS
-    assert(check_last_one_in_cols(m));
-    uint row = 0;
-    uint col = 0;
-    for (; col < m.num_cols && row < m.num_rows && row < i ; col++) {
-        assert(m.matrix.getMatrixAt(row).popcnt() == m.matrix.getMatrixAt(row).popcnt(col));
-        assert(!(m.col_to_var[col] == unassigned_var && m.matrix.getMatrixAt(row)[col]));
-        if (m.col_to_var[col] == unassigned_var || !m.matrix.getMatrixAt(row)[col]) {
-            #ifdef VERBOSE_DEBUG
-            cout << "row:" << row << " col:" << col << " m.last_one_in_col[col]-1: " << m.last_one_in_col[col]-1 << endl;
-            #endif
-            assert(m.col_to_var[col] == unassigned_var || std::min((uint16_t)(m.last_one_in_col[col]-1), m.num_rows) == row);
-            continue;
-        }
-        row++;
-    }
-    #endif
-
-    return i;
-}
-
-Gaussian::gaussian_ret Gaussian::handle_matrix_confl(Clause*& confl, const matrixset& m, const uint size, const uint maxlevel, const uint best_row)
-{
-    assert(best_row != UINT_MAX);
-
-    m.matrix.getVarsetAt(best_row).fill(tmp_clause, solver.assigns, col_to_var_original);
-    confl = (Clause*)XorClause_new(tmp_clause, false, solver.learnt_clause_group++);
-    Clause& cla = *confl;
-    #ifdef STATS_NEEDED
-    if (solver.dynamic_behaviour_analysis)
-        solver.logger.set_group_name(confl->getGroup(), "learnt gauss clause");
-    #endif
-    
-    if (cla.size() <= 1)
-        return unit_conflict;
-
-    assert(cla.size() >= 2);
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")Found conflict:";
-    cla.plainPrint();
-    #endif
-
-    if (maxlevel != solver.decisionLevel()) {
-        #ifdef STATS_NEEDED
-        if (solver.dynamic_behaviour_analysis)
-            solver.logger.conflict(Logger::gauss_confl_type, maxlevel, confl->getGroup(), *confl);
-        #endif
-        solver.cancelUntil(maxlevel);
-    }
-    const uint curr_dec_level = solver.decisionLevel();
-    assert(maxlevel == curr_dec_level);
-    
-    uint maxsublevel = 0;
-    uint maxsublevel_at = UINT_MAX;
-    for (uint i = 0, size = cla.size(); i != size; i++) if (solver.level[cla[i].var()] == curr_dec_level) {
-        uint tmp = find_sublevel(cla[i].var());
-        if (tmp >= maxsublevel) {
-            maxsublevel = tmp;
-            maxsublevel_at = i;
-        }
-    }
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ") || Sublevel of confl: " << maxsublevel << " (due to var:" << cla[maxsublevel_at].var()-1 << ")" << endl;
-    #endif
-    
-    Lit tmp(cla[maxsublevel_at]);
-    cla[maxsublevel_at] = cla[1];
-    cla[1] = tmp;
-
-    cancel_until_sublevel(maxsublevel+1);
-    messed_matrix_vars_since_reversal = true;
-    return conflict;
-}
-
-Gaussian::gaussian_ret Gaussian::handle_matrix_prop_and_confl(matrixset& m, uint last_row, Clause*& confl)
-{
-    uint maxlevel = UINT_MAX;
-    uint size = UINT_MAX;
-    uint best_row = UINT_MAX;
-
-    for (uint row = last_row; row != m.num_rows; row++) {
-        #ifdef DEBUG_GAUSS
-        assert(m.matrix.getMatrixAt(row).isZero());
-        #endif
-        if (m.matrix.getMatrixAt(row).is_true())
-            analyse_confl(m, row, maxlevel, size, best_row);
-    }
-
-    if (maxlevel != UINT_MAX)
-        return handle_matrix_confl(confl, m, size, maxlevel, best_row);
-
-    #ifdef DEBUG_GAUSS
-    assert(check_no_conflict(m));
-    assert(last_row == 0 || !m.matrix.getMatrixAt(last_row-1).isZero());
-    #endif
-    
-    #ifdef VERBOSE_DEBUG
-    cout << "Resizing matrix to num_rows = " << last_row << endl;
-    #endif
-    m.num_rows = last_row;
-    m.matrix.resizeNumRows(m.num_rows);
-
-    gaussian_ret ret = nothing;
-
-    uint num_props = 0;
-    for (const uint* prop_row = propagatable_rows.getData(), *end = prop_row + propagatable_rows.size(); prop_row != end; prop_row++ ) {
-        //this is a "000..1..0000000X" row. I.e. it indicates a propagation
-        ret = handle_matrix_prop(m, *prop_row);
-        num_props++;
-        if (ret == unit_propagation) {
-            #ifdef VERBOSE_DEBUG
-            cout << "(" << matrix_no << ")Unit prop! Breaking from prop examination" << endl;
-            #endif
-            return  unit_propagation;
-        }
-    }
-    #ifdef VERBOSE_DEBUG
-    if (num_props > 0) cout << "(" << matrix_no << ")Number of props during gauss:" << num_props << endl;
-    #endif
-
-    return ret;
-}
-
-uint Gaussian::find_sublevel(const Var v) const
-{
-    for (int i = solver.trail.size()-1; i >= 0; i --)
-        if (solver.trail[i].var() == v) return i;
-    
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")Oooops! Var " << v+1 << " does not have a sublevel!! (so it must be undefined)" << endl;
-    #endif
-    
-    assert(false);
-    return 0;
-}
-
-void Gaussian::cancel_until_sublevel(const uint sublevel)
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")Canceling until sublevel " << sublevel << endl;
-    #endif
-    
-    for (vector<Gaussian*>::iterator gauss = solver.gauss_matrixes.begin(), end= solver.gauss_matrixes.end(); gauss != end; gauss++)
-        if (*gauss != this) (*gauss)->canceling(sublevel);
-
-    for (int level = solver.trail.size()-1; level >= (int)sublevel; level--) {
-        Var     var  = solver.trail[level].var();
-        #ifdef VERBOSE_DEBUG
-        cout << "(" << matrix_no << ")Canceling var " << var+1 << endl;
-        #endif
-
-        solver.assigns[var] = l_Undef;
-        solver.insertVarOrder(var);
-    }
-    solver.trail.shrink(solver.trail.size() - sublevel);
-    
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")Canceling sublevel finished." << endl;
-    #endif
-}
-
-void Gaussian::analyse_confl(const matrixset& m, const uint row, uint& maxlevel, uint& size, uint& best_row) const
-{
-    assert(row < m.num_rows);
-
-    //this is a "000...00000001" row. I.e. it indicates we are on the wrong branch
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")matrix conflict found!" << endl;
-    cout << "(" << matrix_no << ")conflict clause's vars: ";
-    print_matrix_row_with_assigns(m.matrix.getVarsetAt(row));
-    cout << endl;
-    
-    cout << "(" << matrix_no << ")corresponding matrix's row (should be empty): ";
-    print_matrix_row(m.matrix.getMatrixAt(row));
-    cout << endl;
-    #endif
-
-    uint this_maxlevel = 0;
-    unsigned long int var = 0;
-    uint this_size = 0;
-    while (true) {
-        var = m.matrix.getVarsetAt(row).scan(var);
-        if (var == ULONG_MAX) break;
-
-        const Var real_var = col_to_var_original[var];
-        assert(real_var < solver.nVars());
-
-        if (solver.level[real_var] > this_maxlevel)
-            this_maxlevel = solver.level[real_var];
-        var++;
-        this_size++;
-    }
-
-    //the maximum of all lit's level must be lower than the max. level of the current best clause (or this clause must be either empty or unit clause)
-    if (!(
-                (this_maxlevel < maxlevel)
-                || (this_maxlevel == maxlevel && this_size < size)
-                || (this_size <= 1)
-            )) {
-        assert(maxlevel != UINT_MAX);
-    
-        #ifdef VERBOSE_DEBUG
-        cout << "(" << matrix_no << ")Other found conflict just as good or better.";
-        cout << "(" << matrix_no << ") || Old maxlevel:" << maxlevel << " new maxlevel:" << this_maxlevel;
-        cout << "(" << matrix_no << ") || Old size:" << size << " new size:" << this_size << endl;
-        //assert(!(maxlevel != UINT_MAX && maxlevel != this_maxlevel)); //NOTE: only holds if gauss is executed at each level
-        #endif
-        
-        return;
-    }
-
-
-    #ifdef VERBOSE_DEBUG
-    if (maxlevel != UINT_MAX)
-        cout << "(" << matrix_no << ")Better conflict found.";
-    else
-        cout << "(" << matrix_no << ")Found a possible conflict.";
-
-    cout << "(" << matrix_no << ") || Old maxlevel:" << maxlevel << " new maxlevel:" << this_maxlevel;
-    cout << "(" << matrix_no << ") || Old size:" << size << " new size:" << this_size << endl;
-    #endif
-
-    maxlevel = this_maxlevel;
-    size = this_size;
-    best_row = row;
-}
-
-Gaussian::gaussian_ret Gaussian::handle_matrix_prop(matrixset& m, const uint row)
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")matrix prop found!" << endl;
-    cout << m.matrix.getMatrixAt(row) << endl;
-    cout << "(" << matrix_no << ")matrix row:";
-    print_matrix_row(m.matrix.getMatrixAt(row));
-    cout << endl;
-    #endif
-
-    m.matrix.getVarsetAt(row).fill(tmp_clause, solver.assigns, col_to_var_original);
-    Clause& cla = *(Clause*)XorClause_new(tmp_clause, false, solver.learnt_clause_group++);
-    #ifdef VERBOSE_DEBUG
-    cout << "(" << matrix_no << ")matrix prop clause: ";
-    cla.plainPrint();
-    cout << endl;
-    #endif
-    
-    assert(m.matrix.getMatrixAt(row).is_true() == !cla[0].sign());
-    assert(solver.assigns[cla[0].var()].isUndef());
-    if (cla.size() == 1) {
-        const Lit lit = cla[0];
-        
-        solver.cancelUntil(0);
-        solver.uncheckedEnqueue(lit);
-        free(&cla);
-        return unit_propagation;
-    }
-
-    clauses_toclear.push_back(std::make_pair(&cla, solver.trail.size()-1));
-    #ifdef STATS_NEEDED
-    if (solver.dynamic_behaviour_analysis)
-        solver.logger.set_group_name(cla.getGroup(), "gauss prop clause");
-    #endif
-    solver.uncheckedEnqueue(cla[0], &cla);
-
-    return propagation;
-}
-
-void Gaussian::disable_if_necessary()
-{
-    if (//nof_conflicts >= 0
-        //&& conflictC >= nof_conflicts/8
-        !config.dontDisable
-        && called > 50
-        && useful_confl*2+useful_prop < (uint)((double)called*0.05) )
-            disabled = true;
-}
-
-llbool Gaussian::find_truths(vec<Lit>& learnt_clause, int& conflictC)
-{
-    Clause* confl;
-
-    disable_if_necessary();
-    if (should_check_gauss(solver.decisionLevel(), solver.starts)) {
-        called++;
-        gaussian_ret g = gaussian(confl);
-        
-        switch (g) {
-        case conflict: {
-            useful_confl++;
-            llbool ret = solver.handle_conflict(learnt_clause, confl, conflictC, true);
-            clauseFree(confl);
-            
-            if (ret != l_Nothing) return ret;
-            return l_Continue;
-        }
-        case propagation:
-        case unit_propagation:
-            useful_prop++;
-            return l_Continue;
-        case unit_conflict: {
-            useful_confl++;
-            if (confl->size() == 0) {
-                free(confl);
-                return l_False;
-            }
-
-            Lit lit = (*confl)[0];
-            #ifdef STATS_NEEDED
-            if (solver.dynamic_behaviour_analysis)
-                solver.logger.conflict(Logger::gauss_confl_type, 0, confl->getGroup(), *confl);
-            #endif
-            
-            solver.cancelUntil(0);
-            
-            if (solver.assigns[lit.var()].isDef()) {
-                clauseFree(confl);
-                return l_False;
-            }
-            
-            solver.uncheckedEnqueue(lit);
-            
-            clauseFree(confl);
-            return l_Continue;
-        }
-        case nothing:
-            break;
-        }
-    }
-
-    return l_Nothing;
-}
-
-template<class T>
-void Gaussian::print_matrix_row(const T& row) const
-{
-    unsigned long int var = 0;
-    while (true) {
-        var = row.scan(var);
-        if (var == ULONG_MAX) break;
-
-        else cout << col_to_var_original[var]+1 << ", ";
-        var++;
-    }
-    cout << "final:" << row.is_true() << endl;;
-}
-
-template<class T>
-void Gaussian::print_matrix_row_with_assigns(const T& row) const
-{
-    unsigned long int col = 0;
-    while (true) {
-        col = row.scan(col);
-        if (col == ULONG_MAX) break;
-        
-        else {
-            Var var = col_to_var_original[col];
-            cout << var+1 << "(" << lbool_to_string(solver.assigns[var]) << ")";
-            cout << ", ";
-        }
-        col++;
-    }
-    if (!row.is_true()) cout << "xor_clause_inverted";
-}
-
-const string Gaussian::lbool_to_string(const lbool toprint)
-{
-    if (toprint == l_True)
-            return "true";
-    if (toprint == l_False)
-            return "false";
-    if (toprint == l_Undef)
-            return "undef";
-    
-    assert(false);
-    return "";
-}
-
-
-void Gaussian::print_stats() const
-{
-    if (called > 0) {
-        cout.setf(std::ios::fixed);
-        std::cout << " Gauss(" << matrix_no << ") useful";
-        cout << " prop: " << std::setprecision(2) << std::setw(5) << ((double)useful_prop/(double)called)*100.0 << "% ";
-        cout << " confl: " << std::setprecision(2) << std::setw(5) << ((double)useful_confl/(double)called)*100.0 << "% ";
-        if (disabled) std::cout << "disabled";
-    } else
-        std::cout << " Gauss(" << matrix_no << ") not called.";
-}
-
-void Gaussian::print_matrix_stats() const
-{
-    cout << "matrix size: " << cur_matrixset.num_rows << "  x " << cur_matrixset.num_cols << endl;
-}
-
-
-void Gaussian::reset_stats()
-{
-    useful_prop = 0;
-    useful_confl = 0;
-    called = 0;
-    disabled = false;
-}
-
-bool Gaussian::check_no_conflict(matrixset& m) const
-{
-    uint row = 0;
-    for(PackedMatrix::iterator r = m.matrix.beginMatrix(), end = m.matrix.endMatrix(); r != end; ++r, ++row) {
-        if ((*r).is_true() && (*r).isZero()) {
-            cout << "Conflict at row " << row << endl;
-            return false;
-        }
-    }
-    return true;
-}
-
-void Gaussian::print_matrix(matrixset& m) const
-{
-    uint row = 0;
-    for (PackedMatrix::iterator it = m.matrix.beginMatrix(); it != m.matrix.endMatrix(); ++it, row++) {
-        cout << *it << " -- row:" << row;
-        if (row >= m.num_rows)
-            cout << " (considered past the end)";
-        cout << endl;
-    }
-}
-
-void Gaussian::print_last_one_in_cols(matrixset& m) const
-{
-    for (uint i = 0; i < m.num_cols; i++) {
-        cout << "last_one_in_col[" << i << "]-1 = " << m.last_one_in_col[i]-1 << endl;
-    }
-}
-
-const bool Gaussian::nothing_to_propagate(matrixset& m) const
-{
-    for(PackedMatrix::iterator r = m.matrix.beginMatrix(), end = m.matrix.endMatrix(); r != end; ++r) {
-        if ((*r).popcnt_is_one()
-            && solver.assigns[m.col_to_var[(*r).scan(0)]].isUndef())
-            return false;
-    }
-    for(PackedMatrix::iterator r = m.matrix.beginMatrix(), end = m.matrix.endMatrix(); r != end; ++r) {
-        if ((*r).isZero() && (*r).is_true())
-            return false;
-    }
-    return true;
-}
-
-const bool Gaussian::check_last_one_in_cols(matrixset& m) const
-{
-    for(uint i = 0; i < m.num_cols; i++) {
-        const uint last = std::min(m.last_one_in_col[i] - 1, (int)m.num_rows);
-        uint real_last = 0;
-        uint i2 = 0;
-        for (PackedMatrix::iterator it = m.matrix.beginMatrix(); it != m.matrix.endMatrix(); ++it, i2++) {
-            if ((*it)[i])
-                real_last = i2;
-        }
-        if (real_last > last)
-            return false;
-    }
-    
-    return true;
-}
-
-void Gaussian::check_matrix_against_varset(PackedMatrix& matrix, const matrixset& m) const
-{
-    for (uint i = 0; i < matrix.getSize(); i++) {
-        const PackedRow mat_row = matrix.getMatrixAt(i);
-        const PackedRow var_row = matrix.getVarsetAt(i);
-        
-        unsigned long int col = 0;
-        bool final = false;
-        while (true) {
-            col = var_row.scan(col);
-            if (col == ULONG_MAX) break;
-            
-            const Var var = col_to_var_original[col];
-            assert(var < solver.nVars());
-            
-            if (solver.assigns[var] == l_True) {
-                assert(!mat_row[col]);
-                assert(m.col_to_var[col] == unassigned_var);
-                assert(m.var_is_set[var]);
-                final = !final;
-            } else if (solver.assigns[var] == l_False) {
-                assert(!mat_row[col]);
-                assert(m.col_to_var[col] == unassigned_var);
-                assert(m.var_is_set[var]);
-            } else if (solver.assigns[var] == l_Undef) {
-                assert(m.col_to_var[col] != unassigned_var);
-                assert(!m.var_is_set[var]);
-                assert(mat_row[col]);
-            } else assert(false);
-            
-            col++;
-        }
-        if ((final^!mat_row.is_true()) != !var_row.is_true()) {
-            cout << "problem with row:"; print_matrix_row_with_assigns(var_row); cout << endl;
-            assert(false);
-        }
-    }
-}
-
-const void Gaussian::check_first_one_in_row(matrixset& m, const uint j)
-{
-    if (j) {
-        uint16_t until2 = std::min(m.last_one_in_col[m.least_column_changed] - 1, (int)m.num_rows);
-        if (j-1 > m.first_one_in_row[m.num_rows-1]) {
-            until2 = m.num_rows;
-            #ifdef VERBOSE_DEBUG
-            cout << "j-1 > m.first_one_in_row[m.num_rows-1]" << "j:" << j << " m.first_one_in_row[m.num_rows-1]:" << m.first_one_in_row[m.num_rows-1] << endl;
-            #endif
-        }
-        for (uint i2 = 0; i2 != until2; i2++) {
-            #ifdef VERBOSE_DEBUG
-            cout << endl << "row " << i2 << " (num rows:" << m.num_rows << ")" << endl;
-            cout << m.matrix.getMatrixAt(i2) << endl;
-            cout << " m.first_one_in_row[m.num_rows-1]:" << m.first_one_in_row[m.num_rows-1] << endl;
-            cout << "first_one_in_row:" << m.first_one_in_row[i2] << endl;
-            cout << "num_cols:" << m.num_cols << endl;
-            cout << "popcnt:" << m.matrix.getMatrixAt(i2).popcnt() << endl;
-            cout << "popcnt_is_one():" << m.matrix.getMatrixAt(i2).popcnt_is_one() << endl;
-            cout << "popcnt_is_one("<< m.first_one_in_row[i2] <<"): " << m.matrix.getMatrixAt(i2).popcnt_is_one(m.first_one_in_row[i2]) << endl;
-            #endif
-            
-            for (uint i3 = 0; i3 < m.first_one_in_row[i2]; i3++) {
-                assert(m.matrix.getMatrixAt(i2)[i3] == 0);
-            }
-            assert(m.matrix.getMatrixAt(i2)[m.first_one_in_row[i2]]);
-            assert(m.matrix.getMatrixAt(i2).popcnt_is_one() ==
-            m.matrix.getMatrixAt(i2).popcnt_is_one(m.first_one_in_row[i2]));
-        }
-    }
-}
-
-const uint Gaussian::get_called() const
-{
-    return called;
-}
-
-const uint Gaussian::get_useful_prop() const
-{
-    return useful_prop;
-}
-
-const uint Gaussian::get_useful_confl() const
-{
-    return useful_confl;
-}
-
-const bool Gaussian::get_disabled() const
-{
-    return disabled;
-}
-
-void Gaussian::set_disabled(const bool toset)
-{
-    disabled = toset;
-}
-
-//old functions
-
-/*void Gaussian::update_matrix_by_row(matrixset& m) const
-{
-#ifdef VERBOSE_DEBUG
-    cout << "Updating matrix." << endl;
-    uint num_updated = 0;
-#endif
-#ifdef DEBUG_GAUSS
-    assert(nothing_to_propagate(cur_matrixset));
-#endif
-
-    mpz_class toclear, tocount;
-    uint last_col = 0;
-
-    for (uint col = 0; col < m.num_cols; col ++) {
-        Var var = m.col_to_var[col];
-
-        if (var != UINT_MAX && !solver.assigns[var].isUndef()) {
-            toclear.setBit(col);
-            if (solver.assigns[var].getBool()) tocount.setBit(col);
-
-#ifdef DEBUG_GAUSS
-            assert(m.var_to_col[var] < UINT_MAX-1);
-#endif
-            last_col = col;
-            m.least_column_changed = std::min(m.least_column_changed, (int)col);
-
-            m.removeable_cols++;
-            m.col_to_var[col] = UINT_MAX;
-            m.var_to_col[var] = UINT_MAX-1;
-#ifdef VERBOSE_DEBUG
-            num_updated++;
-#endif
-        }
-    }
-
-    toclear.invert();
-    mpz_class tmp;
-    mpz_class* this_row = &m.matrix[0];
-    for(uint i = 0, until = std::min(m.num_rows, m.last_one_in_col[last_col]+1); i < until; i++, this_row++) {
-        mpz_class& r = *this_row;
-        mpz_and(tmp.get_mp(), tocount.get_mp(), r.get_mp());
-        r.invert_is_true(tmp.popcnt() % 2);
-        r &= toclear;
-}
-
-#ifdef VERBOSE_DEBUG
-    cout << "Updated " << num_updated << " matrix cols. Could remove " << m.removeable_cols << " cols " <<endl;
-#endif
-}*/
-
-/*void Gaussian::update_matrix_by_col(matrixset& m, const uint last_level) const
-{
-#ifdef VERBOSE_DEBUG
-    cout << "Updating matrix." << endl;
-    uint num_updated = 0;
-#endif
-#ifdef DEBUG_GAUSS
-    assert(nothing_to_propagate(cur_matrixset));
-#endif
-
-    for (int level = solver.trail.size()-1; level >= last_level; level--){
-        Var var = solver.trail[level].var();
-        const uint col = m.var_to_col[var];
-        if ( col < UINT_MAX-1) {
-            update_matrix_col(m, var, col);
-#ifdef VERBOSE_DEBUG
-            num_updated++;
-#endif
-        }
-    }
-
-#ifdef VERBOSE_DEBUG
-    cout << "Updated " << num_updated << " matrix cols. Could remove " << m.removeable_cols << " cols (out of " << m.num_cols << " )" <<endl;
-#endif
-}*/
-
-}; //NAMESPACE MINISAT
index 5fb66aa5844f8b4f11319358dbaf440633c1b11d..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,213 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef GAUSSIAN_H
-#define GAUSSIAN_H
-
-#include <vector>
-#include <limits>
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-#include "SolverTypes.h"
-#include "Solver.h"
-#include "GaussianConfig.h"
-#include "PackedMatrix.h"
-#include "BitArray.h"
-
-//#define VERBOSE_DEBUG
-//#define DEBUG_GAUSS
-
-#ifdef VERBOSE_DEBUG
-using std::vector;
-using std::cout;
-using std::endl;
-#endif
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class Clause;
-
-static const uint16_t unassigned_col = std::numeric_limits<uint16_t>::max();
-static const Var unassigned_var = std::numeric_limits<Var>::max();
-
-class Gaussian
-{
-public:
-    Gaussian(Solver& solver, const GaussianConfig& config, const uint matrix_no, const vector<XorClause*>& xorclauses);
-    ~Gaussian();
-
-    llbool full_init();
-    llbool find_truths(vec<Lit>& learnt_clause, int& conflictC);
-
-    //statistics
-    void print_stats() const;
-    void print_matrix_stats() const;
-    const uint get_called() const;
-    const uint get_useful_prop() const;
-    const uint get_useful_confl() const;
-    const bool get_disabled() const;
-    void set_disabled(const bool toset);
-
-    //functions used throughout the Solver
-    void canceling(const uint sublevel);
-
-protected:
-    Solver& solver;
-    
-    //Gauss high-level configuration
-    const GaussianConfig& config;
-    const uint matrix_no;
-    vector<XorClause*> xorclauses;
-
-    enum gaussian_ret {conflict, unit_conflict, propagation, unit_propagation, nothing};
-    gaussian_ret gaussian(Clause*& confl);
-
-    vector<Var> col_to_var_original; //Matches columns to variables
-    BitArray var_is_in; //variable is part of the the matrix. var_is_in's size is _minimal_ so you should check whether var_is_in.getSize() < var before issuing var_is_in[var]
-    uint badlevel;
-
-    class matrixset
-    {
-    public:
-        PackedMatrix matrix; // The matrix, updated to reflect variable assignements
-        BitArray var_is_set;
-        vector<Var> col_to_var; // col_to_var[COL] tells which variable is at a given column in the matrix. Gives unassigned_var if the COL has been zeroed (i.e. the variable assigned)
-        uint16_t num_rows; // number of active rows in the matrix. Unactive rows are rows that contain only zeros (and if they are conflicting, then the conflict has been treated)
-        uint num_cols; // number of active columns in the matrix. The columns at the end that have all be zeroed are no longer active
-        int least_column_changed; // when updating the matrix, this value contains the smallest column number that has been updated  (Gauss elim. can start from here instead of from column 0)
-        vector<uint16_t> last_one_in_col; //last_one_in_col[COL] tells the last row+1 that has a '1' in that column. Used to reduce the burden of Gauss elim. (it only needs to look until that row)
-        vector<uint16_t> first_one_in_row;
-        uint removeable_cols; // the number of columns that have been zeroed out (i.e. assigned)
-    };
-
-    //Saved states
-    vector<matrixset> matrix_sets; // The matrixsets for depths 'decision_from' + 0,  'decision_from' + only_nth_gaussian_save, 'decision_from' + 2*only_nth_gaussian_save, ... 'decision_from' + 'decision_until'.
-    matrixset cur_matrixset; // The current matrixset, i.e. the one we are working on, or the last one we worked on
-
-    //Varibales to keep Gauss state
-    bool messed_matrix_vars_since_reversal;
-    int gauss_last_level;
-    vector<pair<Clause*, uint> > clauses_toclear;
-    bool disabled; // Gauss is disabled
-    
-    //State of current elimnation
-    vec<uint> propagatable_rows; //used to store which rows were deemed propagatable during elimination
-    vector<unsigned char> changed_rows; //used to store which rows were deemed propagatable during elimination
-
-    //Statistics
-    uint useful_prop; //how many times Gauss gave propagation as a result
-    uint useful_confl; //how many times Gauss gave conflict as a result
-    uint called; //how many times called the Gauss
-
-    //gauss init functions
-    void init(); // Initalise gauss state
-    void fill_matrix(matrixset& origMat); // Fills the origMat matrix
-    uint select_columnorder(vector<uint16_t>& var_to_col, matrixset& origMat); // Fills var_to_col and col_to_var of the origMat matrix.
-
-    //Main function
-    uint eliminate(matrixset& matrix, uint& conflict_row); //does the actual gaussian elimination
-
-    //matrix update functions
-    void update_matrix_col(matrixset& matrix, const Var x, const uint col); // Update one matrix column
-    void update_matrix_by_col_all(matrixset& m); // Update all columns, column-by-column (and not row-by-row)
-    void set_matrixset_to_cur(); // Save the current matrixset, the cur_matrixset to matrix_sets
-    //void update_matrix_by_row(matrixset& matrix) const;
-    //void update_matrix_by_col(matrixset& matrix, const uint last_level) const;
-
-    //conflict&propagation handling
-    gaussian_ret handle_matrix_prop_and_confl(matrixset& m, uint row, Clause*& confl);
-    void analyse_confl(const matrixset& m, const uint row, uint& maxlevel, uint& size, uint& best_row) const; // analyse conflcit to find the best conflict. Gets & returns the best one in 'maxlevel', 'size' and 'best row' (these are all UINT_MAX when calling this function first, i.e. when there is no other possible conflict to compare to the new in 'row')
-    gaussian_ret handle_matrix_confl(Clause*& confl, const matrixset& m, const uint size, const uint maxlevel, const uint best_row);
-    gaussian_ret handle_matrix_prop(matrixset& m, const uint row); // Handle matrix propagation at row 'row'
-    vec<Lit> tmp_clause;
-
-    //propagation&conflict handling
-    void cancel_until_sublevel(const uint sublevel); // cancels until sublevel 'sublevel'. The var 'sublevel' must NOT go over the current level. I.e. this function is ONLY for moving inside the current level
-    uint find_sublevel(const Var v) const; // find the sublevel (i.e. trail[X]) of a given variable
-
-    //helper functions
-    bool at_first_init() const;
-    bool should_init() const;
-    bool should_check_gauss(const uint decisionlevel, const uint starts) const;
-    void disable_if_necessary();
-    void reset_stats();
-    void update_last_one_in_col(matrixset& m);
-    
-private:
-    
-    //debug functions
-    bool check_no_conflict(matrixset& m) const; // Are there any conflicts that the matrixset 'm' causes?
-    const bool nothing_to_propagate(matrixset& m) const; // Are there any conflicts of propagations that matrixset 'm' clauses?
-    template<class T>
-    void print_matrix_row(const T& row) const; // Print matrix row 'row'
-    template<class T>
-    void print_matrix_row_with_assigns(const T& row) const;
-    void check_matrix_against_varset(PackedMatrix& matrix,const matrixset& m) const;
-    const bool check_last_one_in_cols(matrixset& m) const;
-    const void check_first_one_in_row(matrixset& m, const uint j);
-    void print_matrix(matrixset& m) const;
-    void print_last_one_in_cols(matrixset& m) const;
-    static const string lbool_to_string(const lbool toprint);
-};
-
-inline bool Gaussian::should_init() const
-{
-    return (config.decision_until > 0);
-}
-
-inline bool Gaussian::should_check_gauss(const uint decisionlevel, const uint starts) const
-{
-    return (!disabled
-            && decisionlevel < config.decision_until);
-}
-
-inline void Gaussian::canceling(const uint sublevel)
-{
-    if (disabled)
-        return;
-    uint a = 0;
-    for (int i = clauses_toclear.size()-1; i >= 0 && clauses_toclear[i].second > sublevel; i--) {
-        clauseFree(clauses_toclear[i].first);
-        a++;
-    }
-    clauses_toclear.resize(clauses_toclear.size()-a);
-    
-    if (messed_matrix_vars_since_reversal)
-        return;
-    int c = std::min((int)gauss_last_level, (int)(solver.trail.size())-1);
-    for (; c >= (int)sublevel; c--) {
-        Var var  = solver.trail[c].var();
-        if (var < var_is_in.getSize()
-            && var_is_in[var]
-            && cur_matrixset.var_is_set[var]) {
-        messed_matrix_vars_since_reversal = true;
-        return;
-        }
-    }
-}
-
-std::ostream& operator << (std::ostream& os, const vec<Lit>& v);
-
-}; //NAMESPACE MINISAT
-
-#endif //GAUSSIAN_H
index f98ec171726aa8f30096b9153615a8421a2c3ecd..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,52 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef GAUSSIANCONFIG_H
-#define GAUSSIANCONFIG_H
-
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-#include "PackedRow.h"
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class GaussianConfig
-{
-    public:
-    
-    GaussianConfig() :
-        only_nth_gauss_save(2)
-        , decision_until(0)
-        , dontDisable(false)
-    {
-    }
-        
-    //tuneable gauss parameters
-    uint only_nth_gauss_save;  //save only every n-th gauss matrix
-    uint decision_until; //do Gauss until this level
-    bool dontDisable; //If activated, gauss elimination is never disabled
-};
-
-}; //NAMESPACE MINISAT
-
-#endif //GAUSSIANCONFIG_H
index 94b0d0ace53a4e97c488945f6ffd3d8db102b6c2..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,893 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-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.
-**************************************************************************************************/
-
-#include <time.h>
-#include <cstring>
-#include <algorithm>
-#include <vector>
-#include <iostream>
-#include <iomanip>
-#include <fstream>
-#include <sstream>
-#include <limits>
-using std::cout;
-using std::endl;
-using std::ofstream;
-
-#include "Logger.h"
-#include "SolverTypes.h"
-#include "Solver.h"
-#include "Gaussian.h"
-
-#define FST_WIDTH 10
-#define SND_WIDTH 35
-#define TRD_WIDTH 10
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-Logger::Logger(int& _verbosity) :
-    proof_graph_on(false)
-    , mini_proof(false)
-    , statistics_on(false)
-
-    , max_print_lines(20)
-    , uniqueid(1)
-
-    , proof(NULL)
-
-    , sum_conflict_depths(0)
-    , no_conflicts(0)
-    , no_decisions(0)
-    , no_propagations(0)
-    , sum_decisions_on_branches(0)
-    , sum_propagations_on_branches(0)
-
-    , verbosity(_verbosity)
-    , begin_called(false)
-    , proofStarts(0)
-{
-    runid /= 10;
-    runid = time(NULL) % 10000;
-    if (verbosity >= 1) printf("c RunID is: #%d\n",runid);
-}
-
-void Logger::setSolver(const Solver* _s)
-{
-    S = _s;
-}
-
-// Adds a new variable to the knowledge of the logger
-void Logger::new_var(const Var var)
-{
-    if (!statistics_on && !proof_graph_on)
-        return;
-
-    if (varnames.size() <= var) {
-        varnames.resize(var+1, "Noname");
-        times_var_propagated.resize(var+1, 0);
-        times_var_guessed.resize(var+1, 0);
-        depths_of_assigns_for_var.resize(var+1);
-        depths_of_assigns_unit.resize(var+1, false);
-    }
-}
-
-// Resizes the groupnames and other, related vectors to accomodate for a new group
-void Logger::new_group(const uint group)
-{
-    if (groupnames.size() <= group) {
-        groupnames.resize(group+1, "Noname");
-        times_group_caused_conflict.resize(group+1, 0);
-        times_group_caused_propagation.resize(group+1, 0);
-        depths_of_propagations_for_group.resize(group+1);
-        depths_of_propagations_unit.resize(group+1, false);
-        depths_of_conflicts_for_group.resize(group+1);
-    }
-}
-
-void Logger::cut_name_to_size(string& name) const
-{
-    uint len = name.length();
-    while(len > 0 && (name[len-1] == ' ' || name[len-1] == 0x0A || name[len-1] == 0x0D)) {
-        name[len-1] = '\0';
-        name.resize(len-1);
-        len--;
-    }
-    
-    if (len > SND_WIDTH-2) {
-        name[SND_WIDTH-2] = '\0';
-        name[SND_WIDTH-3] = '.';
-        name[SND_WIDTH-4] = '.';
-    }
-}
-
-// Adds the new clause group's name to the information stored
-void Logger::set_group_name(const uint group, char* name_tmp)
-{
-    if (!statistics_on && !proof_graph_on)
-        return;
-    
-    string name;
-    if (name_tmp == NULL) return;
-    else name = name_tmp;
-    
-    new_group(group);
-    cut_name_to_size(name);
-    
-    if (name == "Noname") return;
-    
-    if (groupnames[group] == "Noname") {
-        groupnames[group] = name;
-    } else if (groupnames[group] != name) {
-        std::cout << "Error! Group no. " <<  group << "has been named twice. First, as '" << groupnames[group] << "', then second as '" <<  name << "'. Name the same group the same always, or don't give a name to the second iteration of the same group (i.e just write 'c g groupnumber' on the line" << std::endl;
-        exit(-1);
-    }
-}
-
-// sets the variable's name
-void Logger::set_variable_name(const uint var, char* name_tmp)
-{
-    if (!statistics_on && !proof_graph_on)
-        return;
-    
-    new_var(var);
-    
-    string name;
-    if (name_tmp == NULL)
-        name = "";
-    else
-        name = name_tmp;
-    
-    cut_name_to_size(name);
-    
-    if (varnames[var] == "Noname") {
-        varnames[var] = name;
-    } else if (varnames[var] != name) {
-        printf("Error! Variable no. %d has been named twice. First, as '%s', then second as '%s'. Name the same group the same always, or don't give a name to the second iteration of the same group (i.e just write 'c g groupnumber' on the line\n", var+1, varnames[var].c_str(), name.c_str());
-        exit(-1);
-    }
-}
-
-void Logger::first_begin()
-{
-    if (begin_called)
-        return;
-    
-    begin();
-}
-
-void Logger::begin()
-{
-    begin_called = true;
-    if (proof_graph_on) {
-        std::stringstream filename;
-        filename << "proofs/" << runid << "-proof" << proofStarts++ << "-" << S->starts << ".dot";
-        
-        if (S->starts == 0)
-            history.push_back(uniqueid);
-        else {
-            if (mini_proof)
-                history.resize(S->decisionLevel()+1);
-            else
-                history.resize(S->trail.size()+1);
-        }
-
-        proof = fopen(filename.str().c_str(),"w");
-        if (!proof) printf("Couldn't open proof file '%s' for writing\n", filename.str().c_str()), exit(-1);
-        fprintf(proof, "digraph G {\n");
-        fprintf(proof,"node%d [shape=circle, label=\"BEGIN\", root];\n", history[history.size()-1]);
-    }
-
-    if (statistics_on)
-        reset_statistics();
-}
-
-// For noting conflicts. Updates the proof graph and the statistics.
-template<class T>
-void Logger::conflict(const confl_type type, const uint goback_level, const uint group, const T& learnt_clause)
-{
-    first_begin();
-    assert(!(proof == NULL && proof_graph_on));
-    
-    const uint goback_sublevel = S->trail_lim[goback_level];
-
-    if (proof_graph_on) {
-        uniqueid++;
-        fprintf(proof,"node%d [shape=polygon,sides=5,label=\"",uniqueid);
-        
-        if (!mini_proof) {
-            for (uint32_t i = 0; i != learnt_clause.size(); i++) {
-                if (learnt_clause[i].sign()) fprintf(proof,"-");
-                int myvar = learnt_clause[i].var();
-                if (varnames[myvar] != "Noname")
-                    fprintf(proof,"%s\\n",varnames[myvar].c_str());
-                else
-                    fprintf(proof,"Var: %d\\n",myvar);
-            }
-        }
-        fprintf(proof,"\"];\n");
-
-        fprintf(proof,"node%d -> node%d [label=\"",history[history.size()-1],uniqueid);
-        if (type == gauss_confl_type)
-            fprintf(proof,"Gauss\",style=bold");
-        else
-            fprintf(proof,"%s\"", groupnames[group].c_str());
-        fprintf(proof,"];\n");
-        
-        if (!mini_proof)
-            history.resize(goback_sublevel+1);
-        else
-            history.resize(goback_level+1);
-        fprintf(proof,"node%d -> node%d [style=dotted];\n",uniqueid,history[history.size()-1]);
-    }
-
-    if (statistics_on) {
-        times_group_caused_conflict[group]++;
-        depths_of_conflicts_for_group[group].sum += S->decisionLevel();
-        depths_of_conflicts_for_group[group].num ++;
-        
-        no_conflicts++;
-        sum_conflict_depths += S->trail.size() - S->trail_lim[0];
-        sum_decisions_on_branches += S->decisionLevel();
-        sum_propagations_on_branches += S->trail.size() - S->trail_lim[0] - S->decisionLevel();
-        
-        if (branch_depth_distrib.size() <= S->decisionLevel())
-            branch_depth_distrib.resize(S->decisionLevel()+1, 0);
-        branch_depth_distrib[S->decisionLevel()]++;
-    }
-}
-
-template void Logger::conflict(const confl_type type, const uint goback_level, const uint group, const Clause& learnt_clause);
-
-template void Logger::conflict(const confl_type type, const uint goback_level, const uint group, const vec<Lit>& learnt_clause);
-
-// Propagating a literal. Type of literal and the (learned clause's)/(propagating clause's)/(etc) group must be given. Updates the proof graph and the statistics. note: the meaning of the variable 'group' depends on the type
-void Logger::propagation(const Lit lit, Clause* c)
-{
-    first_begin();
-    assert(!(proof == NULL && proof_graph_on));
-    
-    uint group;
-    prop_type type;
-    if (c == NULL) {
-        if (S->decisionLevel() == 0)
-            type = add_clause_type;
-        else
-            type = guess_type;
-        group = std::numeric_limits<uint>::max();
-    } else {
-        type = simple_propagation_type;
-        group = c->getGroup();
-    }
-
-    //graph
-    if (proof_graph_on && (!mini_proof || type == guess_type)) {
-        uniqueid++;
-        
-        fprintf(proof,"node%d [shape=box, label=\"",uniqueid);;
-        if (lit.sign())
-            fprintf(proof,"-");
-        if (varnames[lit.var()] != "Noname")
-            fprintf(proof,"%s\"];\n",varnames[lit.var()].c_str());
-        else
-            fprintf(proof,"Var: %d\"];\n",lit.var());
-
-        fprintf(proof,"node%d -> node%d [label=\"",history[history.size()-1],uniqueid);
-        
-        switch (type) {
-        case simple_propagation_type:
-            fprintf(proof,"%s\"];\n", groupnames[group].c_str());
-            break;
-            
-        case add_clause_type:
-            fprintf(proof,"red. from clause\"];\n");
-            break;
-            
-        case guess_type:
-            fprintf(proof,"guess\",style=bold];\n");
-            break;
-        }
-        history.push_back(uniqueid);
-    }
-
-    if (statistics_on) {
-        switch (type) {
-        case simple_propagation_type:
-            depths_of_propagations_for_group[group].sum += S->decisionLevel();
-            depths_of_propagations_for_group[group].num ++;
-            if (S->decisionLevel() == 0) depths_of_propagations_unit[group] = true;
-            times_group_caused_propagation[group]++;
-        case add_clause_type:
-            no_propagations++;
-            times_var_propagated[lit.var()]++;
-            depths_of_assigns_for_var[lit.var()].sum += S->decisionLevel();
-            depths_of_assigns_for_var[lit.var()].num ++;
-            if (S->decisionLevel() == 0) depths_of_assigns_unit[lit.var()] = true;
-            break;
-        case guess_type:
-            no_decisions++;
-            times_var_guessed[lit.var()]++;
-            
-            depths_of_assigns_for_var[lit.var()].sum += S->decisionLevel();
-            depths_of_assigns_for_var[lit.var()].num ++;
-            break;
-        }
-    }
-}
-
-// Ending of a restart iteration
-void Logger::end(const finish_type finish)
-{
-    first_begin();
-    assert(!(proof == NULL && proof_graph_on));
-    
-    if (proof_graph_on) {
-        uniqueid++;
-        switch (finish) {
-        case model_found:
-            fprintf(proof,"node%d [shape=doublecircle, label=\"MODEL\"];\n",uniqueid);
-            break;
-        case unsat_model_found:
-            fprintf(proof,"node%d [shape=doublecircle, label=\"UNSAT\"];\n",uniqueid);
-            break;
-        case restarting:
-            fprintf(proof,"node%d [shape=doublecircle, label=\"Re-starting\\nsearch\"];\n",uniqueid);
-            break;
-        }
-
-        fprintf(proof,"node%d -> node%d;\n",history[history.size()-1],uniqueid);
-        fprintf(proof,"}\n");
-        history.push_back(uniqueid);
-
-        proof = (FILE*)fclose(proof);
-        assert(proof == NULL);
-    }
-
-    if (statistics_on) {
-        printstats();
-        if (finish == restarting)
-            reset_statistics();
-    }
-    
-    if (model_found || unsat_model_found)
-        begin_called = false;
-}
-
-void Logger::print_footer() const
-{
-    cout << "+" << std::setfill('-') << std::setw(FST_WIDTH+SND_WIDTH+TRD_WIDTH+4) << "-" << std::setfill(' ') << "+" << endl;
-}
-
-void Logger::print_assign_var_order() const
-{
-    vector<pair<double, uint> > prop_ordered;
-    for (uint i = 0; i < depths_of_assigns_for_var.size(); i++) {
-        double avg = (double)depths_of_assigns_for_var[i].sum
-                    /(double)depths_of_assigns_for_var[i].num;
-        if (depths_of_assigns_for_var[i].num > 0 && !depths_of_assigns_unit[i])
-            prop_ordered.push_back(std::make_pair(avg, i));
-    }
-
-    if (!prop_ordered.empty()) {
-        print_footer();
-        print_simple_line(" Variables are assigned in the following order");
-        print_simple_line(" (unitary clauses not shown)");
-        print_header("var", "var name", "avg order");
-        std::sort(prop_ordered.begin(), prop_ordered.end());
-        print_vars(prop_ordered);
-    }
-}
-
-void Logger::print_prop_order() const
-{
-    vector<pair<double, uint> > prop_ordered;
-    for (uint i = 0; i < depths_of_propagations_for_group.size(); i++) {
-        double avg = (double)depths_of_propagations_for_group[i].sum
-                    /(double)depths_of_propagations_for_group[i].num;
-        if (depths_of_propagations_for_group[i].num > 0 && !depths_of_propagations_unit[i])
-            prop_ordered.push_back(std::make_pair(avg, i));
-    }
-
-    if (!prop_ordered.empty()) {
-        print_footer();
-        print_simple_line(" Propagation depth order of clause groups");
-        print_simple_line(" (unitary clauses not shown)");
-        print_header("group", "group name", "avg order");
-        std::sort(prop_ordered.begin(), prop_ordered.end());
-        print_groups(prop_ordered);
-    }
-}
-
-void Logger::print_confl_order() const
-{
-    vector<pair<double, uint> > confl_ordered;
-    for (uint i = 0; i < depths_of_conflicts_for_group.size(); i++) {
-        double avg = (double)depths_of_conflicts_for_group[i].sum
-                    /(double)depths_of_conflicts_for_group[i].num;
-        if (depths_of_conflicts_for_group[i].num > 0)
-            confl_ordered.push_back(std::make_pair(avg, i));
-    }
-
-    if (!confl_ordered.empty()) {
-        print_footer();
-        print_simple_line(" Avg. conflict depth order of clause groups");
-        print_header("groupno", "group name", "avg. depth");
-        std::sort(confl_ordered.begin(), confl_ordered.end());
-        print_groups(confl_ordered);
-    }
-}
-
-
-void Logger::print_times_var_guessed() const
-{
-    vector<pair<uint, uint> > times_var_ordered;
-    for (uint32_t i = 0; i != varnames.size(); i++) if (times_var_guessed[i] > 0)
-            times_var_ordered.push_back(std::make_pair(times_var_guessed[i], i));
-
-    if (!times_var_ordered.empty()) {
-        print_footer();
-        print_simple_line(" No. times variable branched on");
-        print_header("var", "var name", "no. times");
-        std::sort(times_var_ordered.rbegin(), times_var_ordered.rend());
-        print_vars(times_var_ordered);
-    }
-}
-
-void Logger::print_times_group_caused_propagation() const
-{
-    vector<pair<uint, uint> > props_group_ordered;
-    for (uint i = 0; i < times_group_caused_propagation.size(); i++)
-        if (times_group_caused_propagation[i] > 0)
-            props_group_ordered.push_back(std::make_pair(times_group_caused_propagation[i], i));
-
-    if (!props_group_ordered.empty()) {
-        print_footer();
-        print_simple_line(" No. propagations made by clause groups");
-        print_header("group", "group name", "no. props");
-        std::sort(props_group_ordered.rbegin(),props_group_ordered.rend());
-        print_groups(props_group_ordered);
-    }
-}
-
-void Logger::print_times_group_caused_conflict() const
-{
-    vector<pair<uint, uint> > confls_group_ordered;
-    for (uint i = 0; i < times_group_caused_conflict.size(); i++)
-        if (times_group_caused_conflict[i] > 0)
-            confls_group_ordered.push_back(std::make_pair(times_group_caused_conflict[i], i));
-
-    if (!confls_group_ordered.empty()) {
-        print_footer();
-        print_simple_line(" No. conflicts made by clause groups");
-        print_header("group", "group name", "no. confl");
-        std::sort(confls_group_ordered.rbegin(), confls_group_ordered.rend());
-        print_groups(confls_group_ordered);
-    }
-}
-
-template<class T>
-void Logger::print_line(const uint& number, const string& name, const T& value) const
-{
-    cout << "|" << std::setw(FST_WIDTH) << number << "  " << std::setw(SND_WIDTH) << name << "  " << std::setw(TRD_WIDTH) << value << "|" << endl;
-}
-
-void Logger::print_header(const string& first, const string& second, const string& third) const
-{
-    cout << "|" << std::setw(FST_WIDTH) << first << "  " << std::setw(SND_WIDTH) << second << "  " << std::setw(TRD_WIDTH) << third << "|" << endl;
-    print_footer();
-}
-
-void Logger::print_groups(const vector<pair<double, uint> >& to_print) const
-{
-    uint i = 0;
-    typedef vector<pair<double, uint> >::const_iterator myiterator;
-    for (myiterator it = to_print.begin(); it != to_print.end() && i < max_print_lines; it++, i++) {
-        print_line(it->second+1, groupnames[it->second], it->first);
-    }
-    print_footer();
-}
-
-void Logger::print_groups(const vector<pair<uint, uint> >& to_print) const
-{
-    uint i = 0;
-    typedef vector<pair<uint, uint> >::const_iterator myiterator;
-    for (myiterator it = to_print.begin(); it != to_print.end() && i < max_print_lines; it++, i++) {
-        print_line(it->second+1, groupnames[it->second], it->first);
-    }
-    print_footer();
-}
-
-void Logger::print_vars(const vector<pair<double, uint> >& to_print) const
-{
-    uint i = 0;
-    for (vector<pair<double, uint> >::const_iterator it = to_print.begin(); it != to_print.end() && i < max_print_lines; it++, i++)
-        print_line(it->second+1, varnames[it->second], it->first);
-    
-    print_footer();
-}
-
-void Logger::print_vars(const vector<pair<uint, uint> >& to_print) const
-{
-    uint i = 0;
-    for (vector<pair<uint, uint> >::const_iterator it = to_print.begin(); it != to_print.end() && i < max_print_lines; it++, i++) {
-        print_line(it->second+1, varnames[it->second], it->first);
-    }
-    
-    print_footer();
-}
-
-template<class T>
-void Logger::print_line(const string& str, const T& num) const
-{
-    cout << "|" << std::setw(FST_WIDTH+SND_WIDTH+4) << str << std::setw(TRD_WIDTH) << num << "|" << endl;
-}
-
-void Logger::print_simple_line(const string& str) const
-{
-    cout << "|" << std::setw(FST_WIDTH+SND_WIDTH+TRD_WIDTH+4) << str << "|" << endl;
-}
-
-void Logger::print_center_line(const string& str) const
-{
-    uint middle = (FST_WIDTH+SND_WIDTH+TRD_WIDTH+4-str.size())/2;
-    int rest = FST_WIDTH+SND_WIDTH+TRD_WIDTH+4-middle*2-str.size();
-    cout << "|" << std::setw(middle) << " " << str << std::setw(middle + rest) << " " << "|" << endl;
-}
-
-void Logger::print_branch_depth_distrib() const
-{
-    //cout << "--- Branch depth stats ---" << endl;
-
-    const uint range = 20;
-    map<uint, uint> range_stat;
-
-    uint i = 0;
-    for (vector<uint>::const_iterator it = branch_depth_distrib.begin(); it != branch_depth_distrib.end(); it++, i++) {
-        range_stat[i/range] += *it;
-    }
-
-    print_footer();
-    print_simple_line(" No. search branches with branch depth between");
-    print_line("Branch depth between", "no. br.-s");
-    print_footer();
-
-    std::stringstream ss;
-    ss << "branch_depths/branch_depth_file" << runid << "-" << S->starts << ".txt";
-    ofstream branch_depth_file;
-    branch_depth_file.open(ss.str().c_str());
-    i = 0;
-    
-    for (map<uint, uint>::iterator it = range_stat.begin(); it != range_stat.end(); it++, i++) {
-        std::stringstream ss2;
-        ss2 << it->first*range << " - " << it->first*range + range-1;
-        print_line(ss2.str(), it->second);
-
-        if (branch_depth_file.is_open()) {
-                branch_depth_file << i << "\t" << it->second << "\t";
-            if (i %  5 == 0)
-                branch_depth_file  << "\"" << it->first*range << "\"";
-            else
-                branch_depth_file << "\"\"";
-            branch_depth_file << endl;
-        }
-    }
-    if (branch_depth_file.is_open())
-        branch_depth_file.close();
-    print_footer();
-
-}
-
-void Logger::print_learnt_clause_distrib() const
-{
-    map<uint, uint> learnt_sizes;
-    const vec<Clause*>& learnts = S->get_learnts();
-    
-    uint maximum = 0;
-    
-    for (uint i = 0; i < learnts.size(); i++)
-    {
-        uint size = learnts[i]->size();
-        maximum = std::max(maximum, size);
-        
-        map<uint, uint>::iterator it = learnt_sizes.find(size);
-        if (it == learnt_sizes.end())
-            learnt_sizes[size] = 1;
-        else
-            it->second++;
-    }
-    
-    learnt_sizes[0] = S->get_unitary_learnts_num();
-    
-    uint slice = (maximum+1)/max_print_lines + (bool)((maximum+1)%max_print_lines);
-    
-    print_footer();
-    print_simple_line(" Learnt clause length distribution");
-    print_line("Length between", "no. cl.");
-    print_footer();
-    
-    uint until = slice;
-    uint from = 0;
-    while(until < maximum+1) {
-        std::stringstream ss2;
-        ss2 << from << " - " << until-1;
-        
-        uint sum = 0;
-        for (; from < until; from++) {
-            map<uint, uint>::const_iterator it = learnt_sizes.find(from);
-            if (it != learnt_sizes.end())
-                sum += it->second;
-        }
-        
-        print_line(ss2.str(), sum);
-        
-        until += slice;
-    }
-    
-    print_footer();
-    
-    print_leearnt_clause_graph_distrib(maximum, learnt_sizes);
-}
-
-void Logger::print_leearnt_clause_graph_distrib(const uint maximum, const map<uint, uint>& learnt_sizes) const
-{
-    uint no_slices = FST_WIDTH  + SND_WIDTH + TRD_WIDTH + 4-3;
-    uint slice = (maximum+1)/no_slices + (bool)((maximum+1)%no_slices);
-    uint until = slice;
-    uint from = 0;
-    vector<uint> slices;
-    uint hmax = 0;
-    while(until < maximum+1) {
-        uint sum = 0;
-        for (; from < until; from++) {
-            map<uint, uint>::const_iterator it = learnt_sizes.find(from);
-            if (it != learnt_sizes.end())
-                sum += it->second;
-        }
-        slices.push_back(sum);
-        until += slice;
-        hmax = std::max(hmax, sum);
-    }
-    slices.resize(no_slices, 0);
-    
-    uint height = max_print_lines;
-    uint hslice = (hmax+1)/height + (bool)((hmax+1)%height);
-    if (hslice == 0) return;
-    
-    print_simple_line(" Learnt clause distribution in graph form");
-    print_footer();
-    string yaxis = "Number";
-    uint middle = (height-yaxis.size())/2;
-    
-    for (int i = height-1; i > 0; i--) {
-        cout << "| ";
-        if (height-1-i >= middle && height-1-i-middle < yaxis.size())
-            cout << yaxis[height-1-i-middle] << " ";
-        else
-            cout << "  ";
-        for (uint i2 = 0; i2 != no_slices; i2++) {
-            if (slices[i2]/hslice >= (uint)i) cout << "+";
-            else cout << " ";
-        }
-        cout << "|" << endl;
-    }
-    print_center_line(" Learnt clause size");
-    print_footer();
-}
-
-void Logger::print_general_stats() const
-{
-    print_footer();
-    print_simple_line(" Standard MiniSat stats -- for all restarts until now");
-    print_footer();
-    print_line("Restart number", S->starts);
-    print_line("Number of conflicts", S->conflicts);
-    print_line("Number of decisions", S->decisions);
-    print_line("Number of variables", S->order_heap.size());
-    print_line("Number of clauses", S->nClauses());
-    print_line("Number of literals in clauses",S->clauses_literals);
-    print_line("Avg. literals per learnt clause",(double)S->learnts_literals/(double)S->nLearnts());
-    print_line("Progress estimate (%):", S->progress_estimate*100.0);
-    print_line("All unitary learnts until now", S->get_unitary_learnts_num());
-    print_footer();
-}
-
-void Logger::print_learnt_unitaries(const uint from, const string display) const
-{
-    print_footer();
-    print_simple_line(display);
-    print_header("var", "name", "value");
-    uint32_t until;
-    if (S->decisionLevel() > 0)
-        until = S->trail_lim[0];
-    else
-        until = S->trail.size();
-    for (uint i = from; i < until; i++) {
-        Var var = S->trail[i].var();
-        bool value = !(S->trail[i].sign());
-        print_line(var+1, varnames[var], value);
-    }
-    print_footer();
-}
-
-
-// Prints statistics on the console
-void Logger::printstats() const
-{
-    assert(statistics_on);
-    assert(varnames.size() == times_var_guessed.size());
-    assert(varnames.size() == times_var_propagated.size());
-
-    const uint fullwidth = FST_WIDTH+SND_WIDTH+TRD_WIDTH+4;
-    cout << endl;
-    cout << "+" << std::setfill('=') << std::setw(fullwidth) << "=" << "+" << endl;
-    std::stringstream tmp;
-    tmp << " STATS FOR RESTART NO. " << std::setw(3) << S->starts << "  BEGIN ";
-    uint len = (fullwidth-2)/2-tmp.str().length()/2;
-    uint len2 = len + tmp.str().length()%2 + (fullwidth-2)%2;
-    cout << "||" << std::setfill('*') << std::setw(len) << "*" << tmp.str() << std::setw(len2) << "*" << "||" << endl;
-    cout << "+" << std::setfill('=') << std::setw(fullwidth) << "=" << std::setfill(' ') << "+" << endl;
-    
-    cout.setf(std::ios_base::left);
-    cout.precision(2);
-    print_statistics_note();
-    print_times_var_guessed();
-    print_times_group_caused_propagation();
-    print_times_group_caused_conflict();
-    print_prop_order();
-    print_confl_order();
-    print_assign_var_order();
-    print_branch_depth_distrib();
-    print_learnt_clause_distrib();
-    #ifdef USE_GAUSS
-    print_matrix_stats();
-    #endif //USE_GAUSS
-    print_learnt_unitaries(0," Unitary clauses learnt until now");
-    print_learnt_unitaries(last_unitary_learnt_clauses, " Unitary clauses during this restart");
-    print_advanced_stats();
-    print_general_stats();
-}
-
-#ifdef USE_GAUSS
-void Logger::print_matrix_stats() const
-{
-    print_footer();
-    print_simple_line(" Matrix statistics");
-    print_footer();
-    
-    uint i = 0;
-    for (vector<Gaussian*>::const_iterator it = S->gauss_matrixes.begin(), end = S->gauss_matrixes.end(); it != end; it++, i++) {
-        std::stringstream s;
-        s << "Matrix " << i << " enabled";
-        std::stringstream tmp;
-        tmp << std::boolalpha << !(*it)->get_disabled();
-        print_line(s.str(), tmp.str());
-        
-        s.str("");
-        s << "Matrix " << i << " called";
-        print_line(s.str(), (*it)->get_called());
-        
-        s.str("");
-        s << "Matrix " << i << " propagations";
-        print_line(s.str(), (*it)->get_useful_prop());
-        
-        s.str("");
-        s << "Matrix " << i << " conflicts";
-        print_line(s.str(), (*it)->get_useful_confl());
-    }
-    
-    print_footer();
-}
-#endif //USE_GAUSS
-
-void Logger::print_advanced_stats() const
-{
-    print_footer();
-    print_simple_line(" Advanced statistics - for only this restart");
-    print_footer();
-    print_line("Unitary learnts", S->get_unitary_learnts_num() - last_unitary_learnt_clauses);
-    print_line("No. branches visited", no_conflicts);
-    print_line("Avg. branch depth", (double)sum_conflict_depths/(double)no_conflicts);
-    print_line("No. decisions", no_decisions);
-    print_line("No. propagations",no_propagations);
-    
-    //printf("no progatations/no decisions (i.e. one decision gives how many propagations on average *for the whole search graph*): %f\n", (double)no_propagations/(double)no_decisions);
-    //printf("no propagations/sum decisions on branches (if you look at one specific branch, what is the average number of propagations you will find?): %f\n", (double)no_propagations/(double)sum_decisions_on_branches);
-    
-    print_simple_line("sum decisions on branches/no. branches");
-    print_simple_line(" (in a given branch, what is the avg.");
-    print_line("  no. of decisions?)",(double)sum_decisions_on_branches/(double)no_conflicts);
-    
-    print_simple_line("sum propagations on branches/no. branches");
-    print_simple_line(" (in a given branch, what is the");
-    print_line("  avg. no. of propagations?)",(double)sum_propagations_on_branches/(double)no_conflicts);
-    
-    print_footer();
-}
-
-void Logger::print_statistics_note() const
-{
-    print_footer();
-    print_simple_line("Statistics note: If you used CryptoMiniSat as");
-    print_simple_line("a library then vars are all shifted by 1 here");
-    print_simple_line("and in every printed output of the solver.");
-    print_simple_line("This does not apply when you use CryptoMiniSat");
-    print_simple_line("as a stand-alone program.");
-    print_footer();
-}
-
-// resets all stored statistics. Might be useful, to generate statistics for each restart and not for the whole search in general
-void Logger::reset_statistics()
-{
-    assert(S->decisionLevel() == 0);
-    assert(times_var_guessed.size() == times_var_propagated.size());
-    assert(times_group_caused_conflict.size() == times_group_caused_propagation.size());
-    
-    typedef vector<uint>::iterator vecit;
-    for (vecit it = times_var_guessed.begin(); it != times_var_guessed.end(); it++)
-        *it = 0;
-
-    for (vecit it = times_var_propagated.begin(); it != times_var_propagated.end(); it++)
-        *it = 0;
-
-    for (vecit it = times_group_caused_conflict.begin(); it != times_group_caused_conflict.end(); it++)
-        *it = 0;
-
-    for (vecit it = times_group_caused_propagation.begin(); it != times_group_caused_propagation.end(); it++)
-        *it = 0;
-
-    for (vecit it = confls_by_group.begin(); it != confls_by_group.end(); it++)
-        *it = 0;
-
-    for (vecit it = props_by_group.begin(); it != props_by_group.end(); it++)
-        *it = 0;
-
-    typedef vector<MyAvg>::iterator avgIt;
-
-    for (avgIt it = depths_of_propagations_for_group.begin(); it != depths_of_propagations_for_group.end(); it++) {
-        it->sum = 0;
-        it->num = 0;
-    }
-
-    for (avgIt it = depths_of_conflicts_for_group.begin(); it != depths_of_conflicts_for_group.end(); it++) {
-        it->sum = 0;
-        it->num = 0;
-    }
-
-    for (avgIt it = depths_of_assigns_for_var.begin(); it != depths_of_assigns_for_var.end(); it++) {
-        it->sum = 0;
-        it->num = 0;
-    }
-    for (uint i = 0; i < depths_of_assigns_unit.size(); i++)
-        depths_of_assigns_unit[i] = false;
-    
-    for (uint i = 0; i < depths_of_propagations_unit.size(); i++)
-        depths_of_propagations_unit[i] = false;
-
-    sum_conflict_depths = 0;
-    no_conflicts = 0;
-    no_decisions = 0;
-    no_propagations = 0;
-    sum_decisions_on_branches = 0;
-    sum_propagations_on_branches = 0;
-    branch_depth_distrib.clear();
-    last_unitary_learnt_clauses = S->get_unitary_learnts_num();
-}
-
-}; //NAMESPACE MINISAT
index a00c785576a07d3f4a959f7e85511b7e66b4ca5c..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,187 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-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 LOGGER_H
-#define LOGGER_H
-
-#include <stdio.h>
-#include <set>
-#include <vector>
-#include <string>
-#include <map>
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-#include "Vec.h"
-#include "Heap.h"
-#include "Alg.h"
-#include "SolverTypes.h"
-#include "limits.h"
-#include "Clause.h"
-
-using std::vector;
-using std::pair;
-using std::string;
-using std::map;
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class Solver;
-
-class MyAvg {
-public:
-    MyAvg() :
-        sum(0)
-        , num(0)
-        {}
-    
-    uint sum;
-    uint num;
-};
-
-class Logger
-{
-public:
-    Logger(int& vebosity);
-    void setSolver(const Solver* S);
-
-    //types of props, confl, and finish
-    enum prop_type { add_clause_type, guess_type, simple_propagation_type};
-    enum confl_type { simple_confl_type, gauss_confl_type };
-    enum finish_type { model_found, unsat_model_found, restarting};
-
-    //Conflict and propagation(guess is also a proapgation...)
-    template<class T>
-    void conflict(const confl_type type, const uint goback_level, const uint group, const T& learnt_clause);
-    void propagation(const Lit lit, Clause* c);
-
-    //functions to add/name variables
-    void new_var(const Var var);
-    void set_variable_name(const uint var, char* name_tmp);
-
-    //function to name clause groups
-    void set_group_name(const uint group, char* name_tmp);
-
-    void begin();
-    void end(const finish_type finish);
-
-    void newclause(const vec<Lit>& ps, const bool xor_clause, const uint group);
-
-    bool proof_graph_on;
-    bool mini_proof;
-    bool statistics_on;
-    
-private:
-    void new_group(const uint group);
-    void cut_name_to_size(string& name) const;
-    
-    void print_groups(const vector<pair<uint, uint> >& to_print) const;
-    void print_groups(const vector<pair<double, uint> >& to_print) const;
-    void print_vars(const vector<pair<uint, uint> >& to_print) const;
-    void print_vars(const vector<pair<double, uint> >& to_print) const;
-    void print_times_var_guessed() const;
-    void print_times_group_caused_propagation() const;
-    void print_times_group_caused_conflict() const;
-    void print_branch_depth_distrib() const;
-    void print_learnt_clause_distrib() const;
-    void print_leearnt_clause_graph_distrib(const uint maximum, const map<uint, uint>& learnt_sizes) const;
-    void print_advanced_stats() const;
-    void print_statistics_note() const;
-    void print_matrix_stats() const;
-    void print_general_stats() const;
-    void print_learnt_unitaries(const uint from, const string display) const;
-
-    uint max_print_lines;
-    template<class T>
-    void print_line(const uint& number, const string& name, const T& value) const;
-    void print_header(const string& first, const string& second, const string& third) const;
-    void print_footer() const;
-    template<class T>
-    void print_line(const string& str, const T& num) const;
-    void print_simple_line(const string& str) const;
-    void print_center_line(const string& str) const;
-    
-    void print_confl_order() const;
-    void print_prop_order() const;
-    void print_assign_var_order() const;
-    void printstats() const;
-    void reset_statistics();
-
-    //internal data structures
-    uint uniqueid; //used to store the last unique ID given to a node
-    vector<uint> history; //stores the node uniqueIDs
-
-    //graph drawing
-    FILE* proof; //The file to store the proof
-    uint runid;
-
-    //---------------------
-    //statistics collection
-    //---------------------
-
-    //group and var names
-    vector<string> groupnames;
-    vector<string> varnames;
-
-    //confls and props grouped by clause groups
-    vector<uint> confls_by_group;
-    vector<uint> props_by_group;
-
-    //props and guesses grouped by vars
-    vector<uint> times_var_guessed;
-    vector<uint> times_var_propagated;
-
-    vector<uint> times_group_caused_conflict;
-    vector<uint> times_group_caused_propagation;
-
-    vector<MyAvg> depths_of_propagations_for_group;
-    vector<bool>  depths_of_propagations_unit;
-    vector<MyAvg> depths_of_conflicts_for_group;
-    vector<MyAvg> depths_of_assigns_for_var;
-    vector<bool>  depths_of_assigns_unit;
-
-    //the distribution of branch depths. first = depth, second = number of occurances
-    vector<uint> branch_depth_distrib;
-
-    uint sum_conflict_depths;
-    uint no_conflicts;
-    uint no_decisions;
-    uint no_propagations;
-    uint sum_decisions_on_branches;
-    uint sum_propagations_on_branches;
-    uint last_unitary_learnt_clauses;
-
-    //message display properties
-    const int& verbosity;
-    
-    const Solver* S;
-    
-    void first_begin();
-    bool begin_called;
-    uint proofStarts;
-};
-
-}; //NAMESPACE MINISAT
-
-#endif //LOGGER_H
index a38b19eec12550df3a511188ed7f27f8f4f207e3..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,27 +0,0 @@
-TOP = ../../..
-include $(TOP)/scripts/Makefile.common
-
-MTL       = mtl
-MTRAND    = MTRand
-SOURCES   = Logger.cpp Solver.cpp PackedRow.cpp XorFinder.cpp Conglomerate.cpp VarReplacer.cpp FindUndef.cpp ClauseCleaner.cpp RestartTypeChooser.cpp Clause.cpp FailedVarSearcher.cpp PartFinder.cpp Subsumer.cpp PartHandler.cpp XorSubsumer.cpp SmallPtr.cpp
-OBJECTS   = $(SOURCES:.cpp=.o)
-LIB       = libminisat.a
-CFLAGS    += -I$(MTL) -I$(MTRAND) -DEXT_HASH_MAP -ffloat-store $(CFLAGS_M32) -c
-EXEC      = minisat
-LFLAGS    = -lz
-
-all: $(LIB) #$(EXEC)
-lib: $(LIB)
-
-$(LIB): $(OBJECTS)
-       rm -f $@
-       ar cq $@ $(OBJECTS)
-       ranlib $@
-       cp $(LIB) ../
-       cp $(OBJECTS) ../
-
-clean:
-       rm -f $(OBJECTS) $(LIB)
-
-.cpp.o:
-       $(CC) $(CFLAGS) $< -o $@
index 1f08a2c9a4bf1ef9a749f0062fe8d09d685e0291..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,224 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#include "MatrixFinder.h"
-
-#include "Solver.h"
-#include "Gaussian.h"
-#include "GaussianConfig.h"
-#include "ClauseCleaner.h"
-
-#include <set>
-#include <map>
-#include <iomanip>
-#include <math.h>
-using std::set;
-using std::map;
-
-//#define VERBOSE_DEBUG
-
-using std::cout;
-using std::endl;
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-//#define PART_FINDING
-
-MatrixFinder::MatrixFinder(Solver& _solver) :
-    solver(_solver)
-{
-}
-
-inline const Var MatrixFinder::fingerprint(const XorClause& c) const
-{
-    Var fingerprint = 0;
-    
-    for (const Lit* a = &c[0], *end = a + c.size(); a != end; a++)
-        fingerprint |= a->var();
-    
-    return fingerprint;
-}
-
-inline const bool MatrixFinder::firstPartOfSecond(const XorClause& c1, const XorClause& c2) const
-{
-    uint i1, i2;
-    for (i1 = 0, i2 = 0; i1 < c1.size() && i2 < c2.size();) {
-        if (c1[i1].var() != c2[i2].var())
-            i2++;
-        else {
-            i1++;
-            i2++;
-        }
-    }
-    
-    return (i1 == c1.size());
-}
-
-const uint MatrixFinder::findMatrixes()
-{
-    table.clear();
-    table.resize(solver.nVars(), var_Undef);
-    reverseTable.clear();
-    matrix_no = 0;
-    
-    if (solver.xorclauses.size() == 0)
-        return 0;
-    
-    solver.clauseCleaner->cleanClauses(solver.xorclauses, ClauseCleaner::xorclauses);
-    //TODO check for solver.ok == false
-    
-    for (XorClause** c = solver.xorclauses.getData(), **end = c + solver.xorclauses.size(); c != end; c++) {
-        set<uint> tomerge;
-        vector<Var> newSet;
-        for (Lit *l = &(**c)[0], *end2 = l + (**c).size(); l != end2; l++) {
-            if (table[l->var()] != var_Undef)
-                tomerge.insert(table[l->var()]);
-            else
-                newSet.push_back(l->var());
-        }
-        if (tomerge.size() == 1) {
-            const uint into = *tomerge.begin();
-            map<uint, vector<Var> >::iterator intoReverse = reverseTable.find(into);
-            for (uint i = 0; i < newSet.size(); i++) {
-                intoReverse->second.push_back(newSet[i]);
-                table[newSet[i]] = into;
-            }
-            continue;
-        }
-        
-        for (set<uint>::iterator it = tomerge.begin(); it != tomerge.end(); it++) {
-            newSet.insert(newSet.end(), reverseTable[*it].begin(), reverseTable[*it].end());
-            reverseTable.erase(*it);
-        }
-        for (uint i = 0; i < newSet.size(); i++)
-            table[newSet[i]] = matrix_no;
-        reverseTable[matrix_no] = newSet;
-        matrix_no++;
-    }
-    
-    #ifdef VERBOSE_DEBUG
-    for (map<uint, vector<Var> >::iterator it = reverseTable.begin(), end = reverseTable.end(); it != end; it++) {
-        cout << "-- set begin --" << endl;
-        for (vector<Var>::iterator it2 = it->second.begin(), end2 = it->second.end(); it2 != end2; it2++) {
-            cout << *it2 << ", ";
-        }
-        cout << "-------" << endl;
-    }
-    #endif
-    
-    return setMatrixes();
-}
-
-const uint MatrixFinder::setMatrixes()
-{
-    vector<pair<uint, uint> > numXorInMatrix;
-    for (uint i = 0; i < matrix_no; i++)
-        numXorInMatrix.push_back(std::make_pair(i, 0));
-    
-    vector<uint> sumXorSizeInMatrix(matrix_no, 0);
-    vector<vector<uint> > xorSizesInMatrix(matrix_no);
-    vector<vector<XorClause*> > xorsInMatrix(matrix_no);
-    
-    #ifdef PART_FINDING
-    vector<vector<Var> > xorFingerprintInMatrix(matrix_no);
-    #endif
-    
-    for (XorClause** c = solver.xorclauses.getData(), **end = c + solver.xorclauses.size(); c != end; c++) {
-        XorClause& x = **c;
-        const uint matrix = table[x[0].var()];
-        assert(matrix < matrix_no);
-        
-        //for stats
-        numXorInMatrix[matrix].second++;
-        sumXorSizeInMatrix[matrix] += x.size();
-        xorSizesInMatrix[matrix].push_back(x.size());
-        xorsInMatrix[matrix].push_back(&x);
-        
-        #ifdef PART_FINDING
-        xorFingerprintInMatrix[matrix].push_back(fingerprint(x));
-        #endif //PART_FINDING
-    }
-    
-    std::sort(numXorInMatrix.begin(), numXorInMatrix.end(), mysorter());
-    
-    #ifdef PART_FINDING
-    for (uint i = 0; i < matrix_no; i++)
-        findParts(xorFingerprintInMatrix[i], xorsInMatrix[i]);
-    #endif //PART_FINDING
-    
-    uint realMatrixNum = 0;
-    for (int a = matrix_no-1; a != -1; a--) {
-        uint i = numXorInMatrix[a].first;
-        
-        if (numXorInMatrix[a].second < 3)
-            continue;
-        
-        const uint totalSize = reverseTable[i].size()*numXorInMatrix[a].second;
-        const double density = (double)sumXorSizeInMatrix[i]/(double)totalSize*100.0;
-        double avg = (double)sumXorSizeInMatrix[i]/(double)numXorInMatrix[a].second;
-        double variance = 0.0;
-        for (uint i2 = 0; i2 < xorSizesInMatrix[i].size(); i2++)
-            variance += pow((double)xorSizesInMatrix[i][i2]-avg, 2);
-        variance /= (double)xorSizesInMatrix.size();
-        const double stdDeviation = sqrt(variance);
-        
-        if (numXorInMatrix[a].second >= 20
-            && numXorInMatrix[a].second <= 1000
-            && realMatrixNum < 3)
-        {
-            if (solver.verbosity >=1)
-                cout << "c |  Matrix no " << std::setw(4) << realMatrixNum;
-            solver.gauss_matrixes.push_back(new Gaussian(solver, solver.gaussconfig, realMatrixNum, xorsInMatrix[i]));
-            realMatrixNum++;
-            
-        } else {
-            if (solver.verbosity >=1  /*&& numXorInMatrix[a].second >= 20*/)
-                cout << "c |  Unused Matrix ";
-        }
-        if (solver.verbosity >=1 /*&& numXorInMatrix[a].second >= 20*/) {
-            cout << std::setw(5) << numXorInMatrix[a].second << " x" << std::setw(5) << reverseTable[i].size();
-            cout << "  density:" << std::setw(5) << std::fixed << std::setprecision(1) << density << "%";
-            cout << "  xorlen avg:" << std::setw(5) << std::fixed << std::setprecision(2)  << avg;
-            cout << " stdev:" << std::setw(6) << std::fixed << std::setprecision(2) << stdDeviation << "  |" << endl;
-        }
-    }
-    
-    return realMatrixNum;
-}
-
-void MatrixFinder::findParts(vector<Var>& xorFingerprintInMatrix, vector<XorClause*>& xorsInMatrix)
-{
-    uint ai = 0;
-    for (XorClause **a = &xorsInMatrix[0], **end = a + xorsInMatrix.size(); a != end; a++, ai++) {
-        const Var fingerprint = xorFingerprintInMatrix[ai];
-        uint ai2 = 0;
-        for (XorClause **a2 = &xorsInMatrix[0]; a2 != end; a2++, ai2++) {
-            if (ai == ai2) continue;
-            const Var fingerprint2 = xorFingerprintInMatrix[ai2];
-            if (((fingerprint & fingerprint2) == fingerprint) && firstPartOfSecond(**a, **a2)) {
-                cout << "First part of second:" << endl;
-                (*a)->plainPrint();
-                (*a2)->plainPrint();
-                cout << "END" << endl;
-            }
-        }
-    }
-}
-
-}; //NAMESPACE MINISAT
index 7be3506acbcbae3f37e496c4216d5bdbb7f3a4aa..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,72 +0,0 @@
-/***********************************************************************************
-CryptoMiniSat -- Copyright (c) 2009 Mate Soos
-
-This program is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program.  If not, see <http://www.gnu.org/licenses/>.
-**************************************************************************************************/
-
-#ifndef MATRIXFINDER_H
-#define MATRIXFINDER_H
-
-#include <vector>
-#include <map>
-#ifdef _MSC_VER
-#include <msvc/stdint.h>
-#else
-#include <stdint.h>
-#endif //_MSC_VER
-
-#include "Clause.h"
-#include "Solver.h"
-
-namespace MINISAT
-{
-using namespace MINISAT;
-
-class Solver;
-
-using std::map;
-using std::vector;
-using std::pair;
-
-class MatrixFinder {
-    
-    public:
-        MatrixFinder(Solver& solver);
-        const uint findMatrixes();
-    
-    private:
-        const uint setMatrixes();
-        
-        struct mysorter
-        {
-            bool operator () (const pair<uint, uint>& left, const pair<uint, uint>& right)
-            {
-                return left.second < right.second;
-            }
-        };
-        
-        void findParts(vector<Var>& xorFingerprintInMatrix, vector<XorClause*>& xorsInMatrix);
-        inline const Var fingerprint(const XorClause& c) const;
-        inline const bool firstPartOfSecond(const XorClause& c1, const XorClause& c2) const;
-        
-        map<uint, vector<Var> > reverseTable; //matrix -> vars
-        vector<Var> table; //var -> matrix
-        uint matrix_no;
-        
-        Solver& solver;
-};
-
-}; //NAMESPACE MINISAT
-
-#endif //MATRIXFINDER_H
index 964ecc736f57f6808e199be3e2501ec34646f590..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,427 +0,0 @@
-// MersenneTwister.h
-// Mersenne Twister random number generator -- a C++ class MTRand
-// Based on code by Makoto Matsumoto, Takuji Nishimura, and Shawn Cokus
-// Richard J. Wagner  v1.0  15 May 2003  rjwagner@writeme.com
-
-// The Mersenne Twister is an algorithm for generating random numbers.  It
-// was designed with consideration of the flaws in various other generators.
-// The period, 2^19937-1, and the order of equidistribution, 623 dimensions,
-// are far greater.  The generator is also fast; it avoids multiplication and
-// division, and it benefits from caches and pipelines.  For more information
-// see the inventors' web page at http://www.math.keio.ac.jp/~matumoto/emt.html
-
-// Reference
-// M. Matsumoto and T. Nishimura, "Mersenne Twister: A 623-Dimensionally
-// Equidistributed Uniform Pseudo-Random Number Generator", ACM Transactions on
-// Modeling and Computer Simulation, Vol. 8, No. 1, January 1998, pp 3-30.
-
-// Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura,
-// Copyright (C) 2000 - 2003, Richard J. Wagner
-// All rights reserved.                          
-//
-// Redistribution and use in source and binary forms, with or without
-// modification, are permitted provided that the following conditions
-// are met:
-//
-//   1. Redistributions of source code must retain the above copyright
-//      notice, this list of conditions and the following disclaimer.
-//
-//   2. Redistributions in binary form must reproduce the above copyright
-//      notice, this list of conditions and the following disclaimer in the
-//      documentation and/or other materials provided with the distribution.
-//
-//   3. The names of its contributors may not be used to endorse or promote 
-//      products derived from this software without specific prior written 
-//      permission.
-//
-// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-// A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
-// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
-// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
-// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
-// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
-// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
-// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
-// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-
-// The original code included the following notice:
-//
-//     When you use this, send an email to: matumoto@math.keio.ac.jp
-//     with an appropriate reference to your work.
-//
-// It would be nice to CC: rjwagner@writeme.com and Cokus@math.washington.edu
-// when you write.
-
-#ifndef MERSENNETWISTER_H
-#define MERSENNETWISTER_H
-
-#include <iostream>
-#include <limits.h>
-#include <stdio.h>
-#include <time.h>
-#include <math.h>
-
-namespace MINISAT
-{
-
-// Not thread safe (unless auto-initialization is avoided and each thread has
-// its own MTRand object)
-
-class MTRand {
-// Data
-public:
-       typedef unsigned long uint32;  // unsigned integer type, at least 32 bits
-       
-       enum { N = 624 };       // length of state vector
-       enum { SAVE = N + 1 };  // length of array for save()
-
-protected:
-       enum { M = 397 };  // period parameter
-       
-       uint32 state[N];   // internal state
-       uint32 *pNext;     // next value to get from state
-       int left;          // number of values left before reload needed
-
-
-//Methods
-public:
-       MTRand( const uint32& oneSeed );  // initialize with a simple uint32
-       MTRand( uint32 *const bigSeed, uint32 const seedLength = N );  // or an array
-       MTRand();  // auto-initialize with /dev/urandom or time() and clock()
-       
-       // Do NOT use for CRYPTOGRAPHY without securely hashing several returned
-       // values together, otherwise the generator state can be learned after
-       // reading 624 consecutive values.
-       
-       // Access to 32-bit random numbers
-       double rand();                          // real number in [0,1]
-       double rand( const double& n );         // real number in [0,n]
-       double randExc();                       // real number in [0,1)
-       double randExc( const double& n );      // real number in [0,n)
-       double randDblExc();                    // real number in (0,1)
-       double randDblExc( const double& n );   // real number in (0,n)
-       uint32 randInt();                       // integer in [0,2^32-1]
-       uint32 randInt( const uint32& n );      // integer in [0,n] for n < 2^32
-       double operator()() { return rand(); }  // same as rand()
-       
-       // Access to 53-bit random numbers (capacity of IEEE double precision)
-       double rand53();  // real number in [0,1)
-       
-       // Access to nonuniform random number distributions
-       double randNorm( const double& mean = 0.0, const double& variance = 0.0 );
-       
-       // Re-seeding functions with same behavior as initializers
-       void seed( const uint32 oneSeed );
-       void seed( uint32 *const bigSeed, const uint32 seedLength = N );
-       void seed();
-       
-       // Saving and loading generator state
-       void save( uint32* saveArray ) const;  // to array of size SAVE
-       void load( uint32 *const loadArray );  // from such array
-       friend std::ostream& operator<<( std::ostream& os, const MTRand& mtrand );
-       friend std::istream& operator>>( std::istream& is, MTRand& mtrand );
-
-protected:
-       void initialize( const uint32 oneSeed );
-       void reload();
-       uint32 hiBit( const uint32& u ) const { return u & 0x80000000UL; }
-       uint32 loBit( const uint32& u ) const { return u & 0x00000001UL; }
-       uint32 loBits( const uint32& u ) const { return u & 0x7fffffffUL; }
-       uint32 mixBits( const uint32& u, const uint32& v ) const
-               { return hiBit(u) | loBits(v); }
-       uint32 twist( const uint32& m, const uint32& s0, const uint32& s1 ) const
-               { return m ^ (mixBits(s0,s1)>>1) ^ (-loBit(s1) & 0x9908b0dfUL); }
-       static uint32 hash( time_t t, clock_t c );
-};
-
-
-inline MTRand::MTRand( const uint32& oneSeed )
-       { seed(oneSeed); }
-
-inline MTRand::MTRand( uint32 *const bigSeed, const uint32 seedLength )
-       { seed(bigSeed,seedLength); }
-
-inline MTRand::MTRand()
-       { seed(); }
-
-inline double MTRand::rand()
-       { return double(randInt()) * (1.0/4294967295.0); }
-
-inline double MTRand::rand( const double& n )
-       { return rand() * n; }
-
-inline double MTRand::randExc()
-       { return double(randInt()) * (1.0/4294967296.0); }
-
-inline double MTRand::randExc( const double& n )
-       { return randExc() * n; }
-
-inline double MTRand::randDblExc()
-       { return ( double(randInt()) + 0.5 ) * (1.0/4294967296.0); }
-
-inline double MTRand::randDblExc( const double& n )
-       { return randDblExc() * n; }
-
-inline double MTRand::rand53()
-{
-       uint32 a = randInt() >> 5, b = randInt() >> 6;
-       return ( a * 67108864.0 + b ) * (1.0/9007199254740992.0);  // by Isaku Wada
-}
-
-inline double MTRand::randNorm( const double& mean, const double& variance )
-{
-       // Return a real number from a normal (Gaussian) distribution with given
-       // mean and variance by Box-Muller method
-       double r = sqrt( -2.0 * log( 1.0-randDblExc()) ) * variance;
-       double phi = 2.0 * 3.14159265358979323846264338328 * randExc();
-       return mean + r * cos(phi);
-}
-
-inline MTRand::uint32 MTRand::randInt()
-{
-       // Pull a 32-bit integer from the generator state
-       // Every other access function simply transforms the numbers extracted here
-       
-       if( left == 0 ) reload();
-       --left;
-               
-       register uint32 s1;
-       s1 = *pNext++;
-       s1 ^= (s1 >> 11);
-       s1 ^= (s1 <<  7) & 0x9d2c5680UL;
-       s1 ^= (s1 << 15) & 0xefc60000UL;
-       return ( s1 ^ (s1 >> 18) );
-}
-
-inline MTRand::uint32 MTRand::randInt( const uint32& n )
-{
-       // Find which bits are used in n
-       // Optimized by Magnus Jonsson (magnus@smartelectronix.com)
-       uint32 used = n;
-       used |= used >> 1;
-       used |= used >> 2;
-       used |= used >> 4;
-       used |= used >> 8;
-       used |= used >> 16;
-       
-       // Draw numbers until one is found in [0,n]
-       uint32 i;
-       do
-               i = randInt() & used;  // toss unused bits to shorten search
-       while( i > n );
-       return i;
-}
-
-
-inline void MTRand::seed( const uint32 oneSeed )
-{
-       // Seed the generator with a simple uint32
-       initialize(oneSeed);
-       reload();
-}
-
-
-inline void MTRand::seed( uint32 *const bigSeed, const uint32 seedLength )
-{
-       // Seed the generator with an array of uint32's
-       // There are 2^19937-1 possible initial states.  This function allows
-       // all of those to be accessed by providing at least 19937 bits (with a
-       // default seed length of N = 624 uint32's).  Any bits above the lower 32
-       // in each element are discarded.
-       // Just call seed() if you want to get array from /dev/urandom
-       initialize(19650218UL);
-       register int i = 1;
-       register uint32 j = 0;
-       register int k = ( N > seedLength ? N : seedLength );
-       for( ; k; --k )
-       {
-               state[i] =
-                       state[i] ^ ( (state[i-1] ^ (state[i-1] >> 30)) * 1664525UL );
-               state[i] += ( bigSeed[j] & 0xffffffffUL ) + j;
-               state[i] &= 0xffffffffUL;
-               ++i;  ++j;
-               if( i >= N ) { state[0] = state[N-1];  i = 1; }
-               if( j >= seedLength ) j = 0;
-       }
-       for( k = N - 1; k; --k )
-       {
-               state[i] =
-                       state[i] ^ ( (state[i-1] ^ (state[i-1] >> 30)) * 1566083941UL );
-               state[i] -= i;
-               state[i] &= 0xffffffffUL;
-               ++i;
-               if( i >= N ) { state[0] = state[N-1];  i = 1; }
-       }
-       state[0] = 0x80000000UL;  // MSB is 1, assuring non-zero initial array
-       reload();
-}
-
-
-inline void MTRand::seed()
-{
-       // Seed the generator with an array from /dev/urandom if available
-       // Otherwise use a hash of time() and clock() values
-       
-       // First try getting an array from /dev/urandom
-       FILE* urandom = fopen( "/dev/urandom", "rb" );
-       if( urandom )
-       {
-               uint32 bigSeed[N];
-               register uint32 *s = bigSeed;
-               register int i = N;
-               register bool success = true;
-               while( success && i-- )
-                       success = fread( s++, sizeof(uint32), 1, urandom );
-               fclose(urandom);
-               if( success ) { seed( bigSeed, N );  return; }
-       }
-       
-       // Was not successful, so use time() and clock() instead
-       seed( hash( time(NULL), clock() ) );
-}
-
-
-inline void MTRand::initialize( const uint32 seed )
-{
-       // Initialize generator state with seed
-       // See Knuth TAOCP Vol 2, 3rd Ed, p.106 for multiplier.
-       // In previous versions, most significant bits (MSBs) of the seed affect
-       // only MSBs of the state array.  Modified 9 Jan 2002 by Makoto Matsumoto.
-       register uint32 *s = state;
-       register uint32 *r = state;
-       register int i = 1;
-       *s++ = seed & 0xffffffffUL;
-       for( ; i < N; ++i )
-       {
-               *s++ = ( 1812433253UL * ( *r ^ (*r >> 30) ) + i ) & 0xffffffffUL;
-               r++;
-       }
-}
-
-
-inline void MTRand::reload()
-{
-       // Generate N new values in state
-       // Made clearer and faster by Matthew Bellew (matthew.bellew@home.com)
-       register uint32 *p = state;
-       register int i;
-       for( i = N - M; i--; ++p )
-               *p = twist( p[M], p[0], p[1] );
-       for( i = M; --i; ++p )
-               *p = twist( p[M-N], p[0], p[1] );
-       *p = twist( p[M-N], p[0], state[0] );
-
-       left = N, pNext = state;
-}
-
-
-inline MTRand::uint32 MTRand::hash( time_t t, clock_t c )
-{
-       // Get a uint32 from t and c
-       // Better than uint32(x) in case x is floating point in [0,1]
-       // Based on code by Lawrence Kirby (fred@genesis.demon.co.uk)
-
-       static uint32 differ = 0;  // guarantee time-based seeds will change
-
-       uint32 h1 = 0;
-       unsigned char *p = (unsigned char *) &t;
-       for( size_t i = 0; i < sizeof(t); ++i )
-       {
-               h1 *= UCHAR_MAX + 2U;
-               h1 += p[i];
-       }
-       uint32 h2 = 0;
-       p = (unsigned char *) &c;
-       for( size_t j = 0; j < sizeof(c); ++j )
-       {
-               h2 *= UCHAR_MAX + 2U;
-               h2 += p[j];
-       }
-       return ( h1 + differ++ ) ^ h2;
-}
-
-
-inline void MTRand::save( uint32* saveArray ) const
-{
-       register uint32 *sa = saveArray;
-       register const uint32 *s = state;
-       register int i = N;
-       for( ; i--; *sa++ = *s++ ) {}
-       *sa = left;
-}
-
-
-inline void MTRand::load( uint32 *const loadArray )
-{
-       register uint32 *s = state;
-       register uint32 *la = loadArray;
-       register int i = N;
-       for( ; i--; *s++ = *la++ ) {}
-       left = *la;
-       pNext = &state[N-left];
-}
-
-
-inline std::ostream& operator<<( std::ostream& os, const MTRand& mtrand )
-{
-       register const MTRand::uint32 *s = mtrand.state;
-       register int i = mtrand.N;
-       for( ; i--; os << *s++ << "\t" ) {}
-       return os << mtrand.left;
-}
-
-
-inline std::istream& operator>>( std::istream& is, MTRand& mtrand )
-{
-       register MTRand::uint32 *s = mtrand.state;
-       register int i = mtrand.N;
-       for( ; i--; is >> *s++ ) {}
-       is >> mtrand.left;
-       mtrand.pNext = &mtrand.state[mtrand.N-mtrand.left];
-       return is;
-}
-};
-
-#endif  // MERSENNETWISTER_H
-
-// Change log:
-//
-// v0.1 - First release on 15 May 2000
-//      - Based on code by Makoto Matsumoto, Takuji Nishimura, and Shawn Cokus
-//      - Translated from C to C++
-//      - Made completely ANSI compliant
-//      - Designed convenient interface for initialization, seeding, and
-//        obtaining numbers in default or user-defined ranges
-//      - Added automatic seeding from /dev/urandom or time() and clock()
-//      - Provided functions for saving and loading generator state
-//
-// v0.2 - Fixed bug which reloaded generator one step too late
-//
-// v0.3 - Switched to clearer, faster reload() code from Matthew Bellew
-//
-// v0.4 - Removed trailing newline in saved generator format to be consistent
-//        with output format of built-in types
-//
-// v0.5 - Improved portability by replacing static const int's with enum's and
-//        clarifying return values in seed(); suggested by Eric Heimburg
-//      - Removed MAXINT constant; use 0xffffffffUL instead
-//
-// v0.6 - Eliminated seed overflow when uint32 is larger than 32 bits
-//      - Changed integer [0,n] generator to give better uniformity
-//
-// v0.7 - Fixed operator precedence ambiguity in reload()
-//      - Added access for real numbers in (0,1) and (0,n)
-//
-// v0.8 - Included time.h header to properly support time_t and clock_t
-//
-// v1.0 - Revised seeding to match 26 Jan 2002 update of Nishimura and Matsumoto
-//      - Allowed for seeding with arrays of any length
-//      - Added access for real numbers in [0,1) with 53-bit resolution
-//      - Added access for real numbers from normal (Gaussian) distributions
-//      - Increased overall speed by optimizing twist()
-//      - Doubled speed of integer [0,n] generation
-//      - Fixed out-of-range number generation on 64-bit machines
-//      - Improved portability by substituting literal constants for long enum's
-//      - Changed license from GNU LGPL to BSD
index 5ab39cddf4024228d4816905627ca1907af4a65a..534032f629505c60c8702d70748f370a2a161a70 100644 (file)
@@ -60,12 +60,12 @@ const bool PartFinder::findParts()
     part_no = 0;
     
     solver.clauseCleaner->removeAndCleanAll(true);
-    if (solver.ok == false) return false;
+    if (!solver.ok) return false;
     while (solver.varReplacer->getNewToReplaceVars() > 0) {
         if (solver.performReplace && !solver.varReplacer->performReplace(true))
             return false;
         solver.clauseCleaner->removeAndCleanAll(true);
-        if (solver.ok == false) return false;
+        if (!solver.ok) return false;
     }
     assert(solver.varReplacer->getClauses().size() == 0);
     
index c1773bd4f986df99a37f759db3e89957de582192..27c567442c115e52956af16fa4629ccefccc4eb3 100644 (file)
@@ -38,8 +38,12 @@ const bool PartHandler::handle()
         return true;
     
     PartFinder partFinder(solver);
-    if (!partFinder.findParts())
+    if (!partFinder.findParts()) {
+        #ifdef VERBOSE_DEBUG
+        std::cout << "c findParts() found UNSAT. Whole problem is unsat." << std::endl;
+        #endif //VERBOSE_DEBUG
         return false;
+    }
     
     uint32_t num_parts = partFinder.getReverseTable().size();
     if (num_parts == 1)
@@ -80,19 +84,23 @@ const bool PartHandler::handle()
         newSolver.doPartHandler = solver.doPartHandler;
         newSolver.fixRestartType = solver.fixRestartType;
         newSolver.var_inc = solver.var_inc;
-        newSolver.polarity_mode = Solver::polarity_manual;
+        newSolver.polarity_mode = solver.polarity_mode;
         std::sort(vars.begin(), vars.end());
         uint32_t i2 = 0;
         for (Var var = 0; var < solver.nVars(); var++) {
             if (i2 < vars.size() && vars[i2] == var) {
+                #ifdef VERBOSE_DEBUG
+                if (!solver.decision_var[var]) {
+                    std::cout << "var " << var + 1 << " is non-decision, but in part... strange." << std::endl;
+                }
+                #endif //VERBOSE_DEBUG
                 newSolver.newVar(solver.decision_var[var]);
                 newSolver.activity[var] = solver.activity[var];
-                newSolver.defaultPolarities[var] = solver.polarity[var];
                 newSolver.order_heap.update(var);
                 assert(partFinder.getVarPart(var) == part);
                 if (solver.decision_var[var]) {
                     solver.setDecisionVar(var, false);
-                    if (solver.decision_var[var]) decisionVarRemoved.push(var);
+                    decisionVarRemoved.push(var);
                 }
                 i2++;
             } else {
@@ -111,8 +119,12 @@ const bool PartHandler::handle()
         assert(checkClauseMovement(newSolver, part, partFinder));
         
         lbool status = newSolver.solve();
-        if (status == l_False)
+        if (status == l_False) {
+            #ifdef VERBOSE_DEBUG
+            std::cout << "c One of the sub-problems was UNSAT. Whole problem is unsat." << std::endl;
+            #endif //VERBOSE_DEBUG
             return false;
+        }
         assert(status != l_Undef);
         
         for (Var var = 0; var < newSolver.nVars(); var++) {
@@ -130,9 +142,13 @@ const bool PartHandler::handle()
         
         for (Var var = 0; var < newSolver.nVars(); var++) {
             if (newSolver.model[var] != l_Undef) {
+                //Must have been decision var in the old solver!??
+                //assert(std::find(decisionVarRemoved.getData(), decisionVarRemoved.getDataEnd(), var) != decisionVarRemoved.getDataEnd());
                 assert(savedState[var] == l_Undef);
                 assert(partFinder.getVarPart(var) == part);
-                savedState[var] = newSolver.model[var];
+                if (newSolver.assigns[var] == l_Undef) {
+                    savedState[var] = newSolver.model[var];
+                }
             }
         }
         
@@ -194,9 +210,14 @@ void PartHandler::moveClauses(vec<Clause*>& cs, Solver& newSolver, const uint32_
             continue;
         }
         solver.detachClause(**i);
-        vec<Lit> cs((*i)->size());
-        std::copy((**i).getData(), (**i).getDataEnd(), cs.getData());
-        newSolver.addClause(cs, (**i).getGroup());
+        #ifdef VERBOSE_DEBUG
+        std::cout << "clause in this part:"; (**i).plainPrint();
+        #endif
+
+        Clause& c = **i;
+        vec<Lit> tmp(c.size());
+        std::copy(c.getData(), c.getDataEnd(), tmp.getData());
+        newSolver.addClause(tmp, c.getGroup());
         //NOTE: we need the CS because otherwise, the addClause could have changed **i, which we need to re-add later!
         clausesRemoved.push(*i);
     }
@@ -212,10 +233,14 @@ void PartHandler::moveClauses(vec<XorClause*>& cs, Solver& newSolver, const uint
             continue;
         }
         solver.detachClause(**i);
-        vec<Lit> cs((*i)->size());
-        for (uint32_t i2 = 0; i2 < (*i)->size(); i2++)
-            cs[i2] = (**i)[i2].unsign();
-        newSolver.addXorClause(cs, (**i).xor_clause_inverted(), (**i).getGroup());
+        #ifdef VERBOSE_DEBUG
+        std::cout << "xor clause in this part:"; (**i).plainPrint();
+        #endif
+
+        XorClause& c = **i;
+        vec<Lit> tmp(c.size());
+        std::copy(c.getData(), c.getDataEnd(), tmp.getData());
+        newSolver.addXorClause(tmp, c.xor_clause_inverted(), c.getGroup());
         //NOTE: we need the CS because otherwise, the addXorClause could have changed **i, which we need to re-add later!
         xorClausesRemoved.push(*i);
     }
@@ -238,7 +263,7 @@ void PartHandler::moveLearntClauses(vec<Clause*>& cs, Solver& newSolver, const u
         for (const Lit* l = c.getData(), *end = l + c.size(); l != end; l++) {
             if (partFinder.getVarPart(l->var()) != clause_part) {
                 #ifdef VERBOSE_DEBUG
-                std::cout << "Learnt clause in both parts!" << std::endl;
+                std::cout << "Learnt clause in both parts:"; c.plainPrint();
                 #endif
                 
                 removed = true;
@@ -249,15 +274,15 @@ void PartHandler::moveLearntClauses(vec<Clause*>& cs, Solver& newSolver, const u
         if (removed) continue;
         if (clause_part == part) {
             #ifdef VERBOSE_DEBUG
-            std::cout << "Learnt clause in this part!" << std::endl;
+            //std::cout << "Learnt clause in this part:"; c.plainPrint();
             #endif
             
             solver.detachClause(c);
             newSolver.addLearntClause(c, c.getGroup(), c.activity());
-            free(*i);
+            clauseFree(&c);
         } else {
             #ifdef VERBOSE_DEBUG
-            std::cout << "Learnt clause in other part!" << std::endl;
+            std::cout << "Learnt clause in other part:"; c.plainPrint();
             #endif
             
             *j++ = *i;
@@ -268,10 +293,11 @@ void PartHandler::moveLearntClauses(vec<Clause*>& cs, Solver& newSolver, const u
 
 void PartHandler::addSavedState()
 {
+    //Don't add these (non-0-decison-level!) solutions to the 0th decision level
+    solver.newDecisionLevel();
     for (Var var = 0; var < savedState.size(); var++) {
         if (savedState[var] != l_Undef) {
-            assert(solver.assigns[var] == l_Undef || (solver.assigns[var] == savedState[var] && solver.level[var] == 0));
-            //decision level should NOT be 0.... TODO
+            assert(solver.assigns[var] == l_Undef);
             solver.uncheckedEnqueue(Lit(var, savedState[var] == l_False));
             assert(solver.assigns[var] == savedState[var]);
             savedState[var] = l_Undef;
@@ -279,8 +305,8 @@ void PartHandler::addSavedState()
         }
     }
     
-    for (uint32_t var = 0; var < decisionVarRemoved.size(); var++)
-        solver.setDecisionVar(var, true);
+    for (uint32_t i = 0; i < decisionVarRemoved.size(); i++)
+        solver.setDecisionVar(decisionVarRemoved[i], true);
     decisionVarRemoved.clear();
 }
 
@@ -295,10 +321,7 @@ void PartHandler::readdRemovedClauses()
     clausesRemoved.clear();
     
     for (XorClause **it = xorClausesRemoved.getData(), **end = xorClausesRemoved.getDataEnd(); it != end; it++) {
-        for (Lit *l = (*it)->getData(), *end2 = (*it)->getDataEnd(); l != end2; l++) {
-            *l = l->unsign();
-        }
-        solver.addXorClause(**it, (*it)->getGroup());
+        solver.addXorClause(**it, (**it).xor_clause_inverted(), (*it)->getGroup());
         assert(solver.ok);
     }
     xorClausesRemoved.clear();
index 1c877a892e304e356486e0836b356b8718690805..2da63b22c2bc1a377c7b3cf38b380689c60903ac 100644 (file)
@@ -32,7 +32,6 @@ OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWA
 
 #include "VarReplacer.h"
 #include "FindUndef.h"
-#include "Conglomerate.h"
 #include "XorFinder.h"
 #include "ClauseCleaner.h"
 #include "RestartTypeChooser.h"
@@ -40,6 +39,7 @@ OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWA
 #include "Subsumer.h"
 #include "PartHandler.h"
 #include "XorSubsumer.h"
+#include "StateSaver.h"
 
 #ifdef USE_GAUSS
 #include "Gaussian.h"
@@ -51,6 +51,7 @@ OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWA
 //#define __builtin_prefetch(a,b)
 #endif //_MSC_VER
 
+//#define DEBUG_UNCHECKEDENQUEUE_LEVEL0
 //#define VERBOSE_DEBUG_POLARITIES
 //#define DEBUG_DYNAMIC_RESTART
 
@@ -89,6 +90,12 @@ Solver::Solver() :
         , doVarElim        (true)
         , doSubsume1       (true)
         , failedVarSearch  (true)
+        , readdOldLearnts  (false)
+        , addExtraBins     (true)
+        , removeUselessBins(true)
+        , regularRemoveUselessBins(true)
+        , subsumeWithNonExistBinaries(true)
+        , regularSubsumeWithNonExistBinaries(true)
         , libraryUsage     (true)
         , greedyUnbound    (false)
         , fixRestartType   (auto_restart)
@@ -101,6 +108,10 @@ Solver::Solver() :
         , improvedClauseNo(0), improvedClauseSize(0)
         
 
+        , sum_gauss_called (0)
+        , sum_gauss_confl  (0)
+        , sum_gauss_prop   (0)
+        , sum_gauss_unit_truths (0)
         , ok               (true)
         , var_inc          (128)
         , cla_inc          (1)
@@ -129,12 +140,15 @@ Solver::Solver() :
         , simplifying      (false)
 {
     varReplacer = new VarReplacer(*this);
-    conglomerate = new Conglomerate(*this);
     clauseCleaner = new ClauseCleaner(*this);
     failedVarSearcher = new FailedVarSearcher(*this);
     partHandler = new PartHandler(*this);
     subsumer = new Subsumer(*this);
+    xorSubsumer = new XorSubsumer(*this);
     restartTypeChooser = new RestartTypeChooser(*this);
+    #ifdef USE_GAUSS
+    matrixFinder = new MatrixFinder(*this);
+    #endif //USE_GAUSS
     
     #ifdef STATS_NEEDED
     logger.setSolver(this);
@@ -146,16 +160,20 @@ Solver::~Solver()
     for (uint32_t i = 0; i != learnts.size(); i++) clauseFree(learnts[i]);
     for (uint32_t i = 0; i != clauses.size(); i++) clauseFree(clauses[i]);
     for (uint32_t i = 0; i != binaryClauses.size(); i++) clauseFree(binaryClauses[i]);
-    for (uint32_t i = 0; i != xorclauses.size(); i++) free(xorclauses[i]);
+    for (uint32_t i = 0; i != xorclauses.size(); i++) clauseFree(xorclauses[i]);
+    for (uint32_t i = 0; i != removedLearnts.size(); i++) clauseFree(removedLearnts[i]);
     #ifdef USE_GAUSS
     clearGaussMatrixes();
+    delete matrixFinder;
     #endif
+    for (uint32_t i = 0; i != freeLater.size(); i++) clauseFree(freeLater[i]);
+    
     delete varReplacer;
-    delete conglomerate;
     delete clauseCleaner;
     delete failedVarSearcher;
     delete partHandler;
     delete subsumer;
+    delete xorSubsumer;
     delete restartTypeChooser;
     
     if (libraryCNFFile)
@@ -184,16 +202,18 @@ Var Solver::newVar(bool dvar)
     seen      .push_back(0);
     permDiff  .push(0);
     
-    polarity  .push_back(true);
-    defaultPolarities.push_back(true);
+    polarity  .push_back(defaultPolarity());
+    #ifdef USE_OLD_POLARITIES
+    oldPolarity.push_back(defaultPolarity());
+    #endif //USE_OLD_POLARITIES
 
     decision_var.push_back(dvar);
     insertVarOrder(v);
     
     varReplacer->newVar();
-    conglomerate->newVar();
     partHandler->newVar();
     subsumer->newVar();
+    xorSubsumer->newVar();
 
     insertVarOrder(v);
     
@@ -211,18 +231,18 @@ Var Solver::newVar(bool dvar)
 template<class T>
 XorClause* Solver::addXorClauseInt(T& ps, bool xor_clause_inverted, const uint32_t group)
 {
+    assert(qhead == trail.size());
+    assert(decisionLevel() == 0);
+    
     if (ps.size() > (0x01UL << 18)) {
         std::cout << "Too long clause!" << std::endl;
         exit(-1);
     }
-    std::sort(ps.getData(), ps.getData()+ps.size());
+    std::sort(ps.getData(), ps.getDataEnd());
     Lit p;
     uint32_t i, j;
     for (i = j = 0, p = lit_Undef; i != ps.size(); i++) {
-        xor_clause_inverted ^= ps[i].sign();
-        ps[i] ^= ps[i].sign();
-        
-        if (ps[i] == p) {
+        if (ps[i].var() == p.var()) {
             //added, but easily removed
             j--;
             p = lit_Undef;
@@ -241,8 +261,7 @@ XorClause* Solver::addXorClauseInt(T& ps, bool xor_clause_inverted, const uint32
             return NULL;
         }
         case 1: {
-            assert(assigns[ps[0].var()].isUndef());
-            uncheckedEnqueue(ps[0] ^ xor_clause_inverted);
+            uncheckedEnqueue(Lit(ps[0].var(), xor_clause_inverted));
             ok = (propagate() == NULL);
             return NULL;
         }
@@ -250,7 +269,10 @@ XorClause* Solver::addXorClauseInt(T& ps, bool xor_clause_inverted, const uint32
             #ifdef VERBOSE_DEBUG
             cout << "--> xor is 2-long, replacing var " << ps[0].var()+1 << " with " << (!xor_clause_inverted ? "-" : "") << ps[1].var()+1 << endl;
             #endif
-            
+
+            learnt_clause_group = std::max(group+1, learnt_clause_group);
+            ps[0] = ps[0].unsign();
+            ps[1] = ps[1].unsign();
             varReplacer->replace(ps, xor_clause_inverted, group);
             return NULL;
         }
@@ -277,9 +299,7 @@ bool Solver::addXorClause(T& ps, bool xor_clause_inverted, const uint group, cha
     
     if (libraryCNFFile) {
         fprintf(libraryCNFFile, "x");
-        for (uint i = 0; i < ps.size(); i++) {
-            fprintf(libraryCNFFile, "%s%d ", ps[i].sign() ? "-" : "", ps[i].var()+1);
-        }
+        for (uint32_t i = 0; i < ps.size(); i++) ps[i].print(libraryCNFFile);
         fprintf(libraryCNFFile, "0\n");
     }
     
@@ -293,11 +313,19 @@ bool Solver::addXorClause(T& ps, bool xor_clause_inverted, const uint group, cha
     assert(qhead == trail.size());
 
     // Check if clause is satisfied and remove false/duplicate literals:
-    if (varReplacer->getNumLastReplacedVars() || subsumer->getNumElimed()) {
+    if (varReplacer->getNumLastReplacedVars() || subsumer->getNumElimed() || xorSubsumer->getNumElimed()) {
         for (uint32_t i = 0; i != ps.size(); i++) {
-            ps[i] = varReplacer->getReplaceTable()[ps[i].var()] ^ ps[i].sign();
             if (subsumer->getVarElimed()[ps[i].var()] && !subsumer->unEliminate(ps[i].var()))
                 return false;
+            else if (xorSubsumer->getVarElimed()[ps[i].var()] && !xorSubsumer->unEliminate(ps[i].var()))
+                return false;
+            else {
+                Lit otherLit = varReplacer->getReplaceTable()[ps[i].var()];
+                if (otherLit.var() != ps[i].var()) {
+                    ps[i] = Lit(otherLit.var(), false);
+                    xor_clause_inverted ^= otherLit.sign();
+                }
+            }
         }
     }
     
@@ -315,14 +343,19 @@ template<class T>
 bool Solver::addLearntClause(T& ps, const uint group, const uint32_t activity)
 {
     Clause* c = addClauseInt(ps, group);
-    if (c == NULL)
-        return ok;
-    
+    if (c == NULL) return ok;
+
+    //compensate for addClauseInt's attachClause, which doesn't know
+    //that this is a learnt clause.
     clauses_literals -= c->size();
+    learnts_literals += c->size();
     
     c->makeLearnt(activity);
-    learnts.push(c);
-    learnts_literals += c->size();
+    if (c->size() > 2) learnts.push(c);
+    else {
+        nbBin++;
+        binaryClauses.push(c);
+    }
     return ok;
 }
 template bool Solver::addLearntClause(Clause& ps, const uint group, const uint32_t activity);
@@ -333,7 +366,7 @@ Clause* Solver::addClauseInt(T& ps, uint group)
 {
     assert(ok);
     
-    std::sort(ps.getData(), ps.getData()+ps.size());
+    std::sort(ps.getData(), ps.getDataEnd());
     Lit p = lit_Undef;
     uint32_t i, j;
     for (i = j = 0; i != ps.size(); i++) {
@@ -373,9 +406,7 @@ bool Solver::addClause(T& ps, const uint group, char* group_name)
     }
     
     if (libraryCNFFile) {
-        for (uint32_t i = 0; i != ps.size(); i++) {
-            fprintf(libraryCNFFile, "%s%d ", ps[i].sign() ? "-" : "", ps[i].var()+1);
-        }
+        for (uint32_t i = 0; i != ps.size(); i++) ps[i].print(libraryCNFFile);
         fprintf(libraryCNFFile, "0\n");
     }
     
@@ -389,11 +420,13 @@ bool Solver::addClause(T& ps, const uint group, char* group_name)
     assert(qhead == trail.size());
 
     // Check if clause is satisfied and remove false/duplicate literals:
-    if (varReplacer->getNumLastReplacedVars() || subsumer->getNumElimed()) {
+    if (varReplacer->getNumLastReplacedVars() || subsumer->getNumElimed() || xorSubsumer->getNumElimed()) {
         for (uint32_t i = 0; i != ps.size(); i++) {
             ps[i] = varReplacer->getReplaceTable()[ps[i].var()] ^ ps[i].sign();
             if (subsumer->getVarElimed()[ps[i].var()] && !subsumer->unEliminate(ps[i].var()))
                 return false;
+            if (xorSubsumer->getVarElimed()[ps[i].var()] && !xorSubsumer->unEliminate(ps[i].var()))
+                return false;
         }
     }
     
@@ -414,6 +447,10 @@ template bool Solver::addClause(Clause& ps, const uint group, char* group_name);
 void Solver::attachClause(XorClause& c)
 {
     assert(c.size() > 2);
+    #ifdef DEBUG_ATTACH
+    assert(assigns[c[0].var()] == l_Undef);
+    assert(assigns[c[1].var()] == l_Undef);
+    #endif //DEBUG_ATTACH
 
     xorwatches[c[0].var()].push(&c);
     xorwatches[c[1].var()].push(&c);
@@ -513,24 +550,27 @@ void Solver::cancelUntil(int level)
     cout << endl;
     #endif
     
-    if (decisionLevel() > level) {
+    if ((int)decisionLevel() > level) {
         
         #ifdef USE_GAUSS
         for (vector<Gaussian*>::iterator gauss = gauss_matrixes.begin(), end= gauss_matrixes.end(); gauss != end; gauss++)
             (*gauss)->canceling(trail_lim[level]);
         #endif //USE_GAUSS
         
-        for (int c = trail.size()-1; c >= (int)trail_lim[level]; c--) {
-            Var     x  = trail[c].var();
+        for (int sublevel = trail.size()-1; sublevel >= (int)trail_lim[level]; sublevel--) {
+            Var var = trail[sublevel].var();
             #ifdef VERBOSE_DEBUG
-            cout << "Canceling var " << x+1 << " sublevel: " << c << endl;
+            cout << "Canceling var " << var+1 << " sublevel: " << sublevel << endl;
             #endif
-            assigns[x] = l_Undef;
-            insertVarOrder(x);
+            #ifdef USE_OLD_POLARITIES
+            polarity[var] = oldPolarity[var];
+            #endif //USE_OLD_POLARITIES
+            assigns[var] = l_Undef;
+            insertVarOrder(var);
         }
         qhead = trail_lim[level];
-        trail.shrink(trail.size() - trail_lim[level]);
-        trail_lim.shrink(trail_lim.size() - level);
+        trail.shrink_(trail.size() - trail_lim[level]);
+        trail_lim.shrink_(trail_lim.size() - level);
     }
 
     #ifdef VERBOSE_DEBUG
@@ -567,6 +607,8 @@ inline bool Solver::defaultPolarity()
             return false;
         case polarity_rnd:
             return mtrand.randInt(1);
+        case polarity_auto:
+            return true;
         default:
             assert(false);
     }
@@ -574,72 +616,57 @@ inline bool Solver::defaultPolarity()
     return true;
 }
 
-void tallyVotes(const vec<Clause*>& cs, vector<double>& votes, vector<bool>& positiveLiteral, vector<bool>& negativeLiteral)
+void Solver::tallyVotes(const vec<Clause*>& cs, vector<double>& votes) const
 {
     for (const Clause * const*it = cs.getData(), * const*end = it + cs.size(); it != end; it++) {
         const Clause& c = **it;
         if (c.learnt()) continue;
         
         double divider;
-        if (c.size() > 63)
-            divider = 0.0;
-        else
-            divider = 1.0/(double)((uint64_t)1<<(c.size()-1));
+        if (c.size() > 63) divider = 0.0;
+        else divider = 1.0/(double)((uint64_t)1<<(c.size()-1));
+        
         for (const Lit *it2 = &c[0], *end2 = it2 + c.size(); it2 != end2; it2++) {
-            if (it2->sign()) {
-                negativeLiteral[it2->var()] = true;
-                votes[it2->var()] += divider;
-            } else {
-                positiveLiteral[it2->var()] = true;
-                votes[it2->var()] -= divider;
-            }
+            if (it2->sign()) votes[it2->var()] += divider;
+            else votes[it2->var()] -= divider;
         }
     }
 }
 
-void tallyVotes(const vec<XorClause*>& cs, vector<double>& votes, vector<bool>& positiveLiteral, vector<bool>& negativeLiteral)
+void Solver::tallyVotes(const vec<XorClause*>& cs, vector<double>& votes) const
 {
     for (const XorClause * const*it = cs.getData(), * const*end = it + cs.size(); it != end; it++) {
         const XorClause& c = **it;
         double divider;
-        if (c.size() > 63)
-            divider = 0.0;
-        else
-            divider = 1.0/(double)((uint64_t)1<<(c.size()-1));
-        for (const Lit *it2 = &c[0], *end2 = it2 + c.size(); it2 != end2; it2++) {
+        if (c.size() > 63) divider = 0.0;
+        else divider = 1.0/(double)((uint64_t)1<<(c.size()-1));
+        
+        for (const Lit *it2 = &c[0], *end2 = it2 + c.size(); it2 != end2; it2++)
             votes[it2->var()] += divider;
-            negativeLiteral[it2->var()] = true;
-            positiveLiteral[it2->var()] = true;
-        }
     }
 }
 
-const lbool Solver::calculateDefaultPolarities()
+void Solver::calculateDefaultPolarities()
 {
     #ifdef VERBOSE_DEBUG_POLARITIES
     std::cout << "Default polarities: " << std::endl;
     #endif
     
     assert(decisionLevel() == 0);
-    
     if (polarity_mode == polarity_auto) {
         double time = cpuTime();
         
         vector<double> votes;
-        vector<bool> positiveLiteral;
-        vector<bool> negativeLiteral;
         votes.resize(nVars(), 0.0);
-        positiveLiteral.resize(nVars(), false);
-        negativeLiteral.resize(nVars(), false);
         
-        tallyVotes(clauses, votes, positiveLiteral, negativeLiteral);
-        tallyVotes(binaryClauses, votes, positiveLiteral, negativeLiteral);
-        tallyVotes(varReplacer->getClauses(), votes, positiveLiteral, negativeLiteral);
-        tallyVotes(xorclauses, votes, positiveLiteral, negativeLiteral);
+        tallyVotes(clauses, votes);
+        tallyVotes(binaryClauses, votes);
+        tallyVotes(varReplacer->getClauses(), votes);
+        tallyVotes(xorclauses, votes);
         
         Var i = 0;
         for (vector<double>::const_iterator it = votes.begin(), end = votes.end(); it != end; it++, i++) {
-            defaultPolarities[i] = (*it >= 0.0);
+            polarity[i] = (*it >= 0.0);
             #ifdef VERBOSE_DEBUG_POLARITIES
             std::cout << !defaultPolarities[i] << ", ";
             #endif //VERBOSE_DEBUG_POLARITIES
@@ -650,27 +677,13 @@ const lbool Solver::calculateDefaultPolarities()
             << std::fixed << std::setw(6) << std::setprecision(2) << cpuTime()-time << " s"
             << "    |" << std:: endl;
         }
-    } else if (polarity_mode != polarity_manual){
-        for (uint i = 0; i != defaultPolarities.size(); i++) {
-            defaultPolarities[i] = defaultPolarity();
-            #ifdef VERBOSE_DEBUG_POLARITIES
-            std::cout << !defaultPolarities[i] << ", ";
-            #endif //VERBOSE_DEBUG_POLARITIES
-        }
+    } else {
+        std::fill(polarity.begin(), polarity.end(), defaultPolarity());
     }
+    
     #ifdef VERBOSE_DEBUG_POLARITIES
     std::cout << std::endl;
     #endif //VERBOSE_DEBUG_POLARITIES
-    
-    return l_Undef;
-}
-
-void Solver::setDefaultPolarities()
-{
-    assert(polarity.size() == defaultPolarities.size());
-    
-    for (uint i = 0; i != polarity.size(); i++)
-        polarity[i] = defaultPolarities[i];
 }
 
 //=================================================================================================
@@ -710,10 +723,10 @@ Lit Solver::pickBranchLit()
     if (next != var_Undef) {
         if (simplifying && random)
             sign = mtrand.randInt(1);
-        /*else
-            sign = polarity[next] ^ (mtrand.randInt(200) == 1);*/
+        #ifdef RANDOM_LOOKAROUND_SEARCHSPACE
         else if (avgBranchDepth.isvalid())
-            sign = polarity[next] ^ (mtrand.randInt(avgBranchDepth.getavg()) == 1);
+            sign = polarity[next] ^ (mtrand.randInt(avgBranchDepth.getavg() * ((lastSelectedRestartType == static_restart) ? 2 : 1) ) == 1);
+        #endif
         else
             sign = polarity[next];
     }
@@ -771,7 +784,7 @@ bool subset(const T1& A, const T2& B, vector<bool>& seen)
 |  Effect:
 |    Will undo part of the trail, upto but not beyond the assumption of the current decision level.
 |________________________________________________________________________________________________@*/
-Clause* Solver::analyze(Clause* confl, vec<Lit>& out_learnt, int& out_btlevel, int &nbLevels, const bool update)
+Clause* Solver::analyze(Clause* confl, vec<Lit>& out_learnt, int& out_btlevel, uint32_t &nbLevels, const bool update)
 {
     int pathC = 0;
     Lit p     = lit_Undef;
@@ -799,11 +812,11 @@ Clause* Solver::analyze(Clause* confl, vec<Lit>& out_learnt, int& out_btlevel, i
             if (!seen[my_var] && level[my_var] > 0) {
                 varBumpActivity(my_var);
                 seen[my_var] = 1;
-                if (level[my_var] >= decisionLevel()) {
+                if (level[my_var] >= (int)decisionLevel()) {
                     pathC++;
                     #ifdef UPDATEVARACTIVITY
-                    if ( reason[q.var()] != NULL  && reason[q.var()]->learnt() )
-                        lastDecisionLevel.push(q);
+                    if (lastSelectedRestartType == dynamic_restart && reason[q.var()] != NULL  && reason[q.var()]->learnt())
+                        lastDecisionLevel.push(q.var());
                     #endif
                 } else {
                     out_learnt.push(q);
@@ -869,26 +882,18 @@ Clause* Solver::analyze(Clause* confl, vec<Lit>& out_learnt, int& out_btlevel, i
         out_btlevel       = level[p.var()];
     }
 
-    nbLevels = 0;
-    MYFLAG++;
-    for(uint32_t i = 0; i != out_learnt.size(); i++) {
-        int lev = level[out_learnt[i].var()];
-        if (permDiff[lev] != MYFLAG) {
-            permDiff[lev] = MYFLAG;
-            nbLevels++;
-            //merged += nbPropagated(lev);
-        }
-    }
-    
-    #ifdef UPDATEVARACTIVITY
-    if (lastDecisionLevel.size() > 0) {
+    if (lastSelectedRestartType == dynamic_restart) {
+        nbLevels = calcNBLevels(out_learnt);
+        #ifdef UPDATEVARACTIVITY
         for(uint32_t i = 0; i != lastDecisionLevel.size(); i++) {
-            if (reason[lastDecisionLevel[i].var()]->activity() < nbLevels)
-                varBumpActivity(lastDecisionLevel[i].var());
+            if (reason[lastDecisionLevel[i]]->activity() < nbLevels)
+                varBumpActivity(lastDecisionLevel[i]);
         }
         lastDecisionLevel.clear();
+        #endif
+    } else {
+        nbLevels = 1000;
     }
-    #endif
 
     for (uint32_t j = 0; j != analyze_toclear.size(); j++)
         seen[analyze_toclear[j].var()] = 0;    // ('seen[]' is now cleared)
@@ -983,15 +988,24 @@ void Solver::analyzeFinal(Lit p, vec<Lit>& out_conflict)
 
 void Solver::uncheckedEnqueue(Lit p, ClausePtr from)
 {
-    #ifdef VERBOSE_DEBUG
-    cout << "uncheckedEnqueue var " << p.var()+1 << " to " << !p.sign() << " level: " << decisionLevel() << " sublevel: " << trail.size() << endl;
-    #endif
+
+    #ifdef DEBUG_UNCHECKEDENQUEUE_LEVEL0
+    #ifndef VERBOSE_DEBUG
+    if (decisionLevel() == 0)
+    #endif //VERBOSE_DEBUG
+    std::cout << "uncheckedEnqueue var " << p.var()+1 << " to " << !p.sign() << " level: " << decisionLevel() << " sublevel: " << trail.size() << std::endl;
+    #endif //DEBUG_UNCHECKEDENQUEUE_LEVEL0
+
+    //assert(decisionLevel() == 0 || !subsumer->getVarElimed()[p.var()]);
     
     assert(assigns[p.var()].isUndef());
     const Var v = p.var();
     assigns [v] = boolToLBool(!p.sign());//lbool(!sign(p));  // <<== abstract but not uttermost effecient
     level   [v] = decisionLevel();
     reason  [v] = from;
+    #ifdef USE_OLD_POLARITIES
+    oldPolarity[p.var()] = polarity[p.var()];
+    #endif //USE_OLD_POLARITIES
     polarity[p.var()] = p.sign();
     trail.push(p);
     
@@ -1001,7 +1015,6 @@ void Solver::uncheckedEnqueue(Lit p, ClausePtr from)
     #endif
 }
 
-
 /*_________________________________________________________________________________________________
 |
 |  propagate : [void]  ->  [Clause*]
@@ -1025,16 +1038,12 @@ Clause* Solver::propagate(const bool update)
 
     while (qhead < trail.size()) {
         
-        Lit            p   = trail[qhead++];     // 'p' is enqueued fact to propagate.
-        vec<Watched>&  ws  = watches[p.toInt()];
-        Watched        *i, *j, *end;
-        
         //First propagate binary clauses
         while (qheadBin < trail.size()) {
             Lit p   = trail[qheadBin++];
             vec<WatchedBin> & wbin = binwatches[p.toInt()];
-            num_props++;
-            for(WatchedBin *k = wbin.getData(), *end = k + wbin.size(); k != end; k++) {
+            num_props += wbin.size()/2;
+            for(WatchedBin *k = wbin.getData(), *end = wbin.getDataEnd(); k != end; k++) {
                 lbool val = value(k->impliedLit);
                 if (val.isUndef()) {
                     uncheckedEnqueue(k->impliedLit, k->clause);
@@ -1046,14 +1055,18 @@ Clause* Solver::propagate(const bool update)
         }
         if (confl != NULL)
             goto EndPropagate;
-        
+
         //Next, propagate normal clauses
+        Lit            p   = trail[qhead++];     // 'p' is enqueued fact to propagate.
+        vec<Watched>&  ws  = watches[p.toInt()];
+        Watched        *i, *j, *end;
+        num_props += ws.size();
         
         #ifdef VERBOSE_DEBUG
         cout << "Propagating lit " << (p.sign() ? '-' : ' ') << p.var()+1 << endl;
         #endif
 
-        for (i = j = ws.getData(), end = i + ws.size();  i != end;) {
+        for (i = j = ws.getData(), end = ws.getDataEnd();  i != end;) {
             if (i+1 != end)
                 __builtin_prefetch((i+1)->clause, 1, 0);
             
@@ -1080,7 +1093,7 @@ Clause* Solver::propagate(const bool update)
                 j++;
             } else {
                 // Look for new watch:
-                for (Lit *k = &c[2], *end2 = c.getData()+c.size(); k != end2; k++) {
+                for (Lit *k = &c[2], *end2 = c.getDataEnd(); k != end2; k++) {
                     if (value(*k) != l_False) {
                         c[1] = *k;
                         *k = false_lit;
@@ -1103,17 +1116,8 @@ Clause* Solver::propagate(const bool update)
                     uncheckedEnqueue(first, &c);
                     #ifdef DYNAMICNBLEVEL
                     if (update && c.learnt() && c.activity() > 2) { // GA
-                        MYFLAG++;
-                        int nbLevels =0;
-                        for(Lit *l = c.getData(), *end2 = l+c.size(); l != end2; l++) {
-                            int lev = level[l->var()];
-                            if (permDiff[lev] != MYFLAG) {
-                                permDiff[lev] = MYFLAG;
-                                nbLevels++;
-                            }
-                            
-                        }
-                        if(nbLevels+1 < c.activity())
+                        uint32_t nbLevels = calcNBLevels(c);
+                        if (nbLevels+1 < c.activity())
                             c.setActivity(nbLevels);
                     }
                     #endif
@@ -1122,7 +1126,7 @@ Clause* Solver::propagate(const bool update)
 FoundWatch:
             ;
         }
-        ws.shrink(i - j);
+        ws.shrink_(i - j);
 
         //Finally, propagate XOR-clauses
         if (xorclauses.size() > 0 && !confl) confl = propagate_xors(p);
@@ -1138,6 +1142,205 @@ EndPropagate:
     return confl;
 }
 
+Clause* Solver::propagateLight()
+{
+    Clause* confl = NULL;
+    uint32_t num_props = 0;
+    uint32_t qheadBin = qhead;
+    
+    while (qhead < trail.size()) {
+        
+        //First propagate binary clauses
+        while (qheadBin < trail.size()) {
+            Lit p   = trail[qheadBin++];
+            vec<WatchedBin> & wbin = binwatches[p.toInt()];
+            num_props += wbin.size()/2;
+            for(WatchedBin *k = wbin.getData(), *end = wbin.getDataEnd(); k != end; k++) {
+                lbool val = value(k->impliedLit);
+                if (val.isUndef()) {
+                    uncheckedEnqueueLight(k->impliedLit);
+                } else if (val == l_False) {
+                    confl = k->clause;
+                    goto EndPropagate;
+                }
+            }
+        }
+        
+        //Next, propagate normal clauses
+        Lit            p   = trail[qhead++];     // 'p' is enqueued fact to propagate.
+        vec<Watched>&  ws  = watches[p.toInt()];
+        Watched        *i, *j, *end;
+        num_props += ws.size();
+        
+        for (i = j = ws.getData(), end = ws.getDataEnd();  i != end;) {
+            if (i+1 != end)
+                __builtin_prefetch((i+1)->clause, 1, 0);
+            
+            if(value(i->blockedLit).getBool()) { // Clause is sat
+                *j++ = *i++;
+                continue;
+            }
+            Lit bl = i->blockedLit;
+            Clause& c = *(i->clause);
+            i++;
+            
+            // Make sure the false literal is data[1]:
+            const Lit false_lit(~p);
+            if (c[0] == false_lit)
+                c[0] = c[1], c[1] = false_lit;
+            
+            assert(c[1] == false_lit);
+            
+            // If 0th watch is true, then clause is already satisfied.
+            const Lit& first = c[0];
+            if (value(first).getBool()) {
+                j->clause = &c;
+                j->blockedLit = first;
+                j++;
+            } else {
+                // Look for new watch:
+                for (Lit *k = &c[2], *end2 = c.getDataEnd(); k != end2; k++) {
+                    if (value(*k) != l_False) {
+                        c[1] = *k;
+                        *k = false_lit;
+                        watches[(~c[1]).toInt()].push(Watched(&c, c[0]));
+                        goto FoundWatch;
+                    }
+                }
+                
+                // Did not find watch -- clause is unit under assignment:
+                j->clause = &c;
+                j->blockedLit = bl;
+                j++;
+                if (value(first) == l_False) {
+                    confl = &c;
+                    qhead = trail.size();
+                    // Copy the remaining watches:
+                    while (i < end)
+                        *j++ = *i++;
+                } else {
+                    uncheckedEnqueueLight(first);
+                }
+            }
+            FoundWatch:
+            ;
+        }
+        ws.shrink_(i - j);
+        
+        //Finally, propagate XOR-clauses
+        if (xorclauses.size() > 0 && !confl) confl = propagate_xors(p);
+    }
+    EndPropagate:
+    propagations += num_props;
+    simpDB_props -= num_props;
+    
+    return confl;
+}
+
+Clause* Solver::propagateBin()
+{
+    while (qhead < trail.size()) {
+        Lit p   = trail[qhead++];
+        vec<WatchedBin> & wbin = binwatches[p.toInt()];
+        propagations += wbin.size()/2;
+        for(WatchedBin *k = wbin.getData(), *end = wbin.getDataEnd(); k != end; k++) {
+            lbool val = value(k->impliedLit);
+            if (val.isUndef()) {
+                //uncheckedEnqueue(k->impliedLit, k->clause);
+                uncheckedEnqueueLight(k->impliedLit);
+            } else if (val == l_False) {
+                return k->clause;
+            }
+        }
+    }
+
+    return NULL;
+}
+
+Clause* Solver::propagateBinNoLearnts()
+{
+    while (qhead < trail.size()) {
+        Lit p   = trail[qhead++];
+        vec<WatchedBin> & wbin = binwatches[p.toInt()];
+        propagations += wbin.size()/2;
+        for(WatchedBin *k = wbin.getData(), *end = wbin.getDataEnd(); k != end; k++) {
+            if (k->clause->learnt()) continue;
+            lbool val = value(k->impliedLit);
+            if (val.isUndef()) {
+                //uncheckedEnqueue(k->impliedLit, k->clause);
+                uncheckedEnqueueLight(k->impliedLit);
+            } else if (val == l_False) {
+                return k->clause;
+            }
+        }
+    }
+    
+    return NULL;
+}
+
+template<bool dontCareLearnt>
+Clause* Solver::propagateBinExcept(const Lit& exceptLit)
+{
+    while (qhead < trail.size()) {
+        Lit p   = trail[qhead++];
+        vec<WatchedBin> & wbin = binwatches[p.toInt()];
+        propagations += wbin.size()/2;
+        for(WatchedBin *k = wbin.getData(), *end = wbin.getDataEnd(); k != end; k++) {
+            if (!dontCareLearnt && k->clause->learnt()) continue;
+            lbool val = value(k->impliedLit);
+            if (val.isUndef() && k->impliedLit != exceptLit) {
+                //uncheckedEnqueue(k->impliedLit, k->clause);
+                uncheckedEnqueueLight(k->impliedLit);
+            } else if (val == l_False) {
+                return k->clause;
+            }
+        }
+    }
+    
+    return NULL;
+}
+
+template Clause* Solver::propagateBinExcept <true>(const Lit& exceptLit);
+template Clause* Solver::propagateBinExcept <false>(const Lit& exceptLit);
+
+template<bool dontCareLearnt>
+Clause* Solver::propagateBinOneLevel()
+{
+    Lit p   = trail[qhead];
+    vec<WatchedBin> & wbin = binwatches[p.toInt()];
+    propagations += wbin.size()/2;
+    for(WatchedBin *k = wbin.getData(), *end = wbin.getDataEnd(); k != end; k++) {
+        if (!dontCareLearnt && k->clause->learnt()) continue;
+        lbool val = value(k->impliedLit);
+        if (val.isUndef()) {
+            //uncheckedEnqueue(k->impliedLit, k->clause);
+            uncheckedEnqueueLight(k->impliedLit);
+        } else if (val == l_False) {
+            return k->clause;
+        }
+    }
+    
+    return NULL;
+}
+
+template Clause* Solver::propagateBinOneLevel <true>();
+template Clause* Solver::propagateBinOneLevel <false>();
+
+template<class T>
+inline const uint32_t Solver::calcNBLevels(const T& ps)
+{
+    MYFLAG++;
+    uint32_t nbLevels = 0;
+    for(const Lit *l = ps.getData(), *end = ps.getDataEnd(); l != end; l++) {
+        int32_t lev = level[l->var()];
+        if (permDiff[lev] != MYFLAG) {
+            permDiff[lev] = MYFLAG;
+            nbLevels++;
+        }
+    }
+    return nbLevels;
+}
+
 Clause* Solver::propagate_xors(const Lit& p)
 {
     #ifdef VERBOSE_DEBUG_XOR
@@ -1231,7 +1434,7 @@ Clause* Solver::propagate_xors(const Lit& p)
 FoundWatch:
         ;
     }
-    ws.shrink(i - j);
+    ws.shrink_(i - j);
 
     return confl;
 }
@@ -1252,8 +1455,10 @@ bool  reduceDB_ltMiniSat::operator () (const Clause* x, const Clause* y) {
     // First criteria
     if (xsize > 2 && ysize == 2) return 1;
     if (ysize > 2 && xsize == 2) return 0;
-    
-    return x->oldActivity() < y->oldActivity();
+
+    if (x->oldActivity() == y->oldActivity())
+        return xsize > ysize;
+    else return x->oldActivity() < y->oldActivity();
 }
     
 bool  reduceDB_ltGlucose::operator () (const Clause* x, const Clause* y) {
@@ -1280,20 +1485,27 @@ void Solver::reduceDB()
         std::sort(learnts.getData(), learnts.getData()+learnts.size(), reduceDB_ltMiniSat());
     
     #ifdef VERBOSE_DEBUG
-    std::cout << "Cleaning clauses" << endl;
+    std::cout << "Cleaning clauses" << std::endl;
     for (uint i = 0; i != learnts.size(); i++) {
-        std::cout << "activity:" << learnts[i]->activity() << " \tsize:" << learnts[i]->size() << std::endl;
+        std::cout << "activity:" << learnts[i]->activity()
+        << " \toldActivity:" << learnts[i]->oldActivity()
+        << " \tsize:" << learnts[i]->size() << std::endl;
     }
     #endif
     
-    
+
     const uint removeNum = (double)learnts.size() / (double)RATIOREMOVECLAUSES;
     for (i = j = 0; i != removeNum; i++){
         //NOTE: The next instruciton only works if removeNum < learnts.size() (strictly smaller!!)
         __builtin_prefetch(learnts[i+1], 0, 0);
-        if (learnts[i]->size() > 2 && !locked(*learnts[i]) && learnts[i]->activity() > 2)
-            removeClause(*learnts[i]);
-        else
+        if (learnts[i]->size() > 2 && !locked(*learnts[i]) && learnts[i]->activity() > 2) {
+            if (readdOldLearnts) {
+                detachClause(*learnts[i]);
+                removedLearnts.push(learnts[i]);
+            } else {
+                removeClause(*learnts[i]);
+            }
+        } else
             learnts[j++] = learnts[i];
     }
     for (; i < learnts.size(); i++) {
@@ -1335,54 +1547,95 @@ void Solver::dumpSortedLearnts(const char* file, const uint32_t maxSize)
         printf("Error: Cannot open file '%s' to write learnt clauses!\n", file);
         exit(-1);
     }
-    
+
+    fprintf(outfile, "c \nc ---------\n");
     fprintf(outfile, "c unitaries\n");
-    if (maxSize > 0) {
-        if (trail_lim.size() > 0) {
-            for (uint32_t i = 0; i != trail_lim[0]; i++) {
-                fprintf(outfile,"%s%d 0\n", trail[i].sign() ? "-" : "", trail[i].var()+1);
-            }
-        }
-        else {
-            for (uint32_t i = 0; i != trail.size(); i++) {
-                fprintf(outfile,"%s%d 0\n", trail[i].sign() ? "-" : "", trail[i].var()+1);
-            }
-        }
+    fprintf(outfile, "c ---------\n");
+    for (uint32_t i = 0, end = (trail_lim.size() > 0) ? trail_lim[0] : trail.size() ; i < end; i++) {
+        trail[i].printFull(outfile);
+        #ifdef STATS_NEEDED
+        if (dynamic_behaviour_analysis)
+            fprintf(outfile, "c name of var: %s\n", logger.get_var_name(trail[i].var()).c_str());
+        #endif //STATS_NEEDED
     }
-    
-    fprintf(outfile, "c clauses from binaryClauses\n");
+
+    fprintf(outfile, "c conflicts %lu\n", conflicts);
+
+    fprintf(outfile, "c \nc ---------------------------------\n");
+    fprintf(outfile, "c learnt clauses from binaryClauses\n");
+    fprintf(outfile, "c ---------------------------------\n");
     if (maxSize >= 2) {
         for (uint i = 0; i != binaryClauses.size(); i++) {
-            if (binaryClauses[i]->learnt())
-                binaryClauses[i]->plainPrint(outfile);
+            if (binaryClauses[i]->learnt()) {
+                binaryClauses[i]->print(outfile);
+            }
         }
     }
-    
-    fprintf(outfile, "c clauses from learnts\n");
-    
-    if (lastSelectedRestartType == dynamic_restart)
-        std::sort(learnts.getData(), learnts.getData()+learnts.size(), reduceDB_ltGlucose());
-    else
-        std::sort(learnts.getData(), learnts.getData()+learnts.size(), reduceDB_ltMiniSat());
-    for (int i = learnts.size()-1; i >= 0 ; i--) {
-        if (learnts[i]->size() <= maxSize)
-            learnts[i]->plainPrint(outfile);
-    }
-    
+
+    fprintf(outfile, "c \nc ---------------------------------------\n");
     fprintf(outfile, "c clauses representing 2-long XOR clauses\n");
+    fprintf(outfile, "c ---------------------------------------\n");
     const vector<Lit>& table = varReplacer->getReplaceTable();
     for (Var var = 0; var != table.size(); var++) {
         Lit lit = table[var];
         if (lit.var() == var)
             continue;
-        
+
         fprintf(outfile, "%s%d %d 0\n", (!lit.sign() ? "-" : ""), lit.var()+1, var+1);
         fprintf(outfile, "%s%d -%d 0\n", (lit.sign() ? "-" : ""), lit.var()+1, var+1);
+        #ifdef STATS_NEEDED
+        if (dynamic_behaviour_analysis)
+            fprintf(outfile, "c name of two vars that are anti/equivalent: '%s' and '%s'\n", logger.get_var_name(lit.var()).c_str(), logger.get_var_name(var).c_str());
+        #endif //STATS_NEEDED
+    }
+
+    fprintf(outfile, "c \nc --------------------n");
+    fprintf(outfile, "c clauses from learnts\n");
+    fprintf(outfile, "c --------------------n");
+    if (lastSelectedRestartType == dynamic_restart)
+        std::sort(learnts.getData(), learnts.getData()+learnts.size(), reduceDB_ltGlucose());
+    else
+        std::sort(learnts.getData(), learnts.getData()+learnts.size(), reduceDB_ltMiniSat());
+    for (int i = learnts.size()-1; i >= 0 ; i--) {
+        if (learnts[i]->size() <= maxSize) {
+            learnts[i]->print(outfile);
+        }
     }
     
     fclose(outfile);
 }
 
+const uint32_t Solver::getNumElimSubsume() const
+{
+    return subsumer->getNumElimed();
+}
+
+const uint32_t Solver::getNumElimXorSubsume() const
+{
+    return xorSubsumer->getNumElimed();
+}
+
+const uint32_t Solver::getNumXorTrees() const
+{
+    return varReplacer->getNumTrees();
+}
+
+const uint32_t Solver::getNumXorTreesCrownSize() const
+{
+    return varReplacer->getNumReplacedVars();
+}
+
+const double Solver::getTotalTimeSubsumer() const
+{
+    return subsumer->getTotalTime();
+}
+
+const double Solver::getTotalTimeXorSubsumer() const
+{
+    return xorSubsumer->getTotalTime();
+}
+
+
 void Solver::setMaxRestarts(const uint num)
 {
     maxRestarts = num;
@@ -1402,17 +1655,18 @@ inline int64_t abs64(int64_t a)
 |    Simplify the clause database according to the current top-level assigment. Currently, the only
 |    thing done here is the removal of satisfied clauses, but more things can be put here.
 |________________________________________________________________________________________________@*/
-lbool Solver::simplify()
+const bool Solver::simplify()
 {
+    testAllClauseAttach();
     assert(decisionLevel() == 0);
 
     if (!ok || propagate() != NULL) {
         ok = false;
-        return l_False;
+        return false;
     }
 
     if (simpDB_props > 0) {
-        return l_Undef;
+        return true;
     }
     
     double slowdown = (100000.0/(double)binaryClauses.size());
@@ -1431,34 +1685,43 @@ lbool Solver::simplify()
         (((double)abs64((int64_t)nbBin - (int64_t)lastNbBin + (int64_t)becameBinary)/BINARY_TO_XOR_APPROX) * slowdown) >
         ((double)order_heap.size() * PERCENTAGEPERFORMREPLACE * speedup)) {
         lastSearchForBinaryXor = propagations;
+
         clauseCleaner->cleanClauses(clauses, ClauseCleaner::clauses);
         clauseCleaner->cleanClauses(learnts, ClauseCleaner::learnts);
         clauseCleaner->removeSatisfied(binaryClauses, ClauseCleaner::binaryClauses);
-        if (ok == false)
-            return l_False;
-    
+        if (!ok) return false;
+        testAllClauseAttach();
+
         XorFinder xorFinder(*this, binaryClauses, ClauseCleaner::binaryClauses);
-        if (xorFinder.doNoPart(2, 2) == false)
-            return l_False;
+        if (!xorFinder.doNoPart(2, 2)) return false;
+        testAllClauseAttach();
         
         lastNbBin = nbBin;
         becameBinary = 0;
     }
-
+    
     // Remove satisfied clauses:
     clauseCleaner->removeAndCleanAll();
-    if (ok == false)
-        return l_False;
-    if (performReplace && varReplacer->performReplace() == false)
-        return l_False;
+    testAllClauseAttach();
+    if (!ok) return false;
+    
+    if (performReplace && !varReplacer->performReplace())
+        return false;
 
     // Remove fixed variables from the variable heap:
     order_heap.filter(VarFilter(*this));
 
+    #ifdef USE_GAUSS
+    for (vector<Gaussian*>::iterator gauss = gauss_matrixes.begin(), end = gauss_matrixes.end(); gauss != end; gauss++) {
+        if (!(*gauss)->full_init()) return false;
+    }
+    #endif //USE_GAUSS
+    
     simpDB_assigns = nAssigns();
     simpDB_props   = clauses_literals + learnts_literals;   // (shouldn't depend on stats really, but it will do for now)
 
-    return l_Undef;
+    testAllClauseAttach();
+    return true;
 }
 
 
@@ -1490,12 +1753,14 @@ lbool Solver::search(int nof_conflicts, int nof_conflicts_fullrestart, const boo
         dynStarts++;
     
     #ifdef USE_GAUSS
-    for (vector<Gaussian*>::iterator gauss = gauss_matrixes.begin(), end= gauss_matrixes.end(); gauss != end; gauss++) {
-        ret = (*gauss)->full_init();
-        if (ret != l_Nothing) return ret;
+    for (vector<Gaussian*>::iterator gauss = gauss_matrixes.begin(), end = gauss_matrixes.end(); gauss != end; gauss++) {
+        if (!(*gauss)->full_init())
+            return l_False;
     }
     #endif //USE_GAUSS
 
+    testAllClauseAttach();
+    findAllAttach();
     for (;;) {
         Clause* confl = propagate(update);
 
@@ -1562,7 +1827,7 @@ llbool Solver::new_decision(const int& nof_conflicts, const int& nof_conflicts_f
         assert(false);
         break;
     }
-    if (nof_conflicts_fullrestart >= 0 && conflicts >= nof_conflicts_fullrestart)  {
+    if (nof_conflicts_fullrestart >= 0 && (int)conflicts >= nof_conflicts_fullrestart)  {
         #ifdef STATS_NEEDED
         if (dynamic_behaviour_analysis)
             progress_estimate = progressEstimate();
@@ -1572,7 +1837,7 @@ llbool Solver::new_decision(const int& nof_conflicts, const int& nof_conflicts_f
     }
 
     // Simplify the set of problem clauses:
-    if (decisionLevel() == 0 && simplify() == l_False) {
+    if (decisionLevel() == 0 && !simplify()) {
         return l_False;
     }
 
@@ -1626,7 +1891,7 @@ llbool Solver::handle_conflict(vec<Lit>& learnt_clause, Clause* confl, int& conf
     #endif
     
     int backtrack_level;
-    int nbLevels;
+    uint32_t nbLevels;
 
     conflicts++;
     conflictC++;
@@ -1635,9 +1900,12 @@ llbool Solver::handle_conflict(vec<Lit>& learnt_clause, Clause* confl, int& conf
     learnt_clause.clear();
     Clause* c = analyze(confl, learnt_clause, backtrack_level, nbLevels, update);
     if (update) {
+        #ifdef RANDOM_LOOKAROUND_SEARCHSPACE
         avgBranchDepth.push(decisionLevel());
+        #endif //RANDOM_LOOKAROUND_SEARCHSPACE
         if (restartType == dynamic_restart)
             nbDecisionLevelHistory.push(nbLevels);
+
         totalSumOfDecisionLevel += nbLevels;
     } else {
         conflictsAtLastSolve++;
@@ -1669,11 +1937,15 @@ llbool Solver::handle_conflict(vec<Lit>& learnt_clause, Clause* confl, int& conf
     } else {
         if (c) {
             detachClause(*c);
-            for (uint i = 0; i != learnt_clause.size(); i++)
+            for (uint32_t i = 0; i != learnt_clause.size(); i++)
                 (*c)[i] = learnt_clause[i];
             c->resize(learnt_clause.size());
-            if (c->learnt() && c->activity() > nbLevels)
-                c->setActivity(nbLevels); // LS
+            if (c->learnt()) {
+                if (c->activity() > nbLevels)
+                    c->setActivity(nbLevels); // LS
+                if (c->size() == 2)
+                    nbBin++;
+            }
             c->setStrenghtened();
         } else {
             c = Clause_new(learnt_clause, learnt_clause_group++, true);
@@ -1715,9 +1987,9 @@ double Solver::progressEstimate() const
 }
 
 #ifdef USE_GAUSS
-void Solver::print_gauss_sum_stats() const
+void Solver::print_gauss_sum_stats()
 {
-    if (gauss_matrixes.size() == 0) {
+    if (gauss_matrixes.size() == 0 && verbosity >= 2) {
         printf("  no matrixes found |\n");
         return;
     }
@@ -1731,21 +2003,27 @@ void Solver::print_gauss_sum_stats() const
         called += (*gauss)->get_called();
         useful_prop += (*gauss)->get_useful_prop();
         useful_confl += (*gauss)->get_useful_confl();
+        sum_gauss_unit_truths += (*gauss)->get_unit_truths();
         //gauss->print_stats();
         //gauss->print_matrix_stats();
     }
+    sum_gauss_called += called;
+    sum_gauss_confl += useful_confl;
+    sum_gauss_prop += useful_prop;
     
-    if (called == 0) {
-        printf("      disabled      |\n");
-    } else {
-        printf(" %3.0lf%% |", (double)useful_prop/(double)called*100.0);
-        printf(" %3.0lf%% |", (double)useful_confl/(double)called*100.0);
-        printf(" %3.0lf%% |\n", 100.0-(double)disabled/(double)gauss_matrixes.size()*100.0);
+    if (verbosity >= 2) {
+        if (called == 0) {
+            printf("      disabled      |\n");
+        } else {
+            printf(" %3.0lf%% |", (double)useful_prop/(double)called*100.0);
+            printf(" %3.0lf%% |", (double)useful_confl/(double)called*100.0);
+            printf(" %3.0lf%% |\n", 100.0-(double)disabled/(double)gauss_matrixes.size()*100.0);
+        }
     }
 }
 #endif //USE_GAUSS
 
-inline void Solver::chooseRestartType(const uint& lastFullRestart)
+const bool Solver::chooseRestartType(const uint& lastFullRestart)
 {
     uint relativeStart = starts - lastFullRestart;
     
@@ -1761,30 +2039,25 @@ inline void Solver::chooseRestartType(const uint& lastFullRestart)
                 tmp = fixRestartType;
             
             if (tmp == dynamic_restart) {
-                lastSelectedRestartType = dynamic_restart;
                 nbDecisionLevelHistory.fastclear();
                 nbDecisionLevelHistory.initSize(100);
                 if (verbosity >= 2)
                     printf("c |                           Decided on dynamic restart strategy                         |\n");
             } else  {
-                lastSelectedRestartType = static_restart;
                 if (verbosity >= 2)
                     printf("c |                            Decided on static restart strategy                         |\n");
                 
                 #ifdef USE_GAUSS
-                if (gaussconfig.decision_until > 0 && xorclauses.size() > 1 && xorclauses.size() < 20000) {
-                    double time = cpuTime();
-                    MatrixFinder m(*this);
-                    const uint numMatrixes = m.findMatrixes();
-                    if (verbosity >=1)
-                        printf("c |  Finding matrixes :    %4.2lf s (found  %5d)                                |\n", cpuTime()-time, numMatrixes);
-                }
+                if (!matrixFinder->findMatrixes()) return false;
                 #endif //USE_GAUSS
             }
+            lastSelectedRestartType = tmp;
             restartType = tmp;
             restartTypeChooser->reset();
         }
     }
+
+    return true;
 }
 
 inline void Solver::setDefaultRestartType()
@@ -1800,16 +2073,17 @@ inline void Solver::setDefaultRestartType()
     lastSelectedRestartType = restartType;
 }
 
-const lbool Solver::simplifyProblem(const uint32_t numConfls, const uint64_t numProps)
+const lbool Solver::simplifyProblem(const uint32_t numConfls)
 {
-    Heap<VarOrderLt> backup_order_heap(order_heap);
-    vector<bool> backup_polarities = polarity;
-    RestartType backup_restartType= restartType;
-    uint32_t backup_random_var_freq = random_var_freq;
-    vec<uint32_t> backup_activity(activity.size());
-    std::copy(activity.getData(), activity.getDataEnd(), backup_activity.getData());
-    uint32_t backup_var_inc = var_inc;
-    
+    testAllClauseAttach();
+    #ifdef USE_GAUSS
+    bool gauss_was_cleared = (gauss_matrixes.size() == 0);
+    clearGaussMatrixes();
+    #endif //USE_GAUSS
+
+    StateSaver savedState(*this);;
+
+    #ifdef BURST_SEARCH
     if (verbosity >= 2)
         std::cout << "c | " << std::setw(24) << " " 
         << "Simplifying problem for " << std::setw(8) << numConfls << " confls" 
@@ -1817,8 +2091,11 @@ const lbool Solver::simplifyProblem(const uint32_t numConfls, const uint64_t num
     random_var_freq = 1;
     simplifying = true;
     uint64_t origConflicts = conflicts;
+    #endif //BURST_SEARCH
     
     lbool status = l_Undef;
+
+    #ifdef BURST_SEARCH
     restartType = static_restart;
     
     while(status == l_Undef && conflicts-origConflicts < numConfls) {
@@ -1829,44 +2106,37 @@ const lbool Solver::simplifyProblem(const uint32_t numConfls, const uint64_t num
     if (status != l_Undef)
         goto end;
     printRestartStat();
-    
-    if (heuleProcess && xorclauses.size() > 1) {
-        if (!conglomerate->heuleProcessFull()) {
-            status = l_False;
-            goto end;
-        }
-        
-        while (performReplace && varReplacer->needsReplace()) {
-            if (!varReplacer->performReplace()) {
-                status = l_False;
-                goto end;
-            }
-            if (!conglomerate->heuleProcessFull()) {
-                status = l_False;
-                goto end;
-            }
-        }
+    #endif //BURST_SEARCH
+
+    if (doXorSubsumption && !xorSubsumer->simplifyBySubsumption()) {
+        status = l_False;
+        goto end;
     }
-    
-    if (failedVarSearch && !failedVarSearcher->search((nClauses() < 500000 && order_heap.size() < 50000) ? 6000000 : 2000000))  {
+    testAllClauseAttach();
+
+    if (failedVarSearch && !failedVarSearcher->search((nClauses() < 500000 && order_heap.size() < 50000) ? 9000000 : 3000000))  {
         status = l_False;
         goto end;
     }
-    
-    if (doXorSubsumption && xorclauses.size() > 1) {
-        XorSubsumer xsub(*this);
-        if (!xsub.simplifyBySubsumption()) {
-            status = l_False;
-            goto end;
-        }
+    testAllClauseAttach();
+
+    if (regularRemoveUselessBins
+        && !failedVarSearcher->removeUslessBinFull<false>()) {
+        status = l_False;
+        goto end;
     }
-    
-    if (doSubsumption) {
-        if (!subsumer->simplifyBySubsumption()) {
-            status = l_False;
-            goto end;
-        }
+
+    if (regularSubsumeWithNonExistBinaries
+        && !subsumer->subsumeWithBinaries(false)) {
+        status = l_False;
+        goto end;
     }
+
+    if (doSubsumption && !subsumer->simplifyBySubsumption()) {
+        status = l_False;
+        goto end;
+    }
+    testAllClauseAttach();
     
     /*if (findNormalXors && xorclauses.size() > 200 && clauses.size() < MAX_CLAUSENUM_XORFIND/8) {
         XorFinder xorFinder(*this, clauses, ClauseCleaner::clauses);
@@ -1880,24 +2150,27 @@ const lbool Solver::simplifyProblem(const uint32_t numConfls, const uint64_t num
     }
     
 end:
-    random_var_freq = backup_random_var_freq;
+    #ifdef BURST_SEARCH
     if (verbosity >= 2)
         printf("c                                      Simplifying finished                               |\n");
-    
-    var_inc = backup_var_inc;
-    std::copy(backup_activity.getData(), backup_activity.getDataEnd(), activity.getData());
-    order_heap = backup_order_heap;
+    #endif //#ifdef BURST_SEARCH
+
+
+    savedState.restore();
     simplifying = false;
-    order_heap.filter(VarFilter(*this));
-    polarity = backup_polarities;
-    restartType = backup_restartType;
     
+    #ifdef USE_GAUSS
+    if (status == l_Undef && !gauss_was_cleared && !matrixFinder->findMatrixes())
+        status = l_False;
+    #endif //USE_GAUSS
+
+    testAllClauseAttach();
     return status;
 }
 
 const bool Solver::checkFullRestart(int& nof_conflicts, int& nof_conflicts_fullrestart, uint& lastFullRestart)
 {
-    if (nof_conflicts_fullrestart > 0 && conflicts >= nof_conflicts_fullrestart) {
+    if (nof_conflicts_fullrestart > 0 && (int)conflicts >= nof_conflicts_fullrestart) {
         #ifdef USE_GAUSS
         clearGaussMatrixes();
         #endif //USE_GAUSS
@@ -1917,9 +2190,7 @@ const bool Solver::checkFullRestart(int& nof_conflicts, int& nof_conflicts_fullr
         if (doPartHandler && !partHandler->handle())
             return false;
         
-        /*if (calculateDefaultPolarities() == l_False)
-            return false;
-        setDefaultPolarities();*/
+        //calculateDefaultPolarities();
         
         fullStarts++;
     }
@@ -1930,46 +2201,48 @@ const bool Solver::checkFullRestart(int& nof_conflicts, int& nof_conflicts_fullr
 inline void Solver::performStepsBeforeSolve()
 {
     assert(qhead == trail.size());
+    testAllClauseAttach();
+
     if (performReplace && !varReplacer->performReplace()) return;
+
+    if (conflicts == 0 && learnts.size() == 0
+        && noLearntBinaries()) {
+        if (subsumeWithNonExistBinaries && !subsumer->subsumeWithBinaries(true)) return;
+        if (removeUselessBins && !failedVarSearcher->removeUslessBinFull<true>()) return;
+    }
     
-    
+    testAllClauseAttach();
     if (doSubsumption
         && !libraryUsage
         && clauses.size() + binaryClauses.size() + learnts.size() < 4800000
         && !subsumer->simplifyBySubsumption())
         return;
+
+    if (conflicts == 0 && learnts.size() == 0
+        && noLearntBinaries()) {
+        if (subsumeWithNonExistBinaries && !subsumer->subsumeWithBinaries(true)) return;
+        if (removeUselessBins && !failedVarSearcher->removeUslessBinFull<true>()) return;
+    }
     
+    testAllClauseAttach();
     if (findBinaryXors && binaryClauses.size() < MAX_CLAUSENUM_XORFIND) {
         XorFinder xorFinder(*this, binaryClauses, ClauseCleaner::binaryClauses);
         if (!xorFinder.doNoPart(2, 2)) return;
-        
         if (performReplace && !varReplacer->performReplace(true)) return;
     }
     
+    testAllClauseAttach();
     if (findNormalXors && clauses.size() < MAX_CLAUSENUM_XORFIND) {
         XorFinder xorFinder(*this, clauses, ClauseCleaner::clauses);
         if (!xorFinder.doNoPart(3, 7)) return;
     }
-        
+    
     if (xorclauses.size() > 1) {
-        if (heuleProcess) {
-            if (!conglomerate->heuleProcessFull()) return;
-            
-            while (performReplace && varReplacer->needsReplace()) {
-                if (!varReplacer->performReplace()) return;
-                if (!conglomerate->heuleProcessFull()) return;
-            }
-        }
-        
-        if (conglomerateXors && !conglomerate->conglomerateXorsFull())
+        testAllClauseAttach();
+        if (doXorSubsumption && !xorSubsumer->simplifyBySubsumption())
             return;
         
-        if (doXorSubsumption && xorclauses.size() > 1) {
-            XorSubsumer xsub(*this);
-            if (!xsub.simplifyBySubsumption())
-                return;
-        }
-        
+        testAllClauseAttach();
         if (performReplace && !varReplacer->performReplace())
             return;
     }
@@ -2003,20 +2276,20 @@ lbool Solver::solve(const vec<Lit>& assumps)
     setDefaultRestartType();
     totalSumOfDecisionLevel = 0;
     conflictsAtLastSolve = conflicts;
+    #ifdef RANDOM_LOOKAROUND_SEARCHSPACE
     avgBranchDepth.fastclear();
     avgBranchDepth.initSize(500);
-    
-    if (!conglomerate->addRemovedClauses()) return l_False;
+    #endif //RANDOM_LOOKAROUND_SEARCHSPACE
     starts = 0;
 
     assumps.copyTo(assumptions);
 
     int  nof_conflicts = restart_first;
-    int  nof_conflicts_fullrestart = (double)restart_first * (double)FULLRESTART_MULTIPLIER + conflicts;
+    int  nof_conflicts_fullrestart = restart_first * FULLRESTART_MULTIPLIER + conflicts;
     //nof_conflicts_fullrestart = -1;
     uint    lastFullRestart  = starts;
     lbool   status        = l_Undef;
-    uint64_t nextSimplify = 30000 + conflicts;
+    uint64_t nextSimplify = restart_first * SIMPLIFY_MULTIPLIER + conflicts;
     
     if (nClauses() * learntsize_factor < nbclausesbeforereduce) {
         if (nClauses() * learntsize_factor < nbclausesbeforereduce/2)
@@ -2024,22 +2297,26 @@ lbool Solver::solve(const vec<Lit>& assumps)
         else
             nbclausesbeforereduce = (nClauses() * learntsize_factor)/2;
     }
+    testAllClauseAttach();
+    findAllAttach();
     
     if (conflicts == 0) {
         performStepsBeforeSolve();
         if (!ok) return l_False;
     
         printStatHeader();
-        if (calculateDefaultPolarities() == l_False)
-        return l_False;
-        setDefaultPolarities();
     }
+    calculateDefaultPolarities();
     
     // Search:
     while (status == l_Undef && starts < maxRestarts) {
+        #ifdef DEBUG_VARELIM
+        assert(subsumer->checkElimedUnassigned());
+        assert(xorSubsumer->checkElimedUnassigned());
+        #endif //DEBUG_VARELIM
         
         if (schedSimplification && conflicts >= nextSimplify) {
-            status = simplifyProblem(500, 7000000);
+            status = simplifyProblem(500);
             nextSimplify = conflicts * 1.5;
             if (status != l_Undef) break;
         }
@@ -2054,11 +2331,15 @@ lbool Solver::solve(const vec<Lit>& assumps)
         
         status = search(nof_conflicts, nof_conflicts_fullrestart);
         nof_conflicts = (double)nof_conflicts * restart_inc;
+        if (status != l_Undef) break;
         if (!checkFullRestart(nof_conflicts, nof_conflicts_fullrestart, lastFullRestart))
             return l_False;
-        chooseRestartType(lastFullRestart);
+        if (!chooseRestartType(lastFullRestart))
+            return l_False;
+        #ifdef RANDOM_LOOKAROUND_SEARCHSPACE
         //if (avgBranchDepth.isvalid())
         //    std::cout << "avg branch depth:" << avgBranchDepth.getavg() << std::endl;
+        #endif //RANDOM_LOOKAROUND_SEARCHSPACE
     }
     printEndSearchStat();
     
@@ -2085,14 +2366,14 @@ lbool Solver::solve(const vec<Lit>& assumps)
             if (verbosity >= 1)
                 printf("c Greedy unbounding     :%5.2lf s, unbounded: %7d vars\n", cpuTime()-time, unbounded);
         }
-        
+
         partHandler->addSavedState();
         varReplacer->extendModelPossible();
 #ifndef NDEBUG
         //checkSolution();
 #endif
         
-        if (subsumer->getNumElimed() > 0 || conglomerate->needCalcAtFinish()) {
+        if (subsumer->getNumElimed() || xorSubsumer->getNumElimed()) {
 #ifdef VERBOSE_DEBUG
             std::cout << "Solution needs extension. Extending." << std::endl;
 #endif //VERBOSE_DEBUG
@@ -2105,12 +2386,11 @@ lbool Solver::solve(const vec<Lit>& assumps)
             s.conglomerateXors = false;
             s.greedyUnbound = greedyUnbound;
             for (Var var = 0; var < nVars(); var++) {
-                s.newVar(decision_var[var] || subsumer->getVarElimed()[var] || varReplacer->varHasBeenReplaced(var) || conglomerate->getRemovedVars()[var]);
+                s.newVar(decision_var[var] || subsumer->getVarElimed()[var] || varReplacer->varHasBeenReplaced(var) || xorSubsumer->getVarElimed()[var]);
                 
-                assert(!(conglomerate->getRemovedVars()[var] && (decision_var[var] || subsumer->getVarElimed()[var] || varReplacer->varHasBeenReplaced(var))));
+                //assert(!(xorSubsumer->getVarElimed()[var] && (decision_var[var] || subsumer->getVarElimed()[var] || varReplacer->varHasBeenReplaced(var))));
                 
                 if (value(var) != l_Undef) {
-                    assert(!conglomerate->getRemovedVars()[var]);
                     vec<Lit> tmp;
                     tmp.push(Lit(var, value(var) == l_False));
                     s.addClause(tmp);
@@ -2118,7 +2398,7 @@ lbool Solver::solve(const vec<Lit>& assumps)
             }
             varReplacer->extendModelImpossible(s);
             subsumer->extendModel(s);
-            conglomerate->extendModel(s);
+            xorSubsumer->extendModel(s);
             
             status = s.solve();
             if (status != l_True) {
@@ -2198,7 +2478,7 @@ bool Solver::verifyXorClauses(const vec<XorClause*>& cs) const
         XorClause* c2 = XorClause_new(c, c.xor_clause_inverted(), c.getGroup());
         std::sort(c2->getData(), c2->getData()+ c2->size());
         c2->plainPrint();
-        free(c2);
+        clauseFree(c2);
         #endif
         
         for (uint j = 0; j < c.size(); j++) {
@@ -2243,12 +2523,10 @@ void Solver::verifyModel()
 {
     assert(!verifyClauses(clauses));
     assert(!verifyClauses(binaryClauses));
-    
     assert(!verifyXorClauses(xorclauses));
-    assert(!verifyXorClauses(conglomerate->getCalcAtFinish()));
 
     if (verbosity >=1)
-        printf("c Verified %d clauses.\n", clauses.size() + xorclauses.size() + conglomerate->getCalcAtFinish().size());
+        printf("c Verified %d clauses.\n", clauses.size() + xorclauses.size());
 }
 
 
@@ -2282,23 +2560,22 @@ void Solver::printStatHeader() const
     }
 }
 
-void Solver::printRestartStat() const
+void Solver::printRestartStat()
 {
-    #ifdef STATS_NEEDED
-    if (verbosity >= 2 && !(dynamic_behaviour_analysis && logger.statistics_on)) {
-    #else
     if (verbosity >= 2) {
-    #endif
-        printf("c | %9d | %7d %8d %8d | %8d %8d %6.0f |", (int)conflicts, (int)order_heap.size(), (int)nClauses(), (int)clauses_literals, (int)(nbclausesbeforereduce*curRestart+nbCompensateSubsumer), (int)nLearnts(), (double)learnts_literals/nLearnts());
-        #ifdef USE_GAUSS
-        print_gauss_sum_stats();
-        #else //USE_GAUSS
+        printf("c | %9d | %7d %8d %8d | %8d %8d %6.0f |", (int)conflicts, (int)order_heap.size(), (int)(nClauses()-nbBin), (int)clauses_literals, (int)(nbclausesbeforereduce*curRestart+nbCompensateSubsumer), (int)(nLearnts()+nbBin), (double)learnts_literals/(double)(nLearnts()+nbBin));
+    }
+    
+    #ifdef USE_GAUSS
+    print_gauss_sum_stats();
+    #else //USE_GAUSS
+    if (verbosity >= 2) {
         printf("                    |\n");
-        #endif //USE_GAUSS
     }
+    #endif //USE_GAUSS
 }
 
-void Solver::printEndSearchStat() const
+void Solver::printEndSearchStat()
 {
     #ifdef STATS_NEEDED
     if (verbosity >= 1 && !(dynamic_behaviour_analysis && logger.statistics_on)) {
@@ -2314,5 +2591,94 @@ void Solver::printEndSearchStat() const
         }
 }
 
-}; //NAMESPACE MINISAT
+#ifdef DEBUG_ATTACH
+void Solver::testAllClauseAttach() const
+{
+    for (Clause *const*it = clauses.getData(), *const*end = clauses.getDataEnd(); it != end; it++) {
+        const Clause& c = **it;
+        if (c.size() > 2) {
+            assert(findWatchedCl(watches[(~c[0]).toInt()], &c));
+            assert(findWatchedCl(watches[(~c[1]).toInt()], &c));
+        } else {
+            assert(findWatchedBinCl(binwatches[(~c[0]).toInt()], &c));
+            assert(findWatchedBinCl(binwatches[(~c[1]).toInt()], &c));
+        }
+    }
+    
+    for (Clause *const*it = binaryClauses.getData(), *const*end = binaryClauses.getDataEnd(); it != end; it++) {
+        const Clause& c = **it;
+        assert(c.size() == 2);
+        assert(findWatchedBinCl(binwatches[(~c[0]).toInt()], &c));
+        assert(findWatchedBinCl(binwatches[(~c[1]).toInt()], &c));
+    }
+    
+    for (XorClause *const*it = xorclauses.getData(), *const*end = xorclauses.getDataEnd(); it != end; it++) {
+        const XorClause& c = **it;
+        assert(find(xorwatches[c[0].var()], &c));
+        assert(find(xorwatches[c[1].var()], &c));
+        if (assigns[c[0].var()]!=l_Undef || assigns[c[1].var()]!=l_Undef) {
+            for (uint i = 0; i < c.size();i++) {
+                assert(assigns[c[i].var()] != l_Undef);
+            }
+        }
+    }
+}
+
+void Solver::findAllAttach() const
+{
+    for (uint32_t i = 0; i < binwatches.size(); i++) {
+        for (uint32_t i2 = 0; i2 < binwatches[i].size(); i2++) {
+            assert(findClause(binwatches[i][i2].clause));
+        }
+    }
+    for (uint32_t i = 0; i < watches.size(); i++) {
+        for (uint32_t i2 = 0; i2 < watches[i].size(); i2++) {
+            assert(findClause(watches[i][i2].clause));
+        }
+    }
+
+    for (uint32_t i = 0; i < xorwatches.size(); i++) {
+        for (uint32_t i2 = 0; i2 < xorwatches[i].size(); i2++) {
+            assert(findClause(xorwatches[i][i2]));
+        }
+    }
+}
+
+const bool Solver::findClause(XorClause* c) const
+{
+    for (uint32_t i = 0; i < xorclauses.size(); i++) {
+        if (xorclauses[i] == c) return true;
+    }
+    return false;
+}
+
+const bool Solver::findClause(Clause* c) const
+{
+    for (uint32_t i = 0; i < binaryClauses.size(); i++) {
+        if (binaryClauses[i] == c) return true;
+    }
+    for (uint32_t i = 0; i < clauses.size(); i++) {
+        if (clauses[i] == c) return true;
+    }
+    for (uint32_t i = 0; i < learnts.size(); i++) {
+        if (learnts[i] == c) return true;
+    }
+    vec<Clause*> cs = varReplacer->getClauses();
+    for (uint32_t i = 0; i < cs.size(); i++) {
+        if (cs[i] == c) return true;
+    }
+    
+    return false;
+}
+#endif //DEBUG_ATTACH
 
+const bool Solver::noLearntBinaries() const
+{
+    for (uint32_t i = 0; i < binaryClauses.size(); i++) {
+        if (binaryClauses[i]->learnt()) return false;
+    }
+
+    return true;
+}
+
+}; //NAMESPACE MINISAT
index 7947c8628b126b6afc7346c3eda9d67115a30c28..5f477ab80a2145bb6cbc90c8e253885fd4e66439 100644 (file)
@@ -56,10 +56,13 @@ class FindUndef;
 class ClauseCleaner;
 class FailedVarSearcher;
 class Subsumer;
+class XorSubsumer;
 class PartHandler;
 class RestartTypeChooser;
+class StateSaver;
 
 #ifdef VERBOSE_DEBUG
+#define DEBUG_UNCHECKEDENQUEUE_LEVEL0
 using std::cout;
 using std::endl;
 #endif
@@ -152,6 +155,12 @@ public:
     bool      doVarElim;            // Perform variable elimination
     bool      doSubsume1;           // Perform clause contraction through resolution
     bool      failedVarSearch;      // Should search for failed vars and doulbly propagated vars
+    bool      readdOldLearnts;      // Should re-add old learnts for failed variable searching
+    bool      addExtraBins;         // Should add extra binaries in failed literal probing
+    bool      removeUselessBins;    // Should try to remove useless binary clauses
+    bool      regularRemoveUselessBins; // Should try to remove useless binary clauses regularly
+    bool      subsumeWithNonExistBinaries;
+    bool      regularSubsumeWithNonExistBinaries;
     bool      libraryUsage;         // Set true if not used as a library
     friend class FindUndef;
     bool      greedyUnbound;        //If set, then variables will be greedily unbounded (set to l_Undef)
@@ -159,7 +168,7 @@ public:
     GaussianConfig gaussconfig;
     
 
-    enum { polarity_true = 0, polarity_false = 1, polarity_rnd = 3, polarity_auto = 4, polarity_manual = 5};
+    enum { polarity_true = 0, polarity_false = 1, polarity_rnd = 3, polarity_auto = 4};
 
     // Statistics: (read-only member variable)
     //
@@ -179,13 +188,34 @@ public:
     void dumpSortedLearnts(const char* file, const uint32_t maxSize); // Dumps all learnt clauses (including unitary ones) into the file
     void needLibraryCNFFile(const char* fileName); //creates file in current directory with the filename indicated, and puts all calls from the library into the file.
 
+    #ifdef USE_GAUSS
+    const uint32_t get_sum_gauss_called() const;
+    const uint32_t get_sum_gauss_confl() const;
+    const uint32_t get_sum_gauss_prop() const;
+    const uint32_t get_sum_gauss_unit_truths() const;
+    #endif //USE_GAUSS
+
+    //Printing statistics
+    const uint32_t getNumElimSubsume() const; // Get variable elimination stats from Subsumer
+    const uint32_t getNumElimXorSubsume() const; // Get variable elimination stats from XorSubsumer
+    const uint32_t getNumXorTrees() const; // Get the number of trees built from 2-long XOR-s. This is effectively the number of variables that replace other variables
+    const uint32_t getNumXorTreesCrownSize() const; // Get the number of variables being replaced by other variables
+    const double getTotalTimeSubsumer() const;
+    const double getTotalTimeXorSubsumer() const;
+    
 protected:
     #ifdef USE_GAUSS
-    void print_gauss_sum_stats() const;
+    void print_gauss_sum_stats();
     void clearGaussMatrixes();
     vector<Gaussian*> gauss_matrixes;
-    #endif //USE_GAUSS
+
+    //stats
+    uint32_t sum_gauss_called;
+    uint32_t sum_gauss_confl;
+    uint32_t sum_gauss_prop;
+    uint32_t sum_gauss_unit_truths;
     friend class Gaussian;
+    #endif //USE_GAUSS
     
     template <class T>
     Clause* addClauseInt(T& ps, uint group);
@@ -196,11 +226,11 @@ protected:
     template<class T>
     void    removeWatchedCl(vec<T> &ws, const Clause *c);
     template<class T>
-    bool    findWatchedCl(vec<T>& ws, const Clause *c);
+    bool    findWatchedCl(const vec<T>& ws, const Clause *c) const;
     template<class T>
     void    removeWatchedBinCl(vec<T> &ws, const Clause *c);
     template<class T>
-    bool    findWatchedBinCl(vec<T>& ws, const Clause *c);
+    bool    findWatchedBinCl(const vec<T>& ws, const Clause *c) const;
     
     // Helper structures:
     //
@@ -228,6 +258,8 @@ protected:
     vec<Clause*>        binaryClauses;    // Binary clauses are regularly moved here
     vec<XorClause*>     xorclauses;       // List of problem xor-clauses. Will be freed
     vec<Clause*>        learnts;          // List of learnt clauses.
+    vec<Clause*>        removedLearnts;   // Clauses that have been learnt, then removed
+    vec<XorClause*>     freeLater;        // xor clauses that need to be freed later due to Gauss
     vec<uint32_t>       activity;         // A heuristic measurement of the activity of a variable.
     uint32_t            var_inc;          // Amount to bump next variable with.
     double              cla_inc;          // Amount to bump learnt clause oldActivity with
@@ -236,15 +268,14 @@ protected:
     vec<vec<WatchedBin> >  binwatches;
     vec<lbool>          assigns;          // The current assignments
     vector<bool>        polarity;         // The preferred polarity of each variable.
+    #ifdef USE_OLD_POLARITIES
+    vector<bool>        oldPolarity;      // The polarity before the last setting. Good for unsetting polairties that have been changed since the last conflict
+    #endif //USE_OLD_POLARITIES
     vector<bool>        decision_var;     // Declares if a variable is eligible for selection in the decision heuristic.
     vec<Lit>            trail;            // Assignment stack; stores all assigments made in the order they were made.
     vec<uint32_t>       trail_lim;        // Separator indices for different decision levels in 'trail'.
     vec<ClausePtr>      reason;           // 'reason[var]' is the clause that implied the variables current value, or 'NULL' if none.
     vec<int32_t>        level;            // 'level[var]' contains the level at which the assignment was made.
-    vec<Var>            permDiff;         // LS: permDiff[var] contains the current conflict number... Used to count the number of different decision level variables in learnt clause
-    #ifdef UPDATEVARACTIVITY
-    vec<Lit>            lastDecisionLevel;
-    #endif
     uint64_t            curRestart;
     uint32_t            nbclausesbeforereduce;
     uint32_t            nbCompensateSubsumer; // Number of learnt clauses that subsumed normal clauses last time subs. was executed
@@ -258,7 +289,9 @@ protected:
     bqueue<uint>        nbDecisionLevelHistory; // Set of last decision level in conflict clauses
     double              totalSumOfDecisionLevel;
     uint64_t            conflictsAtLastSolve;
+    #ifdef RANDOM_LOOKAROUND_SEARCHSPACE
     bqueue<uint>        avgBranchDepth; // Avg branch depth
+    #endif //RANDOM_LOOKAROUND_SEARCHSPACE
     MTRand              mtrand;           // random number generaton
     RestartType         restartType;      // Used internally to determine which restart strategy to choose
     RestartType         lastSelectedRestartType; //the last selected restart type
@@ -276,7 +309,15 @@ protected:
     vec<Lit>            analyze_stack;
     vec<Lit>            analyze_toclear;
     vec<Lit>            add_tmp;
-    unsigned long int   MYFLAG;
+
+    
+    uint64_t MYFLAG;
+    template<class T>
+    const uint32_t calcNBLevels(const T& ps);
+    vec<uint64_t> permDiff; // LS: permDiff[var] contains the current conflict number... Used to count the number of different decision level variables in learnt clause
+    #ifdef UPDATEVARACTIVITY
+    vec<Var> lastDecisionLevel;
+    #endif
 
     //Logging
     uint                learnt_clause_group; //the group number of learnt clauses. Incremented at each added learnt clause
@@ -284,17 +325,25 @@ protected:
 
     // Main internal methods:
     //
-    lbool    simplify    ();                                                           // Removes already satisfied clauses.
+    const bool simplify    ();                                                           // Removes already satisfied clauses.
     //int      nbPropagated     (int level);
     void     insertVarOrder   (Var x);                                                 // Insert a variable in the decision order priority queue.
     Lit      pickBranchLit    ();                                                      // Return the next decision variable.
     void     newDecisionLevel ();                                                      // Begins a new decision level.
     void     uncheckedEnqueue (Lit p, ClausePtr from = (Clause*)NULL);                 // Enqueue a literal. Assumes value of literal is undefined.
+    void     uncheckedEnqueueLight (const Lit p);
     bool     enqueue          (Lit p, Clause* from = NULL);                            // Test if fact 'p' contradicts current state, enqueue otherwise.
     Clause*  propagate        (const bool update = true);                         // Perform unit propagation. Returns possibly conflicting clause.
+    Clause*  propagateLight();
+    Clause*  propagateBin();
+    Clause*  propagateBinNoLearnts();
+    template<bool dontCareLearnt>
+    Clause*  propagateBinExcept(const Lit& exceptLit);
+    template<bool dontCareLearnt>
+    Clause*  propagateBinOneLevel();
     Clause*  propagate_xors   (const Lit& p);
     void     cancelUntil      (int level);                                             // Backtrack until a certain level.
-    Clause*  analyze          (Clause* confl, vec<Lit>& out_learnt, int& out_btlevel, int &nblevels, const bool update); // (bt = backtrack)
+    Clause*  analyze          (Clause* confl, vec<Lit>& out_learnt, int& out_btlevel, uint32_t &nblevels, const bool update); // (bt = backtrack)
     void     analyzeFinal     (Lit p, vec<Lit>& out_conflict);                         // COULD THIS BE IMPLEMENTED BY THE ORDINARIY "analyze" BY SOME REASONABLE GENERALIZATION?
     bool     litRedundant     (Lit p, uint32_t abstract_levels);                       // (helper method for 'analyze()')
     lbool    search           (int nof_conflicts, int nof_conflicts_fullrestart, const bool update = true);      // Search for a given number of conflicts.
@@ -321,6 +370,10 @@ protected:
     void     removeClause(T& c);                       // Detach and free a clause.
     bool     locked           (const Clause& c) const; // Returns TRUE if a clause is a reason for some implication in the current state.
     void     reverse_binary_clause(Clause& c) const;   // Binary clauses --- the first Lit has to be true
+    void     testAllClauseAttach() const;
+    void     findAllAttach() const;
+    const bool findClause(XorClause* c) const;
+    const bool findClause(Clause* c) const;
 
     // Misc:
     //
@@ -339,18 +392,21 @@ protected:
     friend class Subsumer;
     friend class XorSubsumer;
     friend class PartHandler;
+    friend class StateSaver;
     Conglomerate* conglomerate;
     VarReplacer* varReplacer;
     ClauseCleaner* clauseCleaner;
     FailedVarSearcher* failedVarSearcher;
     PartHandler* partHandler;
     Subsumer* subsumer;
+    XorSubsumer* xorSubsumer;
     RestartTypeChooser* restartTypeChooser;
-    void chooseRestartType(const uint& lastFullRestart);
+    MatrixFinder* matrixFinder;
+    const bool chooseRestartType(const uint& lastFullRestart);
     void setDefaultRestartType();
     const bool checkFullRestart(int& nof_conflicts, int& nof_conflicts_fullrestart, uint& lastFullRestart);
     void performStepsBeforeSolve();
-    const lbool simplifyProblem(const uint32_t numConfls, const uint64_t numProps);
+    const lbool simplifyProblem(const uint32_t numConfls);
     bool simplifying;
 
     // Debug & etc:
@@ -361,15 +417,16 @@ protected:
     void     checkSolution();
     void     checkLiteralCount();
     void     printStatHeader  () const;
-    void     printRestartStat () const;
-    void     printEndSearchStat() const;
+    void     printRestartStat ();
+    void     printEndSearchStat();
     double   progressEstimate () const; // DELETE THIS ?? IT'S NOT VERY USEFUL ...
+    const bool noLearntBinaries() const;
     
     // Polarity chooser
-    vector<bool> defaultPolarities; //The default polarity to set the var polarity when doing a full restart
-    const lbool  calculateDefaultPolarities(); //Calculates the default polarity for each var, and fills defaultPolarities[] with it
-    bool         defaultPolarity(); //if polarity_mode is not polarity_auto, this returns the default polarity of the variable
-    void         setDefaultPolarities(); //sets the polarity[] to that indicated by defaultPolarities[]
+    void calculateDefaultPolarities(); //Calculates the default polarity for each var, and fills defaultPolarities[] with it
+    bool defaultPolarity(); //if polarity_mode is not polarity_auto, this returns the default polarity of the variable
+    void tallyVotes(const vec<Clause*>& cs, vector<double>& votes) const;
+    void tallyVotes(const vec<XorClause*>& cs, vector<double>& votes) const;
 };
 
 
@@ -425,7 +482,7 @@ inline void Solver::claBumpActivity (Clause& c)
 
 inline void Solver::claDecayActivity()
 {
-    cla_inc *= clause_decay;
+    //cla_inc *= clause_decay;
 }
 
 inline bool     Solver::enqueue         (Lit p, Clause* from)
@@ -534,6 +591,28 @@ inline void     Solver::setVariableName(Var var, char* name)
 {}
 #endif
 
+#ifdef USE_GAUSS
+inline const uint32_t Solver::get_sum_gauss_unit_truths() const
+{
+    return sum_gauss_unit_truths;
+}
+
+inline const uint32_t Solver::get_sum_gauss_called() const
+{
+    return sum_gauss_called;
+}
+
+inline const uint32_t Solver::get_sum_gauss_confl() const
+{
+    return sum_gauss_confl;
+}
+
+inline const uint32_t Solver::get_sum_gauss_prop() const
+{
+    return sum_gauss_prop;
+}
+#endif
+
 inline const uint Solver::get_unitary_learnts_num() const
 {
     if (decisionLevel() > 0)
@@ -558,14 +637,14 @@ inline void Solver::removeWatchedBinCl(vec<T> &ws, const Clause *c) {
     ws.pop();
 }
 template<class T>
-inline bool Solver::findWatchedCl(vec<T>& ws, const Clause *c)
+inline bool Solver::findWatchedCl(const vec<T>& ws, const Clause *c) const
 {
     uint32_t j = 0;
     for (; j < ws.size() && ws[j].clause != c; j++);
     return j < ws.size();
 }
 template<class T>
-inline bool Solver::findWatchedBinCl(vec<T>& ws, const Clause *c)
+inline bool Solver::findWatchedBinCl(const vec<T>& ws, const Clause *c) const
 {
     uint32_t j = 0;
     for (; j < ws.size() && ws[j].clause != c; j++);
@@ -574,8 +653,7 @@ inline bool Solver::findWatchedBinCl(vec<T>& ws, const Clause *c)
 inline void Solver::reverse_binary_clause(Clause& c) const {
     if (c.size() == 2 && value(c[0]) == l_False) {
         assert(value(c[1]) == l_True);
-        Lit tmp = c[0];
-        c[0] =  c[1], c[1] = tmp;
+        std::swap(c[0], c[1]);
     }
 }
 /*inline void Solver::calculate_xor_clause(Clause& c2) const {
@@ -603,7 +681,6 @@ inline void Solver::removeClause(T& c)
     clauseFree(&c);
 }
 
-
 //=================================================================================================
 // Debug + etc:
 
@@ -637,6 +714,23 @@ static inline void check(bool expr)
     assert(expr);
 }
 
+#ifndef DEBUG_ATTACH
+inline void Solver::testAllClauseAttach() const
+{
+    return;
+}
+inline void Solver::findAllAttach() const
+{
+    return;
+}
+#endif //DEBUG_ATTACH
+
+inline void Solver::uncheckedEnqueueLight(const Lit p)
+{
+    assigns [p.var()] = boolToLBool(!p.sign());//lbool(!sign(p));  // <<== abstract but not uttermost effecient
+    trail.push(p);
+}
+
 //=================================================================================================
 
 }; //NAMESPACE MINISAT
index 5c64d7b40e3d296e004a7a31a6ec45b2b10b745c..452097c170ec063da89dd226bbaadd9dcbe66b15 100644 (file)
@@ -30,6 +30,7 @@ OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWA
 #endif //_MSC_VER
 
 #include "Alg.h"
+#include <stdio.h>
 
 namespace MINISAT
 {
@@ -85,10 +86,18 @@ public:
     bool operator <  (const Lit& p) const {
         return x < p.x;     // '<' guarantees that p, ~p are adjacent in the ordering.
     }
-};    
+    inline void print(FILE* outfile = stdout) const
+    {
+        fprintf(outfile,"%s%d", sign() ? "-" : "", var()+1);
+    }
+    inline void printFull(FILE* outfile = stdout) const
+    {
+        fprintf(outfile,"%s%d 0\n", sign() ? "-" : "", var()+1);
+    }
+};
 
-const Lit lit_Undef(var_Undef, false);  // }- Useful special constants.
-const Lit lit_Error(var_Undef, true );  // }
+const Lit lit_Undef(var_Undef, false);  // Useful special constants.
+const Lit lit_Error(var_Undef, true );  //
 
 //=================================================================================================
 // Lifted booleans:
diff --git a/src/sat/cryptominisat2/StateSaver.cpp b/src/sat/cryptominisat2/StateSaver.cpp
new file mode 100644 (file)
index 0000000..ceb5eab
--- /dev/null
@@ -0,0 +1,54 @@
+/***********************************************************************************
+CryptoMiniSat -- Copyright (c) 2009 Mate Soos
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program.  If not, see <http://www.gnu.org/licenses/>.
+**************************************************************************************************/
+
+#include "StateSaver.h"
+
+namespace MINISAT
+{
+using namespace MINISAT;
+
+StateSaver::StateSaver(Solver& _solver) :
+    solver(_solver)
+    , backup_order_heap(Solver::VarOrderLt(solver.activity))
+{
+    //Saving Solver state
+    backup_var_inc = solver.var_inc;
+    backup_activity.growTo(solver.activity.size());
+    std::copy(solver.activity.getData(), solver.activity.getDataEnd(), backup_activity.getData());
+    backup_order_heap = solver.order_heap;
+    backup_polarities = solver.polarity;
+    backup_restartType = solver.restartType;
+    backup_random_var_freq = solver.random_var_freq;
+    backup_propagations = solver.propagations;
+}
+
+void StateSaver::restore()
+{
+    //Restore Solver state
+    solver.var_inc = backup_var_inc;
+    std::copy(backup_activity.getData(), backup_activity.getDataEnd(), solver.activity.getData());
+    solver.order_heap = backup_order_heap;
+    solver.polarity = backup_polarities;
+    solver.restartType = backup_restartType;
+    solver.random_var_freq = backup_random_var_freq;
+    
+    //Finally, clear the order_heap from variables set/non-decisionned
+    solver.order_heap.filter(Solver::VarFilter(solver));
+    solver.propagations = backup_propagations;
+}
+
+}; //NAMESPACE MINISAT
diff --git a/src/sat/cryptominisat2/StateSaver.h b/src/sat/cryptominisat2/StateSaver.h
new file mode 100644 (file)
index 0000000..7d1f1c3
--- /dev/null
@@ -0,0 +1,46 @@
+/***********************************************************************************
+CryptoMiniSat -- Copyright (c) 2009 Mate Soos
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program.  If not, see <http://www.gnu.org/licenses/>.
+**************************************************************************************************/
+
+#ifndef STATESAVER__H
+#define STATESAVER__H
+
+#include "Solver.h"
+
+namespace MINISAT
+{
+using namespace MINISAT;
+
+class StateSaver
+{
+    public:
+        StateSaver(Solver& _solver);
+        void restore();
+
+    private:
+        Solver& solver;
+        Heap<Solver::VarOrderLt> backup_order_heap;
+        vector<bool> backup_polarities;
+        vec<uint32_t> backup_activity;
+        uint32_t backup_var_inc;
+        RestartType backup_restartType;
+        uint32_t backup_random_var_freq;
+        uint64_t backup_propagations;
+};
+
+}; //NAMESPACE MINISAT
+
+#endif //STATESAVER__H
index fff5ddbeff074e81a4bbf2e9ce5c174a81f584ee..f6cda31dbd8192c93b2b5a48e2b84b3b092958b7 100644 (file)
@@ -12,14 +12,12 @@ Substantially modified by: Mate Soos (2010)
 #include <cmath>
 #include <algorithm>
 #include "VarReplacer.h"
-#include "Conglomerate.h"
 #include "XorFinder.h"
 
 #ifdef _MSC_VER
 #define __builtin_prefetch(a,b,c)
 #endif //_MSC_VER
 
-
 //#define VERBOSE_DEBUG
 #ifdef VERBOSE_DEBUG
 #define BIT_MORE_VERBOSITY
@@ -41,8 +39,9 @@ using namespace MINISAT;
 
 Subsumer::Subsumer(Solver& s):
     solver(s)
-    , numCalls(0)
+    , totalTime(0.0)
     , numElimed(0)
+    , numCalls(0)
 {
 };
 
@@ -52,25 +51,29 @@ Subsumer::~Subsumer()
 
 void Subsumer::extendModel(Solver& solver2)
 {
+    assert(checkElimedUnassigned());
     vec<Lit> tmp;
-    typedef map<Var, vector<vector<Lit> > > elimType;
+    typedef map<Var, vector<Clause*> > elimType;
     for (elimType::iterator it = elimedOutVar.begin(), end = elimedOutVar.end(); it != end; it++) {
-        #ifdef VERBOSE_DEBUG
+        #ifndef NDEBUG
         Var var = it->first;
+        #ifdef VERBOSE_DEBUG
         std::cout << "Reinserting elimed var: " << var+1 << std::endl;
         #endif
+        assert(!solver.decision_var[var]);
+        assert(solver.assigns[var] == l_Undef);
+        assert(!solver.order_heap.inHeap(var));
+        #endif
         
-        for (vector<vector<Lit> >::iterator it2 = it->second.begin(), end2 = it->second.end(); it2 != end2; it2++) {
+        for (vector<Clause*>::iterator it2 = it->second.begin(), end2 = it->second.end(); it2 != end2; it2++) {
+            Clause& c = **it2;
             tmp.clear();
-            tmp.growTo(it2->size());
-            std::copy(it2->begin(), it2->end(), tmp.getData());
+            tmp.growTo(c.size());
+            std::copy(c.getData(), c.getDataEnd(), tmp.getData());
             
             #ifdef VERBOSE_DEBUG
             std::cout << "Reinserting Clause: ";
-            for (uint32_t i = 0; i < tmp.size(); i++) {
-                std::cout << (tmp[i].sign() ? "-" : "")<< tmp[i].var()+1 << " ";
-            }
-            std::cout << std::endl;
+            c.plainPrint();
             #endif
             
             solver2.addClause(tmp);
@@ -81,10 +84,13 @@ void Subsumer::extendModel(Solver& solver2)
 
 const bool Subsumer::unEliminate(const Var var)
 {
+    assert(var_elimed[var]);
     vec<Lit> tmp;
-    typedef map<Var, vector<vector<Lit> > > elimType;
+    typedef map<Var, vector<Clause*> > elimType;
     elimType::iterator it = elimedOutVar.find(var);
-    
+
+    //it MUST have been decision var, otherwise we would
+    //never have removed it
     solver.setDecisionVar(var, true);
     var_elimed[var] = false;
     numElimed--;
@@ -96,11 +102,9 @@ const bool Subsumer::unEliminate(const Var var)
     
     FILE* backup_libraryCNFfile = solver.libraryCNFFile;
     solver.libraryCNFFile = NULL;
-    for (vector<vector<Lit> >::iterator it2 = it->second.begin(), end2 = it->second.end(); it2 != end2; it2++) {
-        tmp.clear();
-        tmp.growTo(it2->size());
-        std::copy(it2->begin(), it2->end(), tmp.getData());
-        solver.addClause(tmp);
+    for (vector<Clause*>::iterator it2 = it->second.begin(), end2 = it->second.end(); it2 != end2; it2++) {
+        solver.addClause(**it2);
+        clauseFree(*it2);
     }
     solver.libraryCNFFile = backup_libraryCNFfile;
     elimedOutVar.erase(it);
@@ -139,63 +143,165 @@ bool selfSubset(Clause& A, Clause& B, vec<char>& seen)
     return flip;
 }
 
-// Will put NULL in 'cs' if clause removed.
-uint32_t Subsumer::subsume0(Clause& ps)
+template <>
+inline uint32_t Subsumer::subsume0(Clause& ps, uint32_t abs)
 {
     ps.subsume0Finished();
     ps.unsetVarChanged();
-    uint32_t retIndex = std::numeric_limits<uint32_t>::max();
     #ifdef VERBOSE_DEBUG
-    cout << "subsume0 orig clause:";
+    cout << "subsume0 orig clause: ";
     ps.plainPrint();
     #endif
-    
+    return subsume0Orig(ps, abs);
+}
+
+template <class T>
+inline uint32_t Subsumer::subsume0(T& ps, uint32_t abs)
+{
+    #ifdef VERBOSE_DEBUG
+    cout << "subsume0 orig vec: ";
+    ps[0].print(); std::cout << " ";
+    ps[1].printFull();
+    #endif
+    return subsume0Orig(ps, abs);
+}
+
+// Will put NULL in 'cs' if clause removed.
+template<class T>
+uint32_t Subsumer::subsume0Orig(const T& ps, uint32_t abs)
+{
+    uint32_t retIndex = std::numeric_limits<uint32_t>::max();
     vec<ClauseSimp> subs;
-    findSubsumed(ps, subs);
+    findSubsumed(ps, abs, subs);
     for (uint32_t i = 0; i < subs.size(); i++){
         clauses_subsumed++;
         #ifdef VERBOSE_DEBUG
-        cout << "subsume0 removing:";
+        cout << "-> subsume0 removing:";
         subs[i].clause->plainPrint();
         #endif
         
         Clause* tmp = subs[i].clause;
-        unlinkClause(subs[i]);
-        free(tmp);
         retIndex = subs[i].index;
+        unlinkClause(subs[i]);
+        clauseFree(tmp);
     }
     
     return retIndex;
 }
 
-// Will put NULL in 'cs' if clause removed.
-uint32_t Subsumer::subsume0(Clause& ps, uint32_t abs)
+void Subsumer::subsume0BIN(const Lit lit1, const vec<char>& lits)
 {
-    ps.subsume0Finished();
-    ps.unsetVarChanged();
-    uint32_t retIndex = std::numeric_limits<uint32_t>::max();
-    #ifdef VERBOSE_DEBUG
-    cout << "subsume0 orig clause:";
-    ps.plainPrint();
-    cout << "pointer:" << &ps << endl;
-    #endif
-    
     vec<ClauseSimp> subs;
-    findSubsumed(ps, abs, subs);
+    vec<ClauseSimp> subs2;
+    vec<Lit> subs2Lit;
+
+    vec<ClauseSimp>& cs = occur[lit1.toInt()];
+    for (ClauseSimp *it = cs.getData(), *end = it + cs.size(); it != end; it++){
+        if (it+1 != end)
+            __builtin_prefetch((it+1)->clause, 0, 1);
+        if (it->clause == NULL) continue;
+        Clause& c = *it->clause;
+        bool removed = false;
+        for (uint32_t i = 0; i < c.size(); i++) {
+            if (lits[c[i].toInt()]) {
+                subs.push(*it);
+                removed = true;
+                break;
+            }
+        }
+        if (!removed) {
+            for (uint32_t i = 0; i < c.size(); i++) {
+                if (lits[(~c[i]).toInt()]) {
+                    subs2.push(*it);
+                    subs2Lit.push(c[i]);
+                    break;
+                }
+            }
+        }
+    }
+    
     for (uint32_t i = 0; i < subs.size(); i++){
         clauses_subsumed++;
         #ifdef VERBOSE_DEBUG
-        cout << "subsume0 removing:";
+        cout << "-> subsume0 removing:";
         subs[i].clause->plainPrint();
         #endif
         
         Clause* tmp = subs[i].clause;
-        retIndex = subs[i].index;
         unlinkClause(subs[i]);
-        free(tmp);
+        clauseFree(tmp);
     }
-    
-    return retIndex;
+
+    if (subs2.size() == 0) return;
+    registerIteration(subs2);
+    for (uint32_t j = 0; j < subs2.size(); j++){
+        if (subs2[j].clause == NULL) continue;
+        ClauseSimp c = subs2[j];
+        Clause& cl = *c.clause;
+        #ifdef VERBOSE_DEBUG
+        cout << "-> Strenghtening clause :";
+        cl.plainPrint();
+        #endif
+        unlinkClause(c);
+
+        literals_removed++;
+        cl.strengthen(subs2Lit[j]);
+        Lit *a, *b, *end;
+        for (a = b = cl.getData(), end = a + cl.size();  a != end; a++) {
+            lbool val = solver.value(*a);
+            if (val == l_Undef)
+                *b++ = *a;
+
+            if (val == l_True) {
+                #ifdef VERBOSE_DEBUG
+                std::cout << "--> Clause was satisfied." << std::endl;
+                #endif
+                clauseFree(&cl);
+                goto endS;
+            }
+        }
+        cl.shrink(a-b);
+        cl.setStrenghtened();
+
+        #ifdef VERBOSE_DEBUG
+        cout << "--> Strenghtened clause:";
+        cl.plainPrint();
+        #endif
+
+        if (cl.size() == 0) {
+            solver.ok = false;
+            unregisterIteration(subs2);
+            clauseFree(&cl);
+            return;
+        }
+        if (cl.size() > 2) {
+            cl.calcAbstraction();
+            linkInAlreadyClause(c);
+            clauses[c.index] = c;
+            solver.attachClause(cl);
+            updateClause(c);
+        } else if (cl.size() == 2) {
+            cl.calcAbstraction();
+            solver.attachClause(cl);
+            solver.becameBinary++;
+            addBinaryClauses.push(&cl);
+            //updateClause(c);
+        } else {
+            assert(cl.size() == 1);
+            solver.uncheckedEnqueue(cl[0]);
+            solver.ok = (solver.propagate() == NULL);
+            if (!solver.ok) {
+                unregisterIteration(subs2);
+                return;
+            }
+            #ifdef VERBOSE_DEBUG
+            cout << "--> Found that var " << cl[0].var()+1 << " must be " << std::boolalpha << !cl[0].sign() << endl;
+            #endif
+            clauseFree(&cl);
+        }
+        endS:;
+    }
+    unregisterIteration(subs2);
 }
 
 void Subsumer::unlinkClause(ClauseSimp c, Var elim)
@@ -204,19 +310,18 @@ void Subsumer::unlinkClause(ClauseSimp c, Var elim)
     
     if (elim != var_Undef) {
         assert(!cl.learnt());
-        io_tmp.clear();
-        for (uint32_t i = 0; i < cl.size(); i++)
-            io_tmp.push_back(cl[i]);
-        elimedOutVar[elim].push_back(io_tmp);
+        #ifdef VERBOSE_DEBUG
+        std::cout << "Eliminating clause: "; c.clause->plainPrint();
+        std::cout << "On variable: " << elim+1 << std::endl;
+        #endif //VERBOSE_DEBUG
+        elimedOutVar[elim].push_back(c.clause);
     }
-    
-    if (updateOccur(cl)) {
-        for (uint32_t i = 0; i < cl.size(); i++) {
-            maybeRemove(occur[cl[i].toInt()], &cl);
-            #ifndef TOUCH_LESS
-            touch(cl[i]);
-            #endif
-        }
+
+    for (uint32_t i = 0; i < cl.size(); i++) {
+        maybeRemove(occur[cl[i].toInt()], &cl);
+        #ifndef TOUCH_LESS
+        touch(cl[i]);
+        #endif
     }
     
     solver.detachClause(cl);
@@ -234,23 +339,19 @@ void Subsumer::unlinkClause(ClauseSimp c, Var elim)
     }
     
     // Remove clause from clause touched set:
-    if (updateOccur(cl)) {
-        cl_touched.exclude(c);
-        cl_added.exclude(c);
-    }
+    cl_touched.exclude(c);
+    cl_added.exclude(c);
     
     clauses[c.index].clause = NULL;
 }
 
 void Subsumer::unlinkModifiedClause(vec<Lit>& origClause, ClauseSimp c)
 {
-    if (updateOccur(*c.clause)) {
-        for (uint32_t i = 0; i < origClause.size(); i++) {
-            maybeRemove(occur[origClause[i].toInt()], c.clause);
-            #ifndef TOUCH_LESS
-            touch(origClause[i]);
-            #endif
-        }
+    for (uint32_t i = 0; i < origClause.size(); i++) {
+        maybeRemove(occur[origClause[i].toInt()], c.clause);
+        #ifndef TOUCH_LESS
+        touch(origClause[i]);
+        #endif
     }
     
     solver.detachModifiedClause(origClause[0], origClause[1], origClause.size(), c.clause);
@@ -268,23 +369,19 @@ void Subsumer::unlinkModifiedClause(vec<Lit>& origClause, ClauseSimp c)
     }
     
     // Remove clause from clause touched set:
-    if (updateOccur(*c.clause)) {
-        cl_touched.exclude(c);
-        cl_added.exclude(c);
-    }
+    cl_touched.exclude(c);
+    cl_added.exclude(c);
     
     clauses[c.index].clause = NULL;
 }
 
 void Subsumer::unlinkModifiedClauseNoDetachNoNULL(vec<Lit>& origClause, ClauseSimp c)
 {
-    if (updateOccur(*c.clause)) {
-        for (uint32_t i = 0; i < origClause.size(); i++) {
-            maybeRemove(occur[origClause[i].toInt()], c.clause);
-            #ifndef TOUCH_LESS
-            touch(origClause[i]);
-            #endif
-        }
+    for (uint32_t i = 0; i < origClause.size(); i++) {
+        maybeRemove(occur[origClause[i].toInt()], c.clause);
+        #ifndef TOUCH_LESS
+        touch(origClause[i]);
+        #endif
     }
     
     // Remove from iterator vectors/sets:
@@ -300,10 +397,8 @@ void Subsumer::unlinkModifiedClauseNoDetachNoNULL(vec<Lit>& origClause, ClauseSi
     }
     
     // Remove clause from clause touched set:
-    if (updateOccur(*c.clause)) {
-        cl_touched.exclude(c);
-        cl_added.exclude(c);
-    }
+    cl_touched.exclude(c);
+    cl_added.exclude(c);
 }
 
 void Subsumer::subsume1(ClauseSimp& ps)
@@ -322,7 +417,7 @@ void Subsumer::subsume1(ClauseSimp& ps)
     while (q < Q.size()){
         if (Q[q].clause == NULL) { q++; continue; }
         #ifdef VERBOSE_DEBUG
-        cout << "subsume1 orig clause:";
+        cout << "subsume1 with clause:";
         Q[q].clause->plainPrint();
         #endif
         
@@ -350,10 +445,10 @@ void Subsumer::subsume1(ClauseSimp& ps)
                 ClauseSimp c = subs[j];
                 Clause& cl = *c.clause;
                 #ifdef VERBOSE_DEBUG
-                cout << "orig clause    :";
+                cout << "-> Strenghtening clause :";
                 cl.plainPrint();
                 #endif
-                unlinkClause(subs[j]);
+                unlinkClause(c);
                 
                 literals_removed++;
                 cl.strengthen(qs[i]);
@@ -364,7 +459,10 @@ void Subsumer::subsume1(ClauseSimp& ps)
                         *b++ = *a;
                     
                     if (val == l_True) {
-                        free(&cl);
+                        #ifdef VERBOSE_DEBUG
+                        std::cout << "--> Clause was satisfied." << std::endl;
+                        #endif
+                        clauseFree(&cl);
                         goto endS;
                     }
                 }
@@ -372,15 +470,15 @@ void Subsumer::subsume1(ClauseSimp& ps)
                 cl.setStrenghtened();
                 
                 #ifdef VERBOSE_DEBUG
-                cout << "strenghtened   :";
-                c.clause->plainPrint();
+                cout << "--> Strenghtened clause:";
+                cl.plainPrint();
                 #endif
                 
                 if (cl.size() == 0) {
                     solver.ok = false;
                     unregisterIteration(Q);
                     unregisterIteration(subs);
-                    free(&cl);
+                    clauseFree(&cl);
                     return;
                 }
                 if (cl.size() > 1) {
@@ -401,9 +499,9 @@ void Subsumer::subsume1(ClauseSimp& ps)
                         return;
                     }
                     #ifdef VERBOSE_DEBUG
-                    cout << "Found that var " << cl[0].var()+1 << " must be " << std::boolalpha << !cl[0].sign() << endl;
+                    cout << "--> Found that var " << cl[0].var()+1 << " must be " << std::boolalpha << !cl[0].sign() << endl;
                     #endif
-                    free(&cl);
+                    clauseFree(&cl);
                 }
                 endS:;
             }
@@ -418,9 +516,106 @@ void Subsumer::subsume1(ClauseSimp& ps)
     unregisterIteration(subs);
 }
 
+template<class T>
+void Subsumer::subsume1Partial(const T& ps)
+{
+    assert(solver.decisionLevel() == 0);
+    registerIteration(subsume1PartialSubs);
+    
+    #ifdef VERBOSE_DEBUG
+    cout << "-> Strenghtening using clause :";
+    ps[0].print(); std::cout << " ";
+    ps[1].printFull();
+    #endif
+
+    assert(ps.size() == 2);
+    subsume1PartialQs.clear();
+    for (uint8_t i = 0; i < 2; i++)
+        subsume1PartialQs.push(ps[i]);
+
+    for (uint8_t i = 0; i < 2; i++){
+        subsume1PartialQs[i] = ~subsume1PartialQs[i];
+
+        uint32_t abst = calcAbstraction(subsume1PartialQs);
+
+        findSubsumed(subsume1PartialQs, abst, subsume1PartialSubs);
+        for (uint32_t j = 0; j < subsume1PartialSubs.size(); j++){
+            if (subsume1PartialSubs[j].clause == NULL) continue;
+            ClauseSimp c = subsume1PartialSubs[j];
+            Clause& cl = *c.clause;
+            #ifdef VERBOSE_DEBUG
+            cout << "-> Strenghtening clause :";
+            cl.plainPrint();
+            #endif
+            unlinkClause(subsume1PartialSubs[j]);
+
+            literals_removed++;
+            cl.strengthen(subsume1PartialQs[i]);
+            Lit *a, *b, *end;
+            for (a = b = cl.getData(), end = a + cl.size();  a != end; a++) {
+                lbool val = solver.value(*a);
+                if (val == l_Undef)
+                    *b++ = *a;
+
+                if (val == l_True) {
+                    #ifdef VERBOSE_DEBUG
+                    std::cout << "--> Clause was satisfied." << std::endl;
+                    #endif
+                    clauseFree(&cl);
+                    goto endS;
+                }
+            }
+            cl.shrink(a-b);
+            cl.setStrenghtened();
+
+            #ifdef VERBOSE_DEBUG
+            cout << "--> Strenghtened clause:";
+            cl.plainPrint();
+            #endif
+
+            if (cl.size() == 0) {
+                solver.ok = false;
+                unregisterIteration(subsume1PartialSubs);
+                clauseFree(&cl);
+                return;
+            }
+            if (cl.size() > 2) {
+                cl.calcAbstraction();
+                linkInAlreadyClause(c);
+                clauses[c.index] = c;
+                solver.attachClause(cl);
+                updateClause(c);
+            } else if (cl.size() == 2) {
+                cl.calcAbstraction();
+                solver.attachClause(cl);
+                solver.becameBinary++;
+                addBinaryClauses.push(&cl);
+                //updateClause(c);
+            } else {
+                assert(cl.size() == 1);
+                solver.uncheckedEnqueue(cl[0]);
+                solver.ok = (solver.propagate() == NULL);
+                if (!solver.ok) {
+                    unregisterIteration(subsume1PartialSubs);
+                    return;
+                }
+                #ifdef VERBOSE_DEBUG
+                cout << "--> Found that var " << cl[0].var()+1 << " must be " << std::boolalpha << !cl[0].sign() << endl;
+                #endif
+                clauseFree(&cl);
+            }
+            endS:;
+        }
+
+        subsume1PartialQs[i] = ~subsume1PartialQs[i];
+        subsume1PartialSubs.clear();
+    }
+    unregisterIteration(subsume1PartialSubs);
+}
+
 void Subsumer::updateClause(ClauseSimp c)
 {
-    if (!c.clause->learnt()) subsume0(*c.clause);
+    if (!c.clause->learnt()) subsume0(*c.clause, c.clause->getAbst());
     
     cl_touched.add(c);
 }
@@ -436,7 +631,7 @@ void Subsumer::almost_all_database()
     
     for (uint32_t i = 0; i < clauses.size(); i++) {
         if (numMaxSubsume1 == 0) break;
-        if (clauses[i].clause != NULL && updateOccur(*clauses[i].clause)) {
+        if (clauses[i].clause != NULL) {
             subsume1(clauses[i]);
             numMaxSubsume1--;
             if (!solver.ok) return;
@@ -579,7 +774,7 @@ void Subsumer::smaller_database()
     // Iteration pass for 0-subsumption:
     for (CSet::iterator it = s0.begin(), end = s0.end(); it != end; ++it) {
         if (it->clause != NULL)
-            subsume0(*it->clause);
+            subsume0(*it->clause, it->clause->getAbst());
     }
     s0.clear();
     unregisterIteration(s0);
@@ -589,11 +784,9 @@ ClauseSimp Subsumer::linkInClause(Clause& cl)
 {
     ClauseSimp c(&cl, clauseID++);
     clauses.push(c);
-    if (updateOccur(cl)) {
-        for (uint32_t i = 0; i < cl.size(); i++) {
-            occur[cl[i].toInt()].push(c);
-            touch(cl[i].var());
-        }
+    for (uint32_t i = 0; i < cl.size(); i++) {
+        occur[cl[i].toInt()].push(c);
+        touch(cl[i].var());
     }
     cl_added.add(c);
     
@@ -603,42 +796,48 @@ ClauseSimp Subsumer::linkInClause(Clause& cl)
 void Subsumer::linkInAlreadyClause(ClauseSimp& c)
 {
     Clause& cl = *c.clause;
-    
-    if (updateOccur(cl)) {
-        for (uint32_t i = 0; i < cl.size(); i++) {
-            occur[cl[i].toInt()].push(c);
-            touch(cl[i].var());
-        }
+    for (uint32_t i = 0; i < cl.size(); i++) {
+        occur[cl[i].toInt()].push(c);
+        touch(cl[i].var());
     }
 }
 
-void Subsumer::addFromSolver(vec<Clause*>& cs)
+template<bool UseCL>
+void Subsumer::addFromSolver(vec<Clause*>& cs, bool alsoLearnt)
 {
     Clause **i = cs.getData();
     Clause **j = i;
     for (Clause **end = i + cs.size(); i !=  end; i++) {
         if (i+1 != end)
             __builtin_prefetch(*(i+1), 1, 1);
-        
-        if ((*i)->learnt()) {
+
+        if (!alsoLearnt && (*i)->learnt()) {
+            *j++ = *i;
+            (*i)->setUnsorted();
+            continue;
+        }
+
+        if (!UseCL && (*i)->size() == 2) {
+            //don't add binary clauses in this case
             *j++ = *i;
             (*i)->setUnsorted();
             continue;
         }
+
         ClauseSimp c(*i, clauseID++);
         clauses.push(c);
         Clause& cl = *c.clause;
-        if (updateOccur(cl)) {
-            for (uint32_t i = 0; i < cl.size(); i++) {
-                occur[cl[i].toInt()].push(c);
-                touch(cl[i].var());
-            }
+        for (uint32_t i = 0; i < cl.size(); i++) {
+            occur[cl[i].toInt()].push(c);
+            touch(cl[i].var());
+        }
+        if (UseCL) {
             if (fullSubsume || cl.getVarChanged()) cl_added.add(c);
             else if (cl.getStrenghtened()) cl_touched.add(c);
-            
-            if (cl.getVarChanged() || cl.getStrenghtened())
-                cl.calcAbstraction();
         }
+
+        if (cl.getVarChanged() || cl.getStrenghtened())
+            cl.calcAbstraction();
     }
     cs.shrink(i-j);
 }
@@ -687,7 +886,7 @@ void Subsumer::removeWrong(vec<Clause*>& cs)
             if (var_elimed[l->var()]) {
                 remove = true;
                 solver.detachClause(c);
-                free(&c);
+                clauseFree(&c);
                 break;
             }
         }
@@ -706,11 +905,6 @@ void Subsumer::fillCannotEliminate()
             cannot_eliminate[c[i2].var()] = true;
     }
     
-    const vec<bool>& tmp2 = solver.conglomerate->getRemovedVars();
-    for (uint32_t i = 0; i < tmp2.size(); i++) {
-        if (tmp2[i]) cannot_eliminate[i] = true;
-    }
-    
     const vec<Clause*>& tmp = solver.varReplacer->getClauses();
     for (uint32_t i = 0; i < tmp.size(); i++) {
         const Clause& c = *tmp[i];
@@ -737,6 +931,7 @@ void Subsumer::subsume0LearntSet(vec<Clause*>& cs)
             uint32_t index = subsume0(**a, calcAbstraction(**a));
             if (index != std::numeric_limits<uint32_t>::max()) {
                 (*a)->makeNonLearnt();
+                //solver.nbBin--;
                 clauses[index].clause = *a;
                 linkInAlreadyClause(clauses[index]);
                 solver.learnts_literals -= (*a)->size();
@@ -749,8 +944,8 @@ void Subsumer::subsume0LearntSet(vec<Clause*>& cs)
                 ((*a)->size() <= 3 && clauses.size() < 300000) ||
                 ((*a)->size() <= 4 && clauses.size() < 60000))) {
                 ClauseSimp c(*a, clauseID++);
-                (*a)->calcAbstraction();
-                clauses.push(c);
+                //(*a)->calcAbstraction();
+                //clauses.push(c);
                 subsume1(c);
                 numMaxSubsume1--;
                 if (!solver.ok) {
@@ -759,8 +954,8 @@ void Subsumer::subsume0LearntSet(vec<Clause*>& cs)
                     cs.shrink(a-b);
                     return;
                 }
-                assert(clauses[c.index].clause != NULL);
-                clauses.pop();
+                //assert(clauses[c.index].clause != NULL);
+                //clauses.pop();
                 clauseID--;
             }
         }
@@ -784,6 +979,189 @@ const bool Subsumer::treatLearnts()
     return true;
 }
 
+const bool Subsumer::subsumeWithBinaries(const bool startUp)
+{
+    clearAll();
+    clauseID = 0;
+    fullSubsume = true;
+    addBinaryClauses.clear();
+
+    //Clearing stats
+    subsNonExistentumFailed = 0;
+    clauses_subsumed = 0;
+    literals_removed = 0;
+    double myTime = cpuTime();
+    uint32_t origTrailSize = solver.trail.size();
+
+    clauses.reserve(solver.clauses.size());
+    solver.clauseCleaner->cleanClauses(solver.clauses, ClauseCleaner::clauses);
+    addFromSolver<false>(solver.clauses);
+    #ifdef DEBUG_BINARIES
+    for (uint32_t i = 0; i < clauses.size(); i++) {
+        assert(clauses[i].clause->size() != 2);
+    }
+    #endif //DEBUG_BINARIES
+
+    for (uint32_t i = 0; i < solver.binaryClauses.size(); i++) {
+        if (startUp || !solver.binaryClauses[i]->learnt()) {
+            Clause& c = *solver.binaryClauses[i];
+            subsume0(c, c.getAbst());
+        }
+    }
+    for (uint32_t i = 0; i < solver.binaryClauses.size(); i++) {
+        Clause& c = *solver.binaryClauses[i];
+        subsume1Partial(c);
+        if (!solver.ok) return false;
+    }
+    if (solver.verbosity >= 1) {
+        std::cout << "c subs with bin: " << std::setw(8) << clauses_subsumed
+        << "  lits-rem: " << std::setw(9) << literals_removed
+        << "  v-fix: " << std::setw(4) <<solver.trail.size() - origTrailSize
+        << "  time: " << std::setprecision(2) << std::setw(5) <<  cpuTime() - myTime << " s"
+        << "   |" << std::endl;
+    }
+    
+    if (!subsWNonExistBinsFull(startUp)) return false;
+
+    #ifdef DEBUG_BINARIES
+    for (uint32_t i = 0; i < clauses.size(); i++) {
+        assert(clauses[i].clause == NULL || clauses[i].clause->size() != 2);
+    }
+    #endif //DEBUG_BINARIES
+    addBackToSolver();
+    for (uint32_t i = 0; i < addBinaryClauses.size(); i++) {
+        solver.binaryClauses.push(addBinaryClauses[i]);
+    }
+    addBinaryClauses.clear();
+
+    if (solver.verbosity >= 1) {
+        std::cout << "c Subs w/ non-existent bins: " << subsNonExistentNum
+        << " lits-rem: " << subsNonExistentLitsRemoved
+        << " v-fix: " << subsNonExistentumFailed
+        << " done: " << doneNum
+        << " time: " << std::fixed << std::setprecision(2) << std::setw(5) << subsNonExistentTime
+        << std::endl;
+    }
+    totalTime += cpuTime() - myTime;
+    solver.order_heap.filter(Solver::VarFilter(solver));
+
+    return true;
+}
+
+#define MAX_BINARY_PROP 40000000
+
+const bool Subsumer::subsWNonExistBinsFull(const bool startUp)
+{
+    uint32_t oldClausesSubusmed = clauses_subsumed;
+    uint32_t oldLitsRemoved = literals_removed;
+    double myTime = cpuTime();
+    uint64_t oldProps = solver.propagations;
+    uint32_t oldTrailSize = solver.trail.size();
+    uint64_t maxProp = MAX_BINARY_PROP;
+    if (!startUp) maxProp /= 3;
+    ps2.clear();
+    ps2.growTo(2);
+    toVisitAll.growTo(solver.nVars()*2, false);
+
+    doneNum = 0;
+    uint32_t startFrom = solver.mtrand.randInt(solver.order_heap.size());
+    for (uint32_t i = 0; i < solver.order_heap.size(); i++) {
+        Var var = solver.order_heap[(i+startFrom)%solver.order_heap.size()];
+        if (solver.propagations - oldProps > maxProp) break;
+        if (solver.assigns[var] != l_Undef || !solver.decision_var[var]) continue;
+        doneNum++;
+
+        Lit lit(var, true);
+        if (!subsWNonExistBins(lit, startUp)) {
+            if (!solver.ok) return false;
+            solver.cancelUntil(0);
+            solver.uncheckedEnqueue(~lit);
+            solver.ok = (solver.propagate() == NULL);
+            if (!solver.ok) return false;
+            continue;
+        }
+
+        //in the meantime it could have got assigned
+        if (solver.assigns[var] != l_Undef) continue;
+        lit = ~lit;
+        if (!subsWNonExistBins(lit, startUp)) {
+            if (!solver.ok) return false;
+            solver.cancelUntil(0);
+            solver.uncheckedEnqueue(~lit);
+            solver.ok = (solver.propagate() == NULL);
+            if (!solver.ok) return false;
+            continue;
+        }
+    }
+    subsNonExistentNum = clauses_subsumed - oldClausesSubusmed;
+    subsNonExistentTime = cpuTime() - myTime;
+    subsNonExistentumFailed = solver.trail.size() - oldTrailSize;
+    subsNonExistentLitsRemoved = literals_removed - oldLitsRemoved;
+
+    return true;
+}
+
+const bool Subsumer::subsWNonExistBins(const Lit& lit, const bool startUp)
+{
+    #ifdef VERBOSE_DEBUG
+    std::cout << "subsWNonExistBins called with lit "; lit.print();
+    std::cout << " startUp: " << startUp << std::endl;
+    #endif //VERBOSE_DEBUG
+    toVisit.clear();
+    solver.newDecisionLevel();
+    solver.uncheckedEnqueueLight(lit);
+    bool failed;
+    if (startUp) {
+        failed = (solver.propagateBin() != NULL);
+    } else {
+        failed = (solver.propagateBinNoLearnts() != NULL);
+    }
+    if (failed) return false;
+
+    assert(solver.decisionLevel() > 0);
+    for (int c = solver.trail.size()-1; c > (int)solver.trail_lim[0]; c--) {
+        Lit x = solver.trail[c];
+        toVisit.push(x);
+        toVisitAll[x.toInt()] = true;
+    }
+    solver.cancelUntil(0);
+
+    if (toVisit.size() <= 1) {
+        ps2[0] = ~lit;
+        for (Lit *l = toVisit.getData(), *end = toVisit.getDataEnd(); l != end; l++) {
+            ps2[1] = *l;
+            assert(ps2[0] != ps2[1]);
+            #ifdef VERBOSE_DEBUG
+            std::cout << "Non-existent bin. lit1: "; ps2[0].print();
+            std::cout << " lit2: "; ps2[1].print(); std::cout << std::endl;
+            #endif //VERBOSE_DEBUG
+            subsume0(ps2, calcAbstraction(ps2));
+            subsume1Partial(ps2);
+        }
+    } else {
+        subsume0BIN(~lit, toVisitAll);
+    }
+    for (uint32_t i = 0; i < toVisit.size(); i++)
+        toVisitAll[toVisit[i].toInt()] = false;
+
+    return true;
+}
+
+void Subsumer::clearAll()
+{
+    touched_list.clear();
+    touched.clear();
+    touched.growTo(solver.nVars(), false);
+    for (Var var = 0; var < solver.nVars(); var++) {
+        if (solver.decision_var[var] && solver.assigns[var] == l_Undef) touch(var);
+        occur[2*var].clear();
+        occur[2*var+1].clear();
+    }
+    clauses.clear();
+    cl_added.clear();
+    cl_touched.clear();
+}
+
 const bool Subsumer::simplifyBySubsumption()
 {
     if (solver.nClauses() > 20000000)  return true;
@@ -797,26 +1175,15 @@ const bool Subsumer::simplifyBySubsumption()
     clauseID = 0;
     numVarsElimed = 0;
     blockTime = 0.0;
+    clearAll();
     
     //if (solver.xorclauses.size() < 30000 && solver.clauses.size() < MAX_CLAUSENUM_XORFIND/10) addAllXorAsNorm();
-    
-    //For VE
-    touched_list.clear();
-    touched.clear();
-    touched.growTo(solver.nVars(), false);
-    for (Var var = 0; var < solver.nVars(); var++) {
-        if (solver.decision_var[var] && solver.assigns[var] == l_Undef) touch(var);
-        occur[2*var].clear();
-        occur[2*var+1].clear();
-    }
-    
+
+    solver.testAllClauseAttach();
     if (solver.performReplace && !solver.varReplacer->performReplace(true))
         return false;
     fillCannotEliminate();
-    
-    clauses.clear();
-    cl_added.clear();
-    cl_touched.clear();
+    solver.testAllClauseAttach();
     
     clauses.reserve(solver.clauses.size() + solver.binaryClauses.size());
     cl_added.reserve(solver.clauses.size() + solver.binaryClauses.size());
@@ -828,41 +1195,40 @@ const bool Subsumer::simplifyBySubsumption()
         fullSubsume = false;
     
     solver.clauseCleaner->cleanClauses(solver.clauses, ClauseCleaner::clauses);
-    addFromSolver(solver.clauses);
-    solver.clauseCleaner->cleanClauses(solver.binaryClauses, ClauseCleaner::binaryClauses);
-    addFromSolver(solver.binaryClauses);
+    addFromSolver<true>(solver.clauses);
+    solver.clauseCleaner->removeSatisfied(solver.binaryClauses, ClauseCleaner::binaryClauses);
+    addFromSolver<true>(solver.binaryClauses);
     
     //Limits
-    if (clauses.size() > 3500000)
+    if (clauses.size() > 3500000) {
         numMaxSubsume0 = 900000 * (1+numCalls/2);
-    else
-        numMaxSubsume0 = 2000000 * (1+numCalls/2);
-    
-    if (solver.doSubsume1) {
-        if (clauses.size() > 3500000)
-            numMaxSubsume1 = 100000 * (1+numCalls/2);
-        else
-            numMaxSubsume1 = 500000 * (1+numCalls/2);
-    } else {
-        numMaxSubsume1 = 0;
-    }
-    
-    if (clauses.size() > 3500000)
         numMaxElim = (uint32_t)((double)solver.order_heap.size() / 5.0 * (0.8+(double)(numCalls)/4.0));
-    else
-        numMaxElim = (uint32_t)((double)solver.order_heap.size() / 2.0 * (0.8+(double)(numCalls)/4.0));
-    
-    if (clauses.size() > 3500000)
+        numMaxSubsume1 = 100000 * (1+numCalls/2);
         numMaxBlockToVisit = (int64_t)(30000.0 * (0.8+(double)(numCalls)/3.0));
-    else
+    }
+    if (clauses.size() <= 3500000 && clauses.size() > 1500000) {
+        numMaxSubsume0 = 2000000 * (1+numCalls/2);
+        numMaxElim = (uint32_t)((double)solver.order_heap.size() / 2.0 * (0.8+(double)(numCalls)/4.0));
+        numMaxSubsume1 = 300000 * (1+numCalls/2);
         numMaxBlockToVisit = (int64_t)(50000.0 * (0.8+(double)(numCalls)/3.0));
+    }
+    if (clauses.size() <= 1500000) {
+        numMaxSubsume0 = 4000000 * (1+numCalls/2);
+        numMaxElim = (uint32_t)((double)solver.order_heap.size() / 2.0 * (0.8+(double)(numCalls)/2.0));
+        numMaxSubsume1 = 400000 * (1+numCalls/2);
+        numMaxBlockToVisit = (int64_t)(80000.0 * (0.8+(double)(numCalls)/3.0));
+    }
+    if (numCalls == 1) numMaxSubsume1 = 0;
+    
+    if (!solver.doSubsume1) numMaxSubsume1 = 0;
+        
     
     if (solver.order_heap.size() > 200000)
         numMaxBlockVars = (uint32_t)((double)solver.order_heap.size() / 3.5 * (0.8+(double)(numCalls)/4.0));
     else
         numMaxBlockVars = (uint32_t)((double)solver.order_heap.size() / 1.5 * (0.8+(double)(numCalls)/4.0));
     
-    //For debugging post-c32s-gcdm16-22.cnf --- an instance that is turned SAT to UNSAT if a bug is in the code
+    //For debugging
     //numMaxBlockToVisit = std::numeric_limits<int64_t>::max();
     //numMaxElim = std::numeric_limits<uint32_t>::max();
     //numMaxSubsume0 = std::numeric_limits<uint32_t>::max();
@@ -880,7 +1246,7 @@ const bool Subsumer::simplifyBySubsumption()
             (fullSubsume
             || !clauses[i].clause->subsume0IsFinished())
             ) {
-            subsume0(*clauses[i].clause);
+            subsume0(*clauses[i].clause, clauses[i].clause->getAbst());
             numMaxSubsume0--;
         }
     }
@@ -1002,15 +1368,13 @@ const bool Subsumer::simplifyBySubsumption()
     //vector<char> var_merged = merge();
     removeWrong(solver.learnts);
     removeWrong(solver.binaryClauses);
+    removeAssignedVarsFromEliminated();
     
-    solver.clauseCleaner->cleanClausesBewareNULL(clauses, ClauseCleaner::simpClauses, *this);
-//     if (solver.doHyperBinRes && clauses.size() < 1000000 && numCalls > 1 && !hyperBinRes())
-//         return false;
-//     
-//     solver.ok = (solver.propagate() == NULL);
-//     if (!solver.ok) return false;
-//     solver.clauseCleaner->cleanClausesBewareNULL(clauses, ClauseCleaner::simpClauses, *this);
-    
+    /*solver.clauseCleaner->cleanClausesBewareNULL(clauses, ClauseCleaner::simpClauses, *this);
+    addFromSolver(solver.learnts, true);
+    addFromSolver(solver.binaryClauses, true);
+    if (solver.doHyperBinRes && clauses.size() < 1000000 && numCalls > 1 && !hyperBinRes())
+        return false;*/
     solver.order_heap.filter(Solver::VarFilter(solver));
     
     addBackToSolver();
@@ -1032,75 +1396,30 @@ const bool Subsumer::simplifyBySubsumption()
             << "                                    |" << std::endl;
         }
     }
-    
-    return true;
-}
+    totalTime += cpuTime() - myTime;
 
-void Subsumer::findSubsumed(Clause& ps, vec<ClauseSimp>& out_subsumed)
-{
-    #ifdef VERBOSE_DEBUG
-    cout << "findSubsumed: ";
-    for (uint32_t i = 0; i < ps.size(); i++) {
-        if (ps[i].sign()) printf("-");
-        printf("%d ", ps[i].var() + 1);
-    }
-    printf("0\n");
-    #endif
-    
-    int min_i = 0;
-    for (uint32_t i = 1; i < ps.size(); i++){
-        if (occur[ps[i].toInt()].size() < occur[ps[min_i].toInt()].size())
-            min_i = i;
-    }
-    
-    vec<ClauseSimp>& cs = occur[ps[min_i].toInt()];
-    for (ClauseSimp *it = cs.getData(), *end = it + cs.size(); it != end; it++){
-        if (it+1 != end)
-            __builtin_prefetch((it+1)->clause, 1, 1);
-        
-        if (it->clause != &ps && subsetAbst(ps.getAbst(), it->clause->getAbst()) && ps.size() <= it->clause->size() && subset(ps, *it->clause)) {
-            out_subsumed.push(*it);
-            #ifdef VERBOSE_DEBUG
-            cout << "subsumed: ";
-            it->clause->plainPrint();
-            #endif
-        }
-    }
+    solver.testAllClauseAttach();
+    return true;
 }
 
-void Subsumer::findSubsumed(Clause& ps, uint32_t abs, vec<ClauseSimp>& out_subsumed)
+void Subsumer::removeAssignedVarsFromEliminated()
 {
-    #ifdef VERBOSE_DEBUG
-    cout << "findSubsumed: ";
-    for (uint32_t i = 0; i < ps.size(); i++) {
-        if (ps[i].sign()) printf("-");
-        printf("%d ", ps[i].var() + 1);
-    }
-    printf("0\n");
-    #endif
-    
-    int min_i = 0;
-    for (uint32_t i = 1; i < ps.size(); i++){
-        if (occur[ps[i].toInt()].size() < occur[ps[min_i].toInt()].size())
-            min_i = i;
-    }
-    
-    vec<ClauseSimp>& cs = occur[ps[min_i].toInt()];
-    for (ClauseSimp *it = cs.getData(), *end = it + cs.size(); it != end; it++){
-        if (it+1 != end)
-            __builtin_prefetch((it+1)->clause, 1, 1);
-        
-        if (it->clause != &ps && subsetAbst(abs, it->clause->getAbst()) && ps.size() <= it->clause->size() && subset(ps, *it->clause)) {
-            out_subsumed.push(*it);
-            #ifdef VERBOSE_DEBUG
-            cout << "subsumed: ";
-            it->clause->plainPrint();
-            #endif
+    for (Var var = 0; var < var_elimed.size(); var++) {
+        if (var_elimed[var] && solver.assigns[var] != l_Undef) {
+            var_elimed[var] = false;
+            solver.setDecisionVar(var, true);
+            numElimed--;
+            map<Var, vector<Clause*> >::iterator it = elimedOutVar.find(var);
+            if (it != elimedOutVar.end()) {
+                //TODO memory loss here
+                elimedOutVar.erase(it);
+            }
         }
     }
 }
 
-void Subsumer::findSubsumed(const vec<Lit>& ps, const uint32_t abst, vec<ClauseSimp>& out_subsumed)
+template<class T>
+void Subsumer::findSubsumed(const T& ps, uint32_t abs, vec<ClauseSimp>& out_subsumed)
 {
     #ifdef VERBOSE_DEBUG
     cout << "findSubsumed: ";
@@ -1122,7 +1441,7 @@ void Subsumer::findSubsumed(const vec<Lit>& ps, const uint32_t abst, vec<ClauseS
         if (it+1 != end)
             __builtin_prefetch((it+1)->clause, 1, 1);
         
-        if (subsetAbst(abst, it->clause->getAbst()) && ps.size() <= it->clause->size() && subset(ps, *it->clause)) {
+        if (it->clause != (Clause*)&ps && subsetAbst(abs, it->clause->getAbst()) && ps.size() <= it->clause->size() && subset(ps, *it->clause)) {
             out_subsumed.push(*it);
             #ifdef VERBOSE_DEBUG
             cout << "subsumed: ";
@@ -1146,12 +1465,12 @@ void inline Subsumer::MigrateToPsNs(vec<ClauseSimp>& poss, vec<ClauseSimp>& negs
 void inline Subsumer::DeallocPsNs(vec<ClauseSimp>& ps, vec<ClauseSimp>& ns)
 {
     for (uint32_t i = 0; i < ps.size(); i++) {
-        clauses[ps[i].index].clause = NULL;
-        free(ps[i].clause);
+        //clauses[ps[i].index].clause = NULL;
+        //clauseFree(ps[i].clause);
     }
     for (uint32_t i = 0; i < ns.size(); i++) {
-        clauses[ns[i].index].clause = NULL;
-        free(ns[i].clause);
+        //clauses[ns[i].index].clause = NULL;
+        //clauseFree(ns[i].clause);
     }
 }
 
@@ -1204,7 +1523,7 @@ bool Subsumer::maybeEliminate(const Var x)
     }
     Abort:;
     
-    // Maybe eliminate:
+    //Eliminate:
     if (after_clauses  <= before_clauses) {
         vec<ClauseSimp> ps, ns;
         MigrateToPsNs(poss, negs, ps, ns, x);
@@ -1212,10 +1531,18 @@ bool Subsumer::maybeEliminate(const Var x)
             dummy.clear();
             bool ok = merge(*ps[i].clause, *ns[j].clause, Lit(x, false), Lit(x, true), dummy);
             if (ok){
-                Clause* cl = solver.addClauseInt(dummy, 0);
+                uint32_t group_num = 0;
+                #ifdef STATS_NEEDED
+                group_num = solver.learnt_clause_group++;
+                if (solver.dynamic_behaviour_analysis) {
+                    string name = solver.logger.get_group_name(ps[i].clause->getGroup()) + " " + solver.logger.get_group_name(ns[j].clause->getGroup());
+                    solver.logger.set_group_name(group_num, name);
+                }
+                #endif
+                Clause* cl = solver.addClauseInt(dummy, group_num);
                 if (cl != NULL) {
                     ClauseSimp c = linkInClause(*cl);
-                    subsume0(*cl);
+                    subsume0(*cl, cl->getAbst());
                 }
                 if (!solver.ok) return true;
             }
@@ -1228,14 +1555,14 @@ bool Subsumer::maybeEliminate(const Var x)
     
     Eliminated:
     assert(occur[Lit(x, false).toInt()].size() + occur[Lit(x, true).toInt()].size() == 0);
-    var_elimed[x] = 1;
+    var_elimed[x] = true;
     numElimed++;
     solver.setDecisionVar(x, false);
     return true;
 }
 
 // Returns FALSE if clause is always satisfied ('out_clause' should not be used). 'seen' is assumed to be cleared.
-bool Subsumer::merge(Clause& ps, Clause& qs, Lit without_p, Lit without_q, vec<Lit>& out_clause)
+bool Subsumer::merge(const Clause& ps, const Clause& qs, const Lit without_p, const Lit without_q, vec<Lit>& out_clause)
 {
     for (uint32_t i = 0; i < ps.size(); i++){
         if (ps[i] != without_p){
@@ -1289,45 +1616,39 @@ void Subsumer::orderVarsForElim(vec<Var>& order)
     }
 }
 
-const bool Subsumer::hyperUtility(vec<ClauseSimp>& iter, const Lit lit, BitArray& inside, vec<ClauseSimp>& addToClauses, uint32_t& hyperBinAdded, uint32_t& hyperBinUnitary)
+const bool Subsumer::hyperUtility(vec<ClauseSimp>& iter, const Lit lit, BitArray& inside, vec<Clause*>& addToClauses)
 {
     for (ClauseSimp *it = iter.getData(), *end = it + iter.size() ; it != end; it++) {
         if (it->clause == NULL) continue;
         uint32_t notIn = 0;
-        Lit notInLit = Lit(0,false);
+        Lit notInLit = lit_Undef;
         
-        Clause& cl2 = *it->clause;
-        for (uint32_t i = 0; i < cl2.size(); i++) {
-            if (cl2[i].var() == lit.var()) {
-                notIn = 2;
-                break;
+        Clause& cl = *it->clause;
+        for (uint32_t i = 0; i < cl.size(); i++) {
+            if (cl[i].var() == lit.var() || cl.size() == 2) {
+                goto next;
             }
-            if (!inside[cl2[i].toInt()]) {
+            if (!inside[cl[i].toInt()]) {
                 notIn++;
-                notInLit = cl2[i];
+                if (notIn > 1) goto next;
+                notInLit = cl[i];
             }
-            if (notIn > 1) break;
         }
         
         if (notIn == 0) {
-            if (solver.assigns[lit.var()] == l_Undef) {
-                solver.uncheckedEnqueue(lit);
-                solver.ok = (solver.propagate() == NULL);
-                if (!solver.ok) return false;
-                hyperBinUnitary++;
-            } else if (solver.assigns[lit.var()] != boolToLBool(!lit.sign())) {
-                solver.ok = false;
-                return false;
-            }
+            vec<Lit> lits(1);
+            lits[0] = lit;
+            solver.addClauseInt(lits, cl.getGroup());
+            if (!solver.ok) return false;
         }
         
         if (notIn == 1 && !inside[(~notInLit).toInt()]) {
             vec<Lit> cs(2);
             cs[0] = lit;
             cs[1] = notInLit;
-            Clause *cl3 = Clause_new(cs, 0);
-            uint32_t index = subsume0(*cl3);
-            if (index != std::numeric_limits<uint32_t>::max()) {
+            //uint32_t index = subsume0(cs, calcAbstraction(cs));
+            /*if (index != std::numeric_limits<uint32_t>::max()) {
+                Clause *cl3 = Clause_new(cs, cl.getGroup());
                 ClauseSimp c(cl3, index);
                 addToClauses.push(c);
                 inside.setBit((~notInLit).toInt());
@@ -1335,9 +1656,13 @@ const bool Subsumer::hyperUtility(vec<ClauseSimp>& iter, const Lit lit, BitArray
                 std::cout << "HyperBinRes adding clause: ";
                 cl3->plainPrint();
                 #endif
-                hyperBinAdded++;
-            }
+            } else {*/
+                Clause *cl3 = Clause_new(cs, cl.getGroup());
+                addToClauses.push(cl3);
+                inside.setBit((~notInLit).toInt());
+            //}
         }
+        next:;
     }
     
     return true;
@@ -1350,15 +1675,16 @@ const bool Subsumer::hyperBinRes()
     BitArray inside;
     inside.resize(solver.nVars()*2, 0);
     uint32_t hyperBinAdded = 0;
-    uint32_t hyperBinUnitary = 0;
-    vec<ClauseSimp> addToClauses;
+    uint32_t oldTrailSize = solver.trail.size();
+    vec<Clause*> addToClauses;
+    vec<Lit> addedToInside;
     uint64_t totalClausesChecked = 0;
 
     vec<Var> varsToCheck;
     
-    if (clauses.size() > 100000 || solver.order_heap.size() > 30000) {
+    if (clauses.size() > 500000 || solver.order_heap.size() > 50000) {
         Heap<Solver::VarOrderLt> tmp(solver.order_heap);
-        uint32_t thisTopX = std::min(tmp.size(), 1000U);
+        uint32_t thisTopX = std::min(tmp.size(), 5000U);
         for (uint32_t i = 0; i != thisTopX; i++)
             varsToCheck.push(tmp.removeMin());
     } else {
@@ -1366,29 +1692,38 @@ const bool Subsumer::hyperBinRes()
             varsToCheck.push(i);
     }
     
-    for (Var test = 0; test < 2*varsToCheck.size(); test++) if (solver.assigns[test/2] == l_Undef && solver.decision_var[test/2]) {
-        if (totalClausesChecked > 5000000)
+    for (uint32_t test = 0; test < 2*varsToCheck.size(); test++) if (solver.assigns[test/2] == l_Undef && solver.decision_var[test/2]) {
+        if (totalClausesChecked > 1000000)
             break;
         
         inside.setZero();
+        addToClauses.clear();
+        addedToInside.clear();
+        
         Lit lit(varsToCheck[test/2], test&1);
         #ifdef HYPER_DEBUG
         std::cout << "Resolving with literal:" << (lit.sign() ? "-" : "") << lit.var()+1 << std::endl;
         #endif
-        
-        vec<Lit> addedToInside;
+
+        //fill inside with binary clauses' literals that this lit is in
+        //addedToInside now contains the list
         vec<ClauseSimp>& set = occur[lit.toInt()];
+        totalClausesChecked += occur.size();
         for (ClauseSimp *it = set.getData(), *end = it + set.size() ; it != end; it++) {
             if (it->clause == NULL) continue;
             Clause& cl2 = *it->clause;
             if (cl2.size() > 2) continue;
             assert(cl2[0] == lit || cl2[1] == lit);
             if (cl2[0] == lit) {
-                inside.setBit((~cl2[1]).toInt());
-                addedToInside.push(~cl2[1]);
+                if (!inside[(~cl2[1]).toInt()]) {
+                    inside.setBit((~cl2[1]).toInt());
+                    addedToInside.push(~cl2[1]);
+                }
             } else {
-                inside.setBit((~cl2[0]).toInt());
-                addedToInside.push(~cl2[0]);
+                if (!inside[(~cl2[0]).toInt()]) {
+                    inside.setBit((~cl2[0]).toInt());
+                    addedToInside.push(~cl2[0]);
+                }
             }
         }
         
@@ -1401,33 +1736,30 @@ const bool Subsumer::hyperBinRes()
             totalClausesChecked += sum;
             for (uint32_t add = 0; add < addedToInside.size(); add++) {
                 vec<ClauseSimp>& iter = occur[addedToInside[add].toInt()];
-                if (!hyperUtility(iter, lit, inside, addToClauses, hyperBinAdded, hyperBinUnitary))
+                if (!hyperUtility(iter, lit, inside, addToClauses))
                     return false;
             }
         } else {
             totalClausesChecked += clauses.size();
-            if (!hyperUtility(clauses, lit, inside, addToClauses, hyperBinAdded, hyperBinUnitary))
+            if (!hyperUtility(clauses, lit, inside, addToClauses))
                 return false;
         }
-        
+
+        hyperBinAdded +=  addToClauses.size();
         for (uint32_t i = 0; i < addToClauses.size(); i++) {
-            Clause *c = solver.addClauseInt(*addToClauses[i].clause, 0);
-            free(addToClauses[i].clause);
+            Clause *c = solver.addClauseInt(*addToClauses[i], addToClauses[i]->getGroup());
+            clauseFree(addToClauses[i]);
             if (c != NULL) {
-                ClauseSimp cc(c, addToClauses[i].index);
-                clauses[cc.index] = cc;
-                linkInAlreadyClause(cc);
-                solver.becameBinary++; //since this binary did not exist, and now it exists.
+                ClauseSimp cc = linkInClause(*c);
                 subsume1(cc);
             }
             if (!solver.ok) return false;
         }
-        addToClauses.clear();
     }
     
     if (solver.verbosity >= 1) {
         std::cout << "c |  Hyper-binary res binary added: " << std::setw(5) << hyperBinAdded 
-        << " unitaries: " << std::setw(5) << hyperBinUnitary 
+        << " unitaries: " << std::setw(5) << solver.trail.size() - oldTrailSize  
         << " time: " << std::setprecision(2) << std::setw(5)<< cpuTime() - myTime << " s" 
         << "                  |"  << std::endl;
     }
@@ -1497,17 +1829,6 @@ class varDataStruct
         int negHash;
 };
 
-int hash32shift(int key)
-{
-    key = ~key + (key << 15); // key = (key << 15) - key - 1;
-    key = key ^ (key >> 12);
-    key = key + (key << 2);
-    key = key ^ (key >> 4);
-    key = key * 2057; // key = (key + (key << 3)) + (key << 11);
-    key = key ^ (key >> 16);
-    return key;
-}
-
 void Subsumer::verifyIntegrity()
 {
     vector<uint> occurNum(solver.nVars()*2, 0);
@@ -1631,12 +1952,18 @@ const bool Subsumer::tryOneSetting(const Lit lit, const Lit negLit)
         solver.setDecisionVar(lit.var(), false);
         vec<ClauseSimp> toRemove(occur[lit.toInt()]);
         for (ClauseSimp *it = toRemove.getData(), *end = toRemove.getDataEnd(); it != end; it++) {
+            #ifdef VERBOSE_DEBUG
+            std::cout << "Next varelim because of block clause elim" << std::endl;
+            #endif //VERBOSE_DEBUG
             unlinkClause(*it, lit.var());
             numblockedClauseRemoved++;
         }
         
         vec<ClauseSimp> toRemove2(occur[negLit.toInt()]);
         for (ClauseSimp *it = toRemove2.getData(), *end = toRemove2.getDataEnd(); it != end; it++) {
+            #ifdef VERBOSE_DEBUG
+            std::cout << "Next varelim because of block clause elim" << std::endl;
+            #endif //VERBOSE_DEBUG
             unlinkClause(*it, lit.var());
             numblockedClauseRemoved++;
         }
@@ -1646,7 +1973,31 @@ const bool Subsumer::tryOneSetting(const Lit lit, const Lit negLit)
     return returnVal;
 }
 
-/*vector<char> Subsumer::merge()
+const bool Subsumer::checkElimedUnassigned() const
+{
+    for (uint32_t i = 0; i < var_elimed.size(); i++) {
+        if (var_elimed[i]) {
+            assert(solver.assigns[i] == l_Undef);
+            if (solver.assigns[i] != l_Undef) return false;
+        }
+    }
+
+    return true;
+}
+
+/*
+int hash32shift(int key)
+{
+    key = ~key + (key << 15); // key = (key << 15) - key - 1;
+    key = key ^ (key >> 12);
+    key = key + (key << 2);
+    key = key ^ (key >> 4);
+    key = key * 2057; // key = (key + (key << 3)) + (key << 11);
+    key = key ^ (key >> 16);
+    return key;
+}
+
+vector<char> Subsumer::merge()
 {
     vector<char> var_merged(solver.nVars(), false);
     double myTime = cpuTime();
@@ -1864,7 +2215,7 @@ void Subsumer::reAddPureLitClauses()
 {
     for (Clause **it = pureLitClauseRemoved.getData(), **end = pureLitClauseRemoved.getDataEnd(); it != end; it++) {
         solver.addClause(**it, (*it)->getGroup());
-        free(*it);
+        clauseFree(*it);
         assert(solver.ok);
     }
     pureLitClauseRemoved.clear();
index 2d3e95ae08bb82527057b5031ee7b14ff5fd913d..098faa9e8da1c3799558a931c75eb44864db6764 100644 (file)
@@ -26,21 +26,35 @@ class ClauseCleaner;
 class Subsumer
 {
 public:
-    
+
+    //Construct-destruct
     Subsumer(Solver& S2);
     ~Subsumer();
+
+    //Called from main
     const bool simplifyBySubsumption();
+    const bool subsumeWithBinaries(const bool startUp);
+    void newVar();
+
+    //Used by cleaner
     void unlinkModifiedClause(vec<Lit>& origClause, ClauseSimp c);
     void unlinkModifiedClauseNoDetachNoNULL(vec<Lit>& origClause, ClauseSimp c);
     void unlinkClause(ClauseSimp cc, Var elim = var_Undef);
     ClauseSimp linkInClause(Clause& cl);
     void linkInAlreadyClause(ClauseSimp& c);
     void updateClause(ClauseSimp c);
-    void newVar();
+
+
+    //UnElimination
     void extendModel(Solver& solver2);
     const bool unEliminate(const Var var);
+
+
+    //Get-functions
     const vec<char>& getVarElimed() const;
     const uint32_t getNumElimed() const;
+    const bool checkElimedUnassigned() const;
+    const double getTotalTime() const;
     
 private:
     
@@ -56,17 +70,18 @@ private:
     vec<vec<ClauseSimp> >  occur;          // 'occur[index(lit)]' is a list of constraints containing 'lit'.
     vec<vec<ClauseSimp>* > iter_vecs;      // Vectors currently used for iterations. Removed clauses will be looked up and replaced by 'Clause_NULL'.
     vec<CSet* >            iter_sets;      // Sets currently used for iterations.
-    Solver&                solver;         // The Solver
-    
-    
-    vec<char>              var_elimed;     // 'eliminated[var]' is TRUE if variable has been eliminated.
     vec<char>              cannot_eliminate;//
-    map<Var, vector<vector<Lit> > > elimedOutVar;
+
+    //Global stats
+    Solver& solver;
+    vec<char> var_elimed; //TRUE if var has been eliminated
+    double totalTime;
+    uint32_t numElimed;
+    map<Var, vector<Clause*> > elimedOutVar;
     
     // Temporaries (to reduce allocation overhead):
     //
     vec<char>           seen_tmp;       // (used in various places)
-    vector<Lit>         io_tmp;         // (used for reading/writing clauses from/to disk)
     
     
     //Limits
@@ -78,14 +93,14 @@ private:
     uint32_t numMaxBlockVars;
     
     //Start-up
-    void addFromSolver(vec<Clause*>& cs);
+    template<bool UseCL>
+    void addFromSolver(vec<Clause*>& cs, bool alsoLearnt = false);
     void addBackToSolver();
     void removeWrong(vec<Clause*>& cs);
+    void removeAssignedVarsFromEliminated();
     void fillCannotEliminate();
     const bool treatLearnts();
-    void addAllXorAsNorm();
-    void addXorAsNormal3(XorClause& c);
-    void addXorAsNormal4(XorClause& c);
+    void clearAll();
     
     //Iterations
     void registerIteration  (CSet& iter_set) { iter_sets.push(&iter_set); }
@@ -96,13 +111,14 @@ private:
     // Subsumption:
     void touch(const Var x);
     void touch(const Lit p);
-    bool updateOccur(Clause& c);
-    void findSubsumed(Clause& ps, vec<ClauseSimp>& out_subsumed);
-    void findSubsumed(const vec<Lit>& ps, const uint32_t abst, vec<ClauseSimp>& out_subsumed);
-    void findSubsumed(Clause& ps, uint32_t abs, vec<ClauseSimp>& out_subsumed);
+    template<class T>
+    void findSubsumed(const T& ps, const uint32_t abst, vec<ClauseSimp>& out_subsumed);
     bool isSubsumed(Clause& ps);
-    uint32_t subsume0(Clause& ps);
-    uint32_t subsume0(Clause& ps, uint32_t abs);
+    template<class T>
+    uint32_t subsume0(T& ps, uint32_t abs);
+    template<class T>
+    uint32_t subsume0Orig(const T& ps, uint32_t abs);
+    void subsume0BIN(const Lit lit, const vec<char>& lits);
     void subsume0LearntSet(vec<Clause*>& cs);
     void subsume1(ClauseSimp& ps);
     void smaller_database();
@@ -116,13 +132,30 @@ private:
     bool maybeEliminate(Var x);
     void MigrateToPsNs(vec<ClauseSimp>& poss, vec<ClauseSimp>& negs, vec<ClauseSimp>& ps, vec<ClauseSimp>& ns, const Var x);
     void DeallocPsNs(vec<ClauseSimp>& ps, vec<ClauseSimp>& ns);
-    bool merge(Clause& ps, Clause& qs, Lit without_p, Lit without_q, vec<Lit>& out_clause);
-    
+    bool merge(const Clause& ps, const Clause& qs, const Lit without_p, const Lit without_q, vec<Lit>& out_clause);
+
+    //Subsume with Nonexistent Bins
+    const bool subsWNonExistBinsFull(const bool startUp);
+    const bool subsWNonExistBins(const Lit& lit, const bool startUp);
+    template<class T>
+    void subsume1Partial(const T& ps);
+    uint32_t subsNonExistentNum;
+    uint32_t subsNonExistentumFailed;
+    bool subsNonExistentFinish;
+    double subsNonExistentTime;
+    uint32_t subsNonExistentLitsRemoved;
+    vec<Clause*> addBinaryClauses;
+    uint32_t doneNum;
+    vec<ClauseSimp> subsume1PartialSubs;
+    vec<Lit> subsume1PartialQs;
+    vec<Lit> toVisit;
+    vec<char> toVisitAll;
+    vec<Lit> ps2;
     
     //hyperBinRes
     void addFromSolverAll(vec<Clause*>& cs);
     const bool hyperBinRes();
-    const bool hyperUtility(vec<ClauseSimp>& iter, const Lit lit, BitArray& inside, vec<ClauseSimp>& addToClauses, uint32_t& hyperBinAdded, uint32_t& hyperBinUnitary);
+    const bool hyperUtility(vec<ClauseSimp>& iter, const Lit lit, BitArray& inside, vec<Clause*>& addToClauses);
     
     //merging
     //vector<char> merge();
@@ -163,7 +196,6 @@ private:
     uint32_t numCalls;
     bool fullSubsume;
     uint32_t clauseID;
-    uint32_t numElimed;
 };
 
 template <class T, class T2>
@@ -194,11 +226,6 @@ inline void Subsumer::touch(const Lit p)
     touch(p.var());
 }
 
-inline bool Subsumer::updateOccur(Clause& c)
-{
-    return !c.learnt();
-}
-
 inline bool Subsumer::subsetAbst(uint32_t A, uint32_t B)
 {
     return !(A & ~B);
@@ -244,6 +271,11 @@ inline const uint32_t Subsumer::getNumElimed() const
     return numElimed;
 }
 
+inline const double Subsumer::getTotalTime() const
+{
+    return totalTime;
+}
+
 }; //NAMESPACE MINISAT
 
 #endif //SIMPLIFIER_H
index 93239f9299458ed12f0ac157a522fe567972b05b..8e966d1a5acaa210b2cabd7eba088d7471f17b0a 100644 (file)
@@ -19,7 +19,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #include <iostream>
 #include <iomanip>
 
-#include "Conglomerate.h"
 #include "ClauseCleaner.h"
 #include "PartHandler.h"
 #include "time_mem.h"
@@ -49,8 +48,7 @@ VarReplacer::VarReplacer(Solver& _solver) :
 VarReplacer::~VarReplacer()
 {
     for (uint i = 0; i != clauses.size(); i++)
-        //binaryClausePool.free(clauses[i]);
-        free(clauses[i]);
+        clauseFree(clauses[i]);
 }
 
 const bool VarReplacer::performReplaceInternal()
@@ -76,7 +74,8 @@ const bool VarReplacer::performReplaceInternal()
     #endif //REPLACE_STATISTICS
     
     solver.clauseCleaner->removeAndCleanAll(true);
-    if (solver.ok == false) return false;
+    if (!solver.ok) return false;
+    solver.testAllClauseAttach();
     
     #ifdef VERBOSE_DEBUG
     {
@@ -89,7 +88,7 @@ const bool VarReplacer::performReplaceInternal()
     #endif
     
     Var var = 0;
-    const vec<bool>& removedVars = solver.conglomerate->getRemovedVars();
+    const vec<char>& removedVars = solver.xorSubsumer->getVarElimed();
     const vec<lbool>& removedVars2 = solver.partHandler->getSavedState();
     const vec<char>& removedVars3 = solver.subsumer->getVarElimed();
     for (vector<Lit>::const_iterator it = table.begin(); it != table.end(); it++, var++) {
@@ -119,10 +118,12 @@ const bool VarReplacer::performReplaceInternal()
     
     lastReplacedVars = replacedVars;
     
-    if (!replace_set(solver.clauses)) goto end;
-    if (!replace_set(solver.learnts)) goto end;
-    if (!replace_set(solver.binaryClauses)) goto end;
+    solver.testAllClauseAttach();
+    if (!replace_set(solver.binaryClauses, true)) goto end;
+    if (!replace_set(solver.clauses, false)) goto end;
+    if (!replace_set(solver.learnts, false)) goto end;
     if (!replace_set(solver.xorclauses)) goto end;
+    solver.testAllClauseAttach();
     
 end:
     for (uint i = 0; i != clauses.size(); i++)
@@ -152,6 +153,7 @@ const bool VarReplacer::replace_set(vec<XorClause*>& cs)
         bool changed = false;
         Var origVar1 = c[0].var();
         Var origVar2 = c[1].var();
+        
         for (Lit *l = &c[0], *end2 = l + c.size(); l != end2; l++) {
             Lit newlit = table[l->var()];
             if (newlit.var() != l->var()) {
@@ -164,11 +166,13 @@ const bool VarReplacer::replace_set(vec<XorClause*>& cs)
         }
         
         if (changed && handleUpdatedClause(c, origVar1, origVar2)) {
-            if (solver.ok == false) {
-                for(;r != end; r++) free(*r);
+            if (!solver.ok) {
+                for(;r != end; r++) clauseFree(*r);
                 cs.shrink(r-a);
                 return false;
             }
+            c.setRemoved();
+            solver.freeLater.push(&c);
         } else {
             *a++ = *r;
         }
@@ -181,18 +185,16 @@ const bool VarReplacer::replace_set(vec<XorClause*>& cs)
 const bool VarReplacer::handleUpdatedClause(XorClause& c, const Var origVar1, const Var origVar2)
 {
     uint origSize = c.size();
-    std::sort(c.getData(), c.getData() + c.size());
+    std::sort(c.getData(), c.getDataEnd());
     Lit p;
     uint32_t i, j;
     for (i = j = 0, p = lit_Undef; i != c.size(); i++) {
-        c[i] = c[i].unsign();
-        if (c[i] == p) {
+        if (c[i].var() == p.var()) {
             //added, but easily removed
             j--;
             p = lit_Undef;
             if (!solver.assigns[c[i].var()].isUndef())
                 c.invert(solver.assigns[c[i].var()].getBool());
-            solver.clauses_literals -= 2;
         } else if (solver.assigns[c[i].var()].isUndef()) //just add
             c[j++] = p = c[i];
         else c.invert(solver.assigns[c[i].var()].getBool()); //modify xor_clause_inverted instead of adding
@@ -212,15 +214,14 @@ const bool VarReplacer::handleUpdatedClause(XorClause& c, const Var origVar1, co
         return true;
     case 1:
         solver.detachModifiedClause(origVar1, origVar2, origSize, &c);
-        solver.uncheckedEnqueue(c[0] ^ c.xor_clause_inverted());
+        solver.uncheckedEnqueue(Lit(c[0].var(), c.xor_clause_inverted()));
         solver.ok = (solver.propagate() == NULL);
         return true;
     case 2: {
         solver.detachModifiedClause(origVar1, origVar2, origSize, &c);
-        vec<Lit> ps(2);
-        ps[0] = c[0];
-        ps[1] = c[1];
-        addBinaryXorClause(ps, c.xor_clause_inverted(), c.getGroup(), true);
+        c[0] = c[0].unsign();
+        c[1] = c[1].unsign();
+        addBinaryXorClause(c, c.xor_clause_inverted(), c.getGroup(), true);
         return true;
     }
     default:
@@ -233,7 +234,7 @@ const bool VarReplacer::handleUpdatedClause(XorClause& c, const Var origVar1, co
     return false;
 }
 
-const bool VarReplacer::replace_set(vec<Clause*>& cs)
+const bool VarReplacer::replace_set(vec<Clause*>& cs, const bool binClauses)
 {
     Clause **a = cs.getData();
     Clause **r = a;
@@ -252,13 +253,17 @@ const bool VarReplacer::replace_set(vec<Clause*>& cs)
         }
         
         if (changed && handleUpdatedClause(c, origLit1, origLit2)) {
-            if (solver.ok == false) {
-                for(;r != end; r++) free(*r);
+            if (!solver.ok) {
+                for(;r != end; r++) clauseFree(*r);
                 cs.shrink(r-a);
                 return false;
             }
         } else {
-            *a++ = *r;
+            if (!binClauses && c.size() == 2) {
+                solver.becameBinary++;
+                solver.binaryClauses.push(&c);
+            } else
+                *a++ = *r;
         }
     }
     cs.shrink(r-a);
@@ -322,6 +327,9 @@ const vector<Var> VarReplacer::getReplacingVars() const
 
 void VarReplacer::extendModelPossible() const
 {
+    #ifdef VERBOSE_DEBUG
+    std::cout << "extendModelPossible() called" << std::endl;
+    #endif //VERBOSE_DEBUG
     uint i = 0;
     for (vector<Lit>::const_iterator it = table.begin(); it != table.end(); it++, i++) {
         if (it->var() == i) continue;
@@ -347,6 +355,11 @@ void VarReplacer::extendModelPossible() const
 
 void VarReplacer::extendModelImpossible(Solver& solver2) const
 {
+
+    #ifdef VERBOSE_DEBUG
+    std::cout << "extendModelImpossible() called" << std::endl;
+    #endif //VERBOSE_DEBUG
+    
     vec<Lit> tmpClause;
     uint i = 0;
     for (vector<Lit>::const_iterator it = table.begin(); it != table.end(); it++, i++) {
index 1a6e7b75ca3ecf284ae0dcffcad43a1b5025ac22..6c7abff8ce53813387bc3f798120911031c8b375 100644 (file)
@@ -56,6 +56,7 @@ class VarReplacer
         const uint getNumReplacedVars() const;
         const uint getNumLastReplacedVars() const;
         const uint getNewToReplaceVars() const;
+        const uint32_t getNumTrees() const;
         const vector<Var> getReplacingVars() const;
         const vector<Lit>& getReplaceTable() const;
         const vec<Clause*>& getClauses() const;
@@ -66,7 +67,7 @@ class VarReplacer
     private:
         const bool performReplaceInternal();
         
-        const bool replace_set(vec<Clause*>& set);
+        const bool replace_set(vec<Clause*>& cs, const bool binClauses);
         const bool replace_set(vec<XorClause*>& cs);
         const bool handleUpdatedClause(Clause& c, const Lit origLit1, const Lit origLit2);
         const bool handleUpdatedClause(XorClause& c, const Var origVar1, const Var origVar2);
@@ -142,6 +143,11 @@ inline const bool VarReplacer::replacingVar(const Var var) const
     return (reverseTable.find(var) != reverseTable.end());
 }
 
+inline const uint32_t VarReplacer::getNumTrees() const
+{
+    return reverseTable.size();
+}
+
 }; //NAMESPACE MINISAT
 
 #endif //VARREPLACER_H
index c2186fd1fb7cded6e27a71e57eba21144efc9fdf..53c00db524e462a27369ea3fe84b886e32676e2e 100644 (file)
@@ -54,9 +54,11 @@ const bool XorFinder::doNoPart(const uint minSize, const uint maxSize)
     uint sumLengths = 0;
     double time = cpuTime();
     foundXors = 0;
-    solver.clauseCleaner->cleanClauses(cls, type);
-    if (solver.ok == false)
-        return false;
+    solver.clauseCleaner->cleanClauses(solver.clauses, ClauseCleaner::clauses);
+    if (type == ClauseCleaner::binaryClauses) {
+        solver.clauseCleaner->cleanClauses(solver.binaryClauses, ClauseCleaner::binaryClauses);
+    }
+    if (!solver.ok) return false;
     
     toRemove.clear();
     toRemove.resize(cls.size(), false);
@@ -85,7 +87,7 @@ const bool XorFinder::doNoPart(const uint minSize, const uint maxSize)
             }
             if (!sorted) {
                 solver.detachClause(c);
-                std::sort(c.getData(), c.getData()+c.size());
+                std::sort(c.getData(), c.getDataEnd());
                 solver.attachClause(c);
             }
         } else {
@@ -215,7 +217,7 @@ const bool XorFinder::findXors(uint& sumLengths)
             XorClause* x = XorClause_new(lits, impair, old_group);
             cout << "- Final 2-long xor-clause: ";
             x->plainPrint();
-            free(x);
+            clauseFree(x);
             #endif
             break;
         }
index 8ec71401372586d06a5227f142a36847e8470352..f7e7fe9da33e77a3ee8272a56ffb5bbfd2c748ef 100644 (file)
@@ -17,12 +17,10 @@ Substantially modified by: Mate Soos (2010)
 
 //#define VERBOSE_DEBUG
 #ifdef VERBOSE_DEBUG
+#define VERBOSE_DEBUGSUBSUME0
 #define BIT_MORE_VERBOSITY
 #endif
 
-//#define BIT_MORE_VERBOSITY
-//#define TOUCH_LESS
-
 #ifdef VERBOSE_DEBUG
 using std::cout;
 using std::endl;
@@ -34,17 +32,18 @@ using namespace MINISAT;
 
 XorSubsumer::XorSubsumer(Solver& s):
     solver(s)
+    , totalTime(0.0)
+    , numElimed(0)
+    , localSubstituteUseful(0)
 {
 };
 
 // Will put NULL in 'cs' if clause removed.
 void XorSubsumer::subsume0(XorClauseSimp& ps)
 {
-    assert(solver.xorclauses.size() ==  0);
-    #ifdef VERBOSE_DEBUG
+    #ifdef VERBOSE_DEBUGSUBSUME0
     cout << "subsume0 orig clause:";
     ps.clause->plainPrint();
-    cout << "pointer:" << &ps << endl;
     #endif
     
     vec<Lit> origClause(ps.clause->size());
@@ -57,19 +56,18 @@ void XorSubsumer::subsume0(XorClauseSimp& ps)
     vec<XorClauseSimp> subs;
     findSubsumed(*ps.clause, subs);
     for (uint32_t i = 0; i < subs.size(); i++){
-        #ifdef VERBOSE_DEBUG
-        cout << "subsume0 removing:";
-        subs[i].clause->plainPrint();
-        #endif
-        
         XorClause* tmp = subs[i].clause;
         findUnMatched(origClause, *tmp, unmatchedPart);
         if (unmatchedPart.size() == 0) {
+            #ifdef VERBOSE_DEBUGSUBSUME0
+            cout << "subsume0 removing:";
+            subs[i].clause->plainPrint();
+            #endif
             clauses_subsumed++;
             assert(tmp->size() == origClause.size());
             if (origClauseInverted == tmp->xor_clause_inverted()) {
                 unlinkClause(subs[i]);
-                free(tmp);
+                clauseFree(tmp);
             } else {
                 solver.ok = false;
                 return;
@@ -77,21 +75,25 @@ void XorSubsumer::subsume0(XorClauseSimp& ps)
         } else {
             assert(unmatchedPart.size() > 0);
             clauses_cut++;
-            //XorClause *c = solver.addXorClauseInt(unmatchedPart, tmp->xor_clause_inverted() ^ origClauseInverted, tmp->getGroup());
-            if (!solver.ok) return;
-            //if (c != NULL) {
-                //linkInClause(*c);
+            #ifdef VERBOSE_DEBUG
+            std::cout << "Cutting xor-clause:";
+            subs[i].clause->plainPrint();
+            #endif //VERBOSE_DEBUG
+            XorClause *c = solver.addXorClauseInt(unmatchedPart, tmp->xor_clause_inverted() ^ !origClauseInverted, tmp->getGroup());
+            if (c != NULL) {
+                linkInClause(*c);
                 needUnlinkPS = true;
-            //}
+            }
+            if (!solver.ok) return;
         }
         unmatchedPart.clear();
     }
     
-    /*if (needUnlinkPS) {
+    if (needUnlinkPS) {
         XorClause* tmp = ps.clause;
         unlinkClause(ps);
-        free(tmp);
-    }*/
+        clauseFree(tmp);
+    }
 }
 
 void XorSubsumer::findUnMatched(vec<Lit>& A, XorClause& B, vec<Lit>& unmatchedPart)
@@ -108,7 +110,7 @@ void XorSubsumer::findUnMatched(vec<Lit>& A, XorClause& B, vec<Lit>& unmatchedPa
     }
 }
 
-void XorSubsumer::unlinkClause(XorClauseSimp c)
+void XorSubsumer::unlinkClause(XorClauseSimp c, const Var elim)
 {
     XorClause& cl = *c.clause;
     
@@ -116,6 +118,9 @@ void XorSubsumer::unlinkClause(XorClauseSimp c)
         maybeRemove(occur[cl[i].var()], &cl);
     }
     
+    if (elim != var_Undef)
+        elimedOutVar[elim].push_back(c.clause);
+    
     solver.detachClause(cl);
     
     clauses[c.index].clause = NULL;
@@ -161,6 +166,8 @@ void XorSubsumer::linkInAlreadyClause(XorClauseSimp& c)
 
 void XorSubsumer::addFromSolver(vec<XorClause*>& cs)
 {
+    clauseID = 0;
+    clauses.clear();
     XorClause **i = cs.getData();
     for (XorClause **end = i + cs.size(); i !=  end; i++) {
         if (i+1 != end)
@@ -171,10 +178,12 @@ void XorSubsumer::addFromSolver(vec<XorClause*>& cs)
             (*i)->calcXorAbstraction();
     }
     cs.clear();
+    cs.push(NULL); //HACK --to force xor-propagation
 }
 
 void XorSubsumer::addBackToSolver()
 {
+    solver.xorclauses.pop(); //HACK --to force xor-propagation
     for (uint32_t i = 0; i < clauses.size(); i++) {
         if (clauses[i].clause != NULL) {
             solver.xorclauses.push(clauses[i].clause);
@@ -189,6 +198,236 @@ void XorSubsumer::addBackToSolver()
     clauseID = 0;
 }
 
+void XorSubsumer::fillCannotEliminate()
+{
+    std::fill(cannot_eliminate.getData(), cannot_eliminate.getDataEnd(), false);
+    for (uint32_t i = 0; i < solver.clauses.size(); i++)
+        addToCannotEliminate(solver.clauses[i]);
+
+    for (uint32_t i = 0; i < solver.binaryClauses.size(); i++)
+        if (!(*solver.binaryClauses[i]).learnt()) addToCannotEliminate(solver.binaryClauses[i]);
+    
+    const vec<Clause*>& tmp = solver.varReplacer->getClauses();
+    for (uint32_t i = 0; i < tmp.size(); i++)
+        addToCannotEliminate(tmp[i]);
+    
+    #ifdef VERBOSE_DEBUG
+    uint32_t tmpNum = 0;
+    for (uint32_t i = 0; i < cannot_eliminate.size(); i++)
+        if (cannot_eliminate[i])
+            tmpNum++;
+        std::cout << "Cannot eliminate num:" << tmpNum << std::endl;
+    #endif
+}
+
+void XorSubsumer::extendModel(Solver& solver2)
+{
+    assert(checkElimedUnassigned());
+    vec<Lit> tmp;
+    typedef map<Var, vector<XorClause*> > elimType;
+    for (elimType::iterator it = elimedOutVar.begin(), end = elimedOutVar.end(); it != end; it++) {
+        #ifdef VERBOSE_DEBUG
+        Var var = it->first;
+        std::cout << "Reinserting elimed var: " << var+1 << std::endl;
+        #endif
+        
+        for (vector<XorClause*>::iterator it2 = it->second.begin(), end2 = it->second.end(); it2 != end2; it2++) {
+            XorClause& c = **it2;
+            #ifdef VERBOSE_DEBUG
+            std::cout << "Reinserting Clause: ";
+            c.plainPrint();
+            #endif
+            tmp.clear();
+            tmp.growTo(c.size());
+            std::copy(c.getData(), c.getDataEnd(), tmp.getData());
+            bool inverted = c.xor_clause_inverted();
+            solver2.addXorClause(tmp, inverted);
+            assert(solver2.ok);
+        }
+    }
+}
+
+const bool XorSubsumer::localSubstitute()
+{
+    vec<Lit> tmp;
+    for (Var var = 0; var < occur.size(); var++) {
+        vec<XorClauseSimp>& occ = occur[var];
+
+        if (occ.size() <= 1) continue;
+        for (uint32_t i = 0; i < occ.size(); i++) {
+            XorClause& c1 = *occ[i].clause;
+            for (uint32_t i2 = i+1; i2 < occ.size(); i2++) {
+                XorClause& c2 = *occ[i2].clause;
+                tmp.clear();
+                tmp.growTo(c1.size() + c2.size());
+                std::copy(c1.getData(), c1.getDataEnd(), tmp.getData());
+                std::copy(c2.getData(), c2.getDataEnd(), tmp.getData() + c1.size());
+                clearDouble(tmp);
+                if (tmp.size() <= 2) {
+                    #ifdef VERBOSE_DEBUG
+                    std::cout << "Local substiuting. Clause1:"; c1.plainPrint();
+                    std::cout << "Clause 2:"; c2.plainPrint();
+                    #endif //VERBOSE_DEBUG
+                    localSubstituteUseful++;
+                    uint32_t lastSize = solver.varReplacer->getClauses().size();
+                    solver.addXorClauseInt(tmp, c1.xor_clause_inverted() ^ !c2.xor_clause_inverted(), c1.getGroup());
+                    for (uint32_t i = lastSize; i  < solver.varReplacer->getClauses().size(); i++)
+                        addToCannotEliminate(solver.varReplacer->getClauses()[i]);
+                    if (!solver.ok) {
+                        #ifdef VERBOSE_DEBUG
+                        std::cout << "solver.ok is false after local substitution" << std::endl;
+                        #endif //VERBOSE_DEBUG
+                        return false;
+                    }
+                }
+            }
+        }
+    }
+    
+    return true;
+}
+
+void XorSubsumer::clearDouble(vec<Lit>& ps) const
+{
+    std::sort(ps.getData(), ps.getDataEnd());
+    Lit p;
+    uint32_t i, j;
+    for (i = j = 0, p = lit_Undef; i != ps.size(); i++) {
+        if (ps[i].var() == p.var()) {
+            //added, but easily removed
+            j--;
+            p = lit_Undef;
+        } else
+            ps[j++] = p = ps[i];
+    }
+    ps.shrink(i - j);
+}
+
+void XorSubsumer::removeWrong(vec<Clause*>& cs)
+{
+    Clause **i = cs.getData();
+    Clause **j = i;
+    for (Clause **end =  i + cs.size(); i != end; i++) {
+        Clause& c = **i;
+        if (!c.learnt())  {
+            *j++ = *i;
+            continue;
+        }
+        bool remove = false;
+        for (Lit *l = c.getData(), *end2 = l+c.size(); l != end2; l++) {
+            if (var_elimed[l->var()]) {
+                remove = true;
+                solver.detachClause(c);
+                clauseFree(&c);
+                break;
+            }
+        }
+        if (!remove)
+            *j++ = *i;
+    }
+    cs.shrink(i-j);
+}
+
+
+const bool XorSubsumer::removeDependent()
+{
+    for (Var var = 0; var < occur.size(); var++) {
+        if (cannot_eliminate[var] || !solver.decision_var[var] || solver.assigns[var] != l_Undef) continue;
+        vec<XorClauseSimp>& occ = occur[var];
+
+        if (occ.size() == 1) {
+            #ifdef VERBOSE_DEBUG
+            std::cout << "Eliminating dependent var " << var + 1 << std::endl;
+            std::cout << "-> Removing dependent clause "; occ[0].clause->plainPrint();
+            #endif //VERBOSE_DEBUG
+            unlinkClause(occ[0], var);
+            solver.setDecisionVar(var, false);
+            var_elimed[var] = true;
+            numElimed++;
+        } else if (occ.size() == 2) {
+            vec<Lit> lits;
+            XorClause& c1 = *(occ[0].clause);
+            lits.growTo(c1.size());
+            std::copy(c1.getData(), c1.getDataEnd(), lits.getData());
+            bool inverted = c1.xor_clause_inverted();
+            
+            XorClause& c2 = *(occ[1].clause);
+            lits.growTo(lits.size() + c2.size());
+            std::copy(c2.getData(), c2.getDataEnd(), lits.getData() + c1.size());
+            inverted ^= !c2.xor_clause_inverted();
+            uint32_t group = c2.getGroup();
+
+            #ifdef VERBOSE_DEBUG
+            std::cout << "Eliminating var " << var + 1 << " present in 2 xor-clauses" << std::endl;
+            std::cout << "-> Removing xor clause "; occ[0].clause->plainPrint();
+            std::cout << "-> Removing xor clause "; occ[1].clause->plainPrint();
+            #endif //VERBOSE_DEBUG
+            XorClauseSimp toUnlink0 = occ[0];
+            XorClauseSimp toUnlink1 = occ[1];
+            unlinkClause(toUnlink0);
+            clauseFree(toUnlink0.clause);
+            unlinkClause(toUnlink1, var);
+            solver.setDecisionVar(var, false);
+            var_elimed[var] = true;
+            numElimed++;
+            
+            uint32_t lastSize =  solver.varReplacer->getClauses().size();
+            XorClause* c = solver.addXorClauseInt(lits, inverted, group);
+            #ifdef VERBOSE_DEBUG
+            if (c != NULL) {
+                std::cout << "-> Added combined xor clause:"; c->plainPrint();
+            } else
+                std::cout << "-> Combined xor clause is NULL" << std::endl;
+            #endif
+            if (c != NULL) linkInClause(*c);
+            for (uint32_t i = lastSize; i  < solver.varReplacer->getClauses().size(); i++)
+                addToCannotEliminate(solver.varReplacer->getClauses()[i]);
+            if (!solver.ok) {
+                #ifdef VERBOSE_DEBUG
+                std::cout << "solver.ok is false after var-elim through xor" << std::endl;
+                #endif //VERBOSE_DEBUG
+                return false;
+            }
+        }
+    }
+    
+    return true;
+}
+
+inline void XorSubsumer::addToCannotEliminate(Clause* it)
+{
+    const Clause& c = *it;
+    for (uint32_t i2 = 0; i2 < c.size(); i2++)
+        cannot_eliminate[c[i2].var()] = true;
+}
+
+const bool XorSubsumer::unEliminate(const Var var)
+{
+    assert(var_elimed[var]);
+    typedef map<Var, vector<XorClause*> > elimType;
+    elimType::iterator it = elimedOutVar.find(var);
+
+    //MUST set to decision, since it would never have been eliminated
+    //had it not been decision var
+    solver.setDecisionVar(var, true);
+    var_elimed[var] = false;
+    numElimed--;
+    assert(it != elimedOutVar.end());
+    
+    FILE* backup_libraryCNFfile = solver.libraryCNFFile;
+    solver.libraryCNFFile = NULL;
+    for (vector<XorClause*>::iterator it2 = it->second.begin(), end2 = it->second.end(); it2 != end2; it2++) {
+        XorClause& c = **it2;
+        solver.addXorClause(c, c.xor_clause_inverted());
+        clauseFree(&c);
+    }
+    solver.libraryCNFFile = backup_libraryCNFfile;
+    elimedOutVar.erase(it);
+    
+    return solver.ok;
+}
+
+
 const bool XorSubsumer::simplifyBySubsumption(const bool doFullSubsume)
 {
     double myTime = cpuTime();
@@ -196,19 +435,21 @@ const bool XorSubsumer::simplifyBySubsumption(const bool doFullSubsume)
     clauses_subsumed = 0;
     clauses_cut = 0;
     clauseID = 0;
-    
-    for (Var var = 0; var < solver.nVars(); var++) {
-        //occur[var].clear(true);
-        newVar();
-    }
-    
+    uint32_t lastNumElimed = numElimed;
+    localSubstituteUseful = 0;
     while (solver.performReplace && solver.varReplacer->needsReplace()) {
         if (!solver.varReplacer->performReplace())
             return false;
     }
     
+    for (Var var = 0; var < solver.nVars(); var++) {
+        occur[var].clear();
+    }
+    solver.findAllAttach();
+    
     solver.clauseCleaner->cleanClauses(solver.xorclauses, ClauseCleaner::xorclauses);
     if (!solver.ok) return false;
+    solver.testAllClauseAttach();
     
     clauses.clear();
     clauses.reserve(solver.xorclauses.size());
@@ -231,20 +472,37 @@ const bool XorSubsumer::simplifyBySubsumption(const bool doFullSubsume)
         for (uint32_t i = 0; i < clauses.size(); i++) {
             if (clauses[i].clause != NULL) {
                 subsume0(clauses[i]);
-                if (!solver.ok) return false;
+                if (!solver.ok) {
+                    addBackToSolver();
+                    return false;
+                }
             }
         }
         
-        if (solver.qhead != solver.trail.size()) propagated = true;
-        solver.ok = solver.propagate() == NULL;
+        propagated =  (solver.qhead != solver.trail.size());
+        solver.ok = (solver.propagate() == NULL);
         if (!solver.ok) {
             std::cout << "c (contradiction during subsumption)" << std::endl;
             return false;
         }
         solver.clauseCleaner->cleanXorClausesBewareNULL(clauses, ClauseCleaner::xorSimpClauses, *this);
         if (!solver.ok) return false;
-        
-        if (solver.performReplace && solver.varReplacer->needsReplace()) {
+        testAllClauseAttach();
+
+        fillCannotEliminate();
+        if (solver.conglomerateXors && !removeDependent()) {
+            addBackToSolver();
+            return false;
+        }
+        testAllClauseAttach();
+
+        if (solver.heuleProcess && !localSubstitute()) {
+            addBackToSolver();
+            return false;
+        }
+        testAllClauseAttach();
+
+        /*if (solver.performReplace && solver.varReplacer->needsReplace()) {
             addBackToSolver();
             while (solver.performReplace && solver.varReplacer->needsReplace()) {
                 replaced = true;
@@ -252,28 +510,55 @@ const bool XorSubsumer::simplifyBySubsumption(const bool doFullSubsume)
                     return false;
             }
             addFromSolver(solver.xorclauses);
-        }
+        }*/
     }
-    
-    if (solver.trail.size() - origTrailSize > 0)
-        solver.order_heap.filter(Solver::VarFilter(solver));
-    
+
+    solver.order_heap.filter(Solver::VarFilter(solver));
+
+    removeWrong(solver.learnts);
+    removeWrong(solver.binaryClauses);
     addBackToSolver();
     
     if (solver.verbosity >= 1) {
-        std::cout << "c | xorclauses-subsumed: " << std::setw(9) << clauses_subsumed
-        << " xorclauses-cut: " << std::setw(9) << clauses_cut
-        << " vars fixed: " << std::setw(3) <<solver.trail.size() - origTrailSize
-        << " time: " << std::setw(5) << std::setprecision(2) << (cpuTime() - myTime)
-        << "  |" << std::endl;
+        std::cout << "c |  x-sub: " << std::setw(5) << clauses_subsumed
+        << " x-cut: " << std::setw(6) << clauses_cut
+        << " vfix: " << std::setw(6) <<solver.trail.size() - origTrailSize
+        << " v-elim: " <<std::setw(6) << numElimed - lastNumElimed
+        << " locsubst:" << std::setw(6) << localSubstituteUseful
+        << " time: " << std::setw(6) << std::setprecision(2) << (cpuTime() - myTime)
+        << std::setw(3) << " |" << std::endl;
     }
+    totalTime += cpuTime() - myTime;
     
+    solver.testAllClauseAttach();
     return true;
 }
 
+#ifdef DEBUG_ATTACH
+void XorSubsumer::testAllClauseAttach() const
+{
+    for (const XorClauseSimp *it = clauses.getData(), *end = clauses.getDataEnd(); it != end; it++) {
+        if (it->clause == NULL) continue;
+        const XorClause& c = *it->clause;
+        assert(find(solver.xorwatches[c[0].var()], &c));
+        assert(find(solver.xorwatches[c[1].var()], &c));
+        if (solver.assigns[c[0].var()]!=l_Undef || solver.assigns[c[1].var()]!=l_Undef) {
+            for (uint i = 0; i < c.size();i++) {
+                assert(solver.assigns[c[i].var()] != l_Undef);
+            }
+        }
+    }
+}
+#else
+inline void XorSubsumer::testAllClauseAttach() const
+{
+    return;
+}
+#endif //DEBUG_ATTACH
+
 void XorSubsumer::findSubsumed(XorClause& ps, vec<XorClauseSimp>& out_subsumed)
 {
-    #ifdef VERBOSE_DEBUG
+    #ifdef VERBOSE_DEBUGSUBSUME0
     cout << "findSubsumed: ";
     for (uint32_t i = 0; i < ps.size(); i++) {
         if (ps[i].sign()) printf("-");
@@ -295,7 +580,7 @@ void XorSubsumer::findSubsumed(XorClause& ps, vec<XorClauseSimp>& out_subsumed)
         
         if (it->clause != &ps && subsetAbst(ps.getAbst(), it->clause->getAbst()) && ps.size() <= it->clause->size() && subset(ps, *it->clause)) {
             out_subsumed.push(*it);
-            #ifdef VERBOSE_DEBUG
+            #ifdef VERBOSE_DEBUGSUBSUME0
             cout << "subsumed: ";
             it->clause->plainPrint();
             #endif
@@ -303,4 +588,16 @@ void XorSubsumer::findSubsumed(XorClause& ps, vec<XorClauseSimp>& out_subsumed)
     }
 }
 
-}; //NAMESPACE MINISAT
+const bool XorSubsumer::checkElimedUnassigned() const
+{
+    for (uint32_t i = 0; i < var_elimed.size(); i++) {
+        if (var_elimed[i]) {
+            assert(solver.assigns[i] == l_Undef);
+            if (solver.assigns[i] != l_Undef) return false;
+        }
+    }
+
+    return true;
+}
+
+}; //NAMESPACE MINISAT
\ No newline at end of file
index 1876bce8c507ad8faa19051ea23ceb33a40ca9e4..b603a94cebaeac5a348d93a028de38868ee8e8a8 100644 (file)
@@ -24,10 +24,16 @@ public:
     const bool simplifyBySubsumption(const bool doFullSubsume = false);
     void unlinkModifiedClause(vec<Lit>& origClause, XorClauseSimp c);
     void unlinkModifiedClauseNoDetachNoNULL(vec<Lit>& origClause, XorClauseSimp c);
-    void unlinkClause(XorClauseSimp cc);
+    void unlinkClause(XorClauseSimp cc, Var elim = var_Undef);
     XorClauseSimp linkInClause(XorClause& cl);
     void linkInAlreadyClause(XorClauseSimp& c);
     void newVar();
+    void extendModel(Solver& solver2);
+    const uint32_t getNumElimed() const;
+    const vec<char>& getVarElimed() const;
+    const bool unEliminate(const Var var);
+    const bool checkElimedUnassigned() const;
+    const double getTotalTime() const;
     
 private:
     
@@ -54,6 +60,27 @@ private:
     bool subset(const T1& A, const T2& B);
     bool subsetAbst(uint32_t A, uint32_t B);
     void findUnMatched(vec<Lit>& A, XorClause& B, vec<Lit>& unmatchedPart);
+
+    //helper
+    void testAllClauseAttach() const;
+    
+    //dependent removal
+    const bool removeDependent();
+    void fillCannotEliminate();
+    vec<char> cannot_eliminate;
+    void addToCannotEliminate(Clause* it);
+    void removeWrong(vec<Clause*>& cs);
+
+    //Global stats
+    double totalTime;
+    map<Var, vector<XorClause*> > elimedOutVar;
+    vec<char> var_elimed;
+    uint32_t numElimed;
+    
+    //Heule-process
+    void clearDouble(vec<Lit>& ps) const;
+    const bool localSubstitute();
+    uint32_t localSubstituteUseful;
     
     uint32_t clauses_subsumed;
     uint32_t clauses_cut;
@@ -87,7 +114,24 @@ bool XorSubsumer::subset(const T1& A, const T2& B)
 inline void XorSubsumer::newVar()
 {
     occur       .push();
-    seen_tmp    .push(0);       // (one for each polarity)
+    seen_tmp    .push(0);
+    cannot_eliminate.push(0);
+    var_elimed.push(0);
+}
+
+inline const vec<char>& XorSubsumer::getVarElimed() const
+{
+    return var_elimed;
+}
+
+inline const uint32_t XorSubsumer::getNumElimed() const
+{
+    return numElimed;
+}
+
+inline const double XorSubsumer::getTotalTime() const
+{
+    return totalTime;
 }
 
 }; //NAMESPACE MINISAT
index 4c94beb6737457e7f3a1ffc1d5fd1c97d0ba27dd..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,36 +0,0 @@
-/****************************************************************************************[Solver.h]
-MiniSat -- Copyright (c) 2003-2006, Niklas Een, Niklas Sorensson
-glucose -- Gilles Audemard, Laurent Simon (2008)
-
-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.
-**************************************************************************************************/
-
-#define RATIOREMOVECLAUSES 3
-#define NBCLAUSESBEFOREREDUCE 20000
-#define DYNAMICNBLEVEL
-#define UPDATEVARACTIVITY
-#define FIXCLEANREPLACE 30U
-#define PERCENTAGEPERFORMREPLACE 0.01
-#define PERCENTAGECLEANCLAUSES 0.01
-#define MAX_CLAUSENUM_XORFIND 5000000
-#define BINARY_TO_XOR_APPROX 4.0
-#define FULLRESTART_MULTIPLIER 250.0
-#define FULLRESTART_MULTIPLIER_MULTIPLIER 3.5
-#define RESTART_TYPE_DECIDER_FROM 2
-#define RESTART_TYPE_DECIDER_UNTIL 7
-//#define VERBOSE_DEBUG_XOR
-//#define VERBOSE_DEBUG
-//#define USE_GAUSS