ABC: A System for Sequential Synthesis and Verification
 
Loading...
Searching...
No Matches
mfsInter.c
Go to the documentation of this file.
1
20
21#include "mfsInt.h"
22#include "bool/kit/kit.h"
23
25
26
30
34
46int Abc_MfsSatAddXor( sat_solver * pSat, int iVarA, int iVarB, int iVarC )
47{
48 lit Lits[3];
49
50 Lits[0] = toLitCond( iVarA, 1 );
51 Lits[1] = toLitCond( iVarB, 1 );
52 Lits[2] = toLitCond( iVarC, 1 );
53 if ( !sat_solver_addclause( pSat, Lits, Lits + 3 ) )
54 return 0;
55
56 Lits[0] = toLitCond( iVarA, 1 );
57 Lits[1] = toLitCond( iVarB, 0 );
58 Lits[2] = toLitCond( iVarC, 0 );
59 if ( !sat_solver_addclause( pSat, Lits, Lits + 3 ) )
60 return 0;
61
62 Lits[0] = toLitCond( iVarA, 0 );
63 Lits[1] = toLitCond( iVarB, 1 );
64 Lits[2] = toLitCond( iVarC, 0 );
65 if ( !sat_solver_addclause( pSat, Lits, Lits + 3 ) )
66 return 0;
67
68 Lits[0] = toLitCond( iVarA, 0 );
69 Lits[1] = toLitCond( iVarB, 0 );
70 Lits[2] = toLitCond( iVarC, 1 );
71 if ( !sat_solver_addclause( pSat, Lits, Lits + 3 ) )
72 return 0;
73
74 return 1;
75}
76
88sat_solver * Abc_MfsCreateSolverResub( Mfs_Man_t * p, int * pCands, int nCands, int fInvert )
89{
90 sat_solver * pSat;
91 Aig_Obj_t * pObjPo;
92 int Lits[2], status, iVar, i, c;
93
94 // get the literal for the output of F
95 pObjPo = Aig_ManCo( p->pAigWin, Aig_ManCoNum(p->pAigWin) - Vec_PtrSize(p->vDivs) - 1 );
96 Lits[0] = toLitCond( p->pCnf->pVarNums[pObjPo->Id], fInvert );
97
98 // collect the outputs of the divisors
99 Vec_IntClear( p->vProjVarsCnf );
100 Vec_PtrForEachEntryStart( Aig_Obj_t *, p->pAigWin->vCos, pObjPo, i, Aig_ManCoNum(p->pAigWin) - Vec_PtrSize(p->vDivs) )
101 {
102 assert( p->pCnf->pVarNums[pObjPo->Id] >= 0 );
103 Vec_IntPush( p->vProjVarsCnf, p->pCnf->pVarNums[pObjPo->Id] );
104 }
105 assert( Vec_IntSize(p->vProjVarsCnf) == Vec_PtrSize(p->vDivs) );
106
107 // start the solver
108 pSat = sat_solver_new();
109 sat_solver_setnvars( pSat, 2 * p->pCnf->nVars + Vec_PtrSize(p->vDivs) );
110 if ( pCands )
112
113 // load the first copy of the clauses
114 for ( i = 0; i < p->pCnf->nClauses; i++ )
115 {
116 if ( !sat_solver_addclause( pSat, p->pCnf->pClauses[i], p->pCnf->pClauses[i+1] ) )
117 {
118 sat_solver_delete( pSat );
119 return NULL;
120 }
121 }
122 // add the clause for the first output of F
123 if ( !sat_solver_addclause( pSat, Lits, Lits+1 ) )
124 {
125 sat_solver_delete( pSat );
126 return NULL;
127 }
128
129 // add one-hotness constraints
130 if ( p->pPars->fOneHotness )
131 {
132 p->pSat = pSat;
133 if ( !Abc_NtkAddOneHotness( p ) )
134 return NULL;
135 p->pSat = NULL;
136 }
137
138 // bookmark the clauses of A
139 if ( pCands )
141
142 // transform the literals
143 for ( i = 0; i < p->pCnf->nLiterals; i++ )
144 p->pCnf->pClauses[0][i] += 2 * p->pCnf->nVars;
145 // load the second copy of the clauses
146 for ( i = 0; i < p->pCnf->nClauses; i++ )
147 {
148 if ( !sat_solver_addclause( pSat, p->pCnf->pClauses[i], p->pCnf->pClauses[i+1] ) )
149 {
150 sat_solver_delete( pSat );
151 return NULL;
152 }
153 }
154 // add one-hotness constraints
155 if ( p->pPars->fOneHotness )
156 {
157 p->pSat = pSat;
158 if ( !Abc_NtkAddOneHotness( p ) )
159 return NULL;
160 p->pSat = NULL;
161 }
162 // transform the literals
163 for ( i = 0; i < p->pCnf->nLiterals; i++ )
164 p->pCnf->pClauses[0][i] -= 2 * p->pCnf->nVars;
165 // add the clause for the second output of F
166 Lits[0] = 2 * p->pCnf->nVars + lit_neg( Lits[0] );
167 if ( !sat_solver_addclause( pSat, Lits, Lits+1 ) )
168 {
169 sat_solver_delete( pSat );
170 return NULL;
171 }
172
173 if ( pCands )
174 {
175 // add relevant clauses for EXOR gates
176 for ( c = 0; c < nCands; c++ )
177 {
178 // get the variable number of this divisor
179 i = lit_var( pCands[c] ) - 2 * p->pCnf->nVars;
180 // get the corresponding SAT variable
181 iVar = Vec_IntEntry( p->vProjVarsCnf, i );
182 // add the corresponding EXOR gate
183 if ( !Abc_MfsSatAddXor( pSat, iVar, iVar + p->pCnf->nVars, 2 * p->pCnf->nVars + i ) )
184 {
185 sat_solver_delete( pSat );
186 return NULL;
187 }
188 // add the corresponding clause
189 if ( !sat_solver_addclause( pSat, pCands + c, pCands + c + 1 ) )
190 {
191 sat_solver_delete( pSat );
192 return NULL;
193 }
194 }
195 // bookmark the roots
197 }
198 else
199 {
200 // add the clauses for the EXOR gates - and remember their outputs
201 Vec_IntClear( p->vProjVarsSat );
202 Vec_IntForEachEntry( p->vProjVarsCnf, iVar, i )
203 {
204 if ( !Abc_MfsSatAddXor( pSat, iVar, iVar + p->pCnf->nVars, 2 * p->pCnf->nVars + i ) )
205 {
206 sat_solver_delete( pSat );
207 return NULL;
208 }
209 Vec_IntPush( p->vProjVarsSat, 2 * p->pCnf->nVars + i );
210 }
211 assert( Vec_IntSize(p->vProjVarsCnf) == Vec_IntSize(p->vProjVarsSat) );
212 // simplify the solver
213 status = sat_solver_simplify(pSat);
214 if ( status == 0 )
215 {
216// printf( "Abc_MfsCreateSolverResub(): SAT solver construction has failed. Skipping node.\n" );
217 sat_solver_delete( pSat );
218 return NULL;
219 }
220 }
221 return pSat;
222}
223
235unsigned * Abc_NtkMfsInterplateTruth( Mfs_Man_t * p, int * pCands, int nCands, int fInvert )
236{
237 sat_solver * pSat;
238 Sto_Man_t * pCnf = NULL;
239 unsigned * puTruth;
240 int nFanins, status;
241 int c, i, * pGloVars;
242
243 // derive the SAT solver for interpolation
244 pSat = Abc_MfsCreateSolverResub( p, pCands, nCands, fInvert );
245
246 // solve the problem
247 status = sat_solver_solve( pSat, NULL, NULL, (ABC_INT64_T)p->pPars->nBTLimit, (ABC_INT64_T)0, (ABC_INT64_T)0, (ABC_INT64_T)0 );
248 if ( status != l_False )
249 {
250 p->nTimeOuts++;
251 return NULL;
252 }
253 // get the learned clauses
254 pCnf = (Sto_Man_t *)sat_solver_store_release( pSat );
255 sat_solver_delete( pSat );
256
257 // set the global variables
258 pGloVars = Int_ManSetGlobalVars( p->pMan, nCands );
259 for ( c = 0; c < nCands; c++ )
260 {
261 // get the variable number of this divisor
262 i = lit_var( pCands[c] ) - 2 * p->pCnf->nVars;
263 // get the corresponding SAT variable
264 pGloVars[c] = Vec_IntEntry( p->vProjVarsCnf, i );
265 }
266
267 // derive the interpolant
268 nFanins = Int_ManInterpolate( p->pMan, pCnf, 0, &puTruth );
269 Sto_ManFree( pCnf );
270 assert( nFanins == nCands );
271 return puTruth;
272}
273
285int Abc_NtkMfsInterplateEval( Mfs_Man_t * p, int * pCands, int nCands )
286{
287 unsigned * pTruth, uTruth0[2], uTruth1[2];
288 int nCounter;
289 pTruth = Abc_NtkMfsInterplateTruth( p, pCands, nCands, 0 );
290 if ( nCands == 6 )
291 {
292 uTruth1[0] = pTruth[0];
293 uTruth1[1] = pTruth[1];
294 }
295 else
296 {
297 uTruth1[0] = pTruth[0];
298 uTruth1[1] = pTruth[0];
299 }
300 pTruth = Abc_NtkMfsInterplateTruth( p, pCands, nCands, 1 );
301 if ( nCands == 6 )
302 {
303 uTruth0[0] = ~pTruth[0];
304 uTruth0[1] = ~pTruth[1];
305 }
306 else
307 {
308 uTruth0[0] = ~pTruth[0];
309 uTruth0[1] = ~pTruth[0];
310 }
311 nCounter = Extra_WordCountOnes( uTruth0[0] ^ uTruth1[0] );
312 nCounter += Extra_WordCountOnes( uTruth0[1] ^ uTruth1[1] );
313// printf( "%d ", nCounter );
314 return nCounter;
315}
316
317
329Hop_Obj_t * Abc_NtkMfsInterplate( Mfs_Man_t * p, int * pCands, int nCands )
330{
331 extern Hop_Obj_t * Kit_GraphToHop( Hop_Man_t * pMan, Kit_Graph_t * pGraph );
332 int fDumpFile = 0;
333 char FileName[32];
334 sat_solver * pSat;
335 Sto_Man_t * pCnf = NULL;
336 unsigned * puTruth;
337 Kit_Graph_t * pGraph;
338 Hop_Obj_t * pFunc;
339 int nFanins, status;
340 int c, i, * pGloVars;
341// abctime clk = Abc_Clock();
342// p->nDcMints += Abc_NtkMfsInterplateEval( p, pCands, nCands );
343
344 // derive the SAT solver for interpolation
345 pSat = Abc_MfsCreateSolverResub( p, pCands, nCands, 0 );
346
347 // dump CNF file (remember to uncomment two-lit clases in clause_create_new() in 'satSolver.c')
348 if ( fDumpFile )
349 {
350 static int Counter = 0;
351 sprintf( FileName, "cnf\\pj1_if6_mfs%03d.cnf", Counter++ );
352 Sat_SolverWriteDimacs( pSat, FileName, NULL, NULL, 1 );
353 }
354
355 // solve the problem
356 status = sat_solver_solve( pSat, NULL, NULL, (ABC_INT64_T)p->pPars->nBTLimit, (ABC_INT64_T)0, (ABC_INT64_T)0, (ABC_INT64_T)0 );
357 if ( fDumpFile )
358 printf( "File %s has UNSAT problem with %d conflicts.\n", FileName, (int)pSat->stats.conflicts );
359 if ( status != l_False )
360 {
361 p->nTimeOuts++;
362 return NULL;
363 }
364//printf( "%d\n", pSat->stats.conflicts );
365// ABC_PRT( "S", Abc_Clock() - clk );
366 // get the learned clauses
367 pCnf = (Sto_Man_t *)sat_solver_store_release( pSat );
368 sat_solver_delete( pSat );
369
370 // set the global variables
371 pGloVars = Int_ManSetGlobalVars( p->pMan, nCands );
372 for ( c = 0; c < nCands; c++ )
373 {
374 // get the variable number of this divisor
375 i = lit_var( pCands[c] ) - 2 * p->pCnf->nVars;
376 // get the corresponding SAT variable
377 pGloVars[c] = Vec_IntEntry( p->vProjVarsCnf, i );
378 }
379
380 // derive the interpolant
381 nFanins = Int_ManInterpolate( p->pMan, pCnf, 0, &puTruth );
382 Sto_ManFree( pCnf );
383 assert( nFanins == nCands );
384
385 // transform interpolant into AIG
386 pGraph = Kit_TruthToGraph( puTruth, nFanins, p->vMem );
387 pFunc = Kit_GraphToHop( (Hop_Man_t *)p->pNtk->pManFunc, pGraph );
388 Kit_GraphFree( pGraph );
389 return pFunc;
390}
391
395
396
398
#define ABC_NAMESPACE_IMPL_START
#define ABC_NAMESPACE_IMPL_END
struct Aig_Obj_t_ Aig_Obj_t
Definition aig.h:51
#define l_False
Definition bmcBmcS.c:36
#define sat_solver_addclause
Definition cecSatG2.c:37
#define sat_solver
Definition cecSatG2.c:34
#define sat_solver_solve
Definition cecSatG2.c:45
Cube * p
Definition exorList.c:222
typedefABC_NAMESPACE_HEADER_START struct Hop_Man_t_ Hop_Man_t
INCLUDES ///.
Definition hop.h:49
struct Hop_Obj_t_ Hop_Obj_t
Definition hop.h:50
Hop_Obj_t * Kit_GraphToHop(Hop_Man_t *pMan, Kit_Graph_t *pGraph)
Definition kitHop.c:261
struct Kit_Graph_t_ Kit_Graph_t
Definition kit.h:88
void Kit_GraphFree(Kit_Graph_t *pGraph)
Definition kitGraph.c:132
Kit_Graph_t * Kit_TruthToGraph(unsigned *pTruth, int nVars, Vec_Int_t *vMemory)
Definition kitGraph.c:356
struct Mfs_Man_t_ Mfs_Man_t
Definition mfsInt.h:49
int Abc_NtkAddOneHotness(Mfs_Man_t *p)
Definition mfsSat.c:155
ABC_NAMESPACE_IMPL_START int Abc_MfsSatAddXor(sat_solver *pSat, int iVarA, int iVarB, int iVarC)
DECLARATIONS ///.
Definition mfsInter.c:46
sat_solver * Abc_MfsCreateSolverResub(Mfs_Man_t *p, int *pCands, int nCands, int fInvert)
Definition mfsInter.c:88
unsigned * Abc_NtkMfsInterplateTruth(Mfs_Man_t *p, int *pCands, int nCands, int fInvert)
Definition mfsInter.c:235
Hop_Obj_t * Abc_NtkMfsInterplate(Mfs_Man_t *p, int *pCands, int nCands)
Definition mfsInter.c:329
int Abc_NtkMfsInterplateEval(Mfs_Man_t *p, int *pCands, int nCands)
Definition mfsInter.c:285
int * Int_ManSetGlobalVars(Int_Man_t *p, int nGloVars)
Definition satInter.c:133
int Int_ManInterpolate(Int_Man_t *p, Sto_Man_t *pCnf, int fVerbose, unsigned **ppResult)
Definition satInter.c:1005
sat_solver * sat_solver_new(void)
Definition satSolver.c:1137
void sat_solver_store_mark_clauses_a(sat_solver *s)
Definition satSolver.c:2417
int sat_solver_simplify(sat_solver *s)
Definition satSolver.c:1515
void sat_solver_setnvars(sat_solver *s, int n)
Definition satSolver.c:1272
void sat_solver_store_alloc(sat_solver *s)
Definition satSolver.c:2389
void sat_solver_store_mark_roots(sat_solver *s)
Definition satSolver.c:2412
void * sat_solver_store_release(sat_solver *s)
Definition satSolver.c:2422
void sat_solver_delete(sat_solver *s)
Definition satSolver.c:1341
void Sat_SolverWriteDimacs(sat_solver *p, char *pFileName, lit *assumptionsBegin, lit *assumptionsEnd, int incrementVars)
Definition satUtil.c:74
void Sto_ManFree(Sto_Man_t *p)
Definition satStore.c:143
struct Sto_Man_t_ Sto_Man_t
Definition satStore.h:81
int lit
Definition satVec.h:130
int Id
Definition aig.h:85
stats_t stats
Definition satSolver.h:163
ABC_INT64_T conflicts
Definition satVec.h:156
#define assert(ex)
Definition util_old.h:213
char * sprintf()
#define Vec_IntForEachEntry(vVec, Entry, i)
MACRO DEFINITIONS ///.
Definition vecInt.h:54
#define Vec_PtrForEachEntryStart(Type, vVec, pEntry, i, Start)
Definition vecPtr.h:57