ABC: A System for Sequential Synthesis and Verification
 
Loading...
Searching...
No Matches
amapMatch.c
Go to the documentation of this file.
1
20
21#include "amapInt.h"
22
24
25
29
33
46{
47 Amap_Cut_t * pNew;
48 int nBytes = sizeof(Amap_Cut_t) + sizeof(int) * pCut->nFans;
49 pNew = (Amap_Cut_t *)Aig_MmFlexEntryFetch( p->pMemCutBest, nBytes );
50 memcpy( pNew, pCut, (size_t)nBytes );
51 return pNew;
52}
53
65static inline void Amap_ManMatchStart( Amap_Mat_t * p, Amap_Cut_t * pCut, Amap_Set_t * pSet )
66{
67 memset( p, 0, sizeof(Amap_Mat_t) );
68 p->pCut = pCut;
69 p->pSet = pSet;
70}
71
84{
85 Amap_Obj_t * pObj;
86 int i;
87 Amap_ManForEachObj( p, pObj, i )
88 pObj->nFouts[0] = pObj->nFouts[1] = 0;
89}
90
103{
104 Amap_Obj_t * pObj;
105 float Delay = 0.0;
106 int i;
107 Amap_ManForEachPo( p, pObj, i )
108 Delay = Abc_MaxInt( Delay, Amap_ObjFanin0(p,pObj)->Best.Delay );
109 return Delay;
110}
111
124{
125 Amap_Obj_t * pObj;
126 int i;
127// Amap_ManForEachNode( p, pObj, i )
128// ABC_FREE( pObj->pData );
129 Amap_ManForEachObj( p, pObj, i )
130 pObj->pData = NULL;
131}
132
144float Amap_ManComputeMapping_rec( Amap_Man_t * p, Amap_Obj_t * pObj, int fCompl )
145{
146 Amap_Mat_t * pM = &pObj->Best;
147 Amap_Obj_t * pFanin;
148 Amap_Gat_t * pGate;
149 int i, iFanin, fComplFanin;
150 float Area;
151 if ( pObj->nFouts[fCompl]++ + pObj->nFouts[!fCompl] > 0 )
152 return 0.0;
153 if ( Amap_ObjIsPi(pObj) || Amap_ObjIsConst1(pObj) )
154 return 0.0;
155 pGate = Amap_LibGate( p->pLib, pM->pSet->iGate );
156 assert( pGate->nPins == pM->pCut->nFans );
157 Area = pGate->dArea;
158 for ( i = 0; i < (int)pGate->nPins; i++ )
159 {
160 iFanin = Abc_Lit2Var( pM->pSet->Ins[i] );
161 pFanin = Amap_ManObj( p, Abc_Lit2Var(pM->pCut->Fans[iFanin]) );
162 fComplFanin = Abc_LitIsCompl( pM->pSet->Ins[i] ) ^ Abc_LitIsCompl( pM->pCut->Fans[iFanin] );
163 Area += Amap_ManComputeMapping_rec( p, pFanin, fComplFanin );
164 }
165 return Area;
166}
167
180{
181 Amap_Obj_t * pObj;
182 float Area = 0.0;
183 int i;
185 Amap_ManForEachPo( p, pObj, i )
186 Area += Amap_ManComputeMapping_rec( p, Amap_ObjFanin0(p, pObj), Amap_ObjFaninC0(pObj) );
187 return Area;
188}
189
202{
203 Amap_Obj_t * pObj;
204 int i, Counter = 0;
205 Amap_ManForEachObj( p, pObj, i )
206 Counter += (int)(pObj->nFouts[!pObj->fPolar] > 0);
207 return Counter;
208}
209
221static inline int Amap_CutCompareDelay( Amap_Man_t * p, Amap_Mat_t * pM0, Amap_Mat_t * pM1 )
222{
223 // compare delay
224 if ( pM0->Delay < pM1->Delay - p->pPars->fEpsilon )
225 return -1;
226 if ( pM0->Delay > pM1->Delay + p->pPars->fEpsilon )
227 return 1;
228
229 // compare area flows
230 if ( pM0->Area < pM1->Area - p->pPars->fEpsilon )
231 return -1;
232 if ( pM0->Area > pM1->Area + p->pPars->fEpsilon )
233 return 1;
234
235 // compare average fanouts
236 if ( pM0->AveFan > pM1->AveFan - p->pPars->fEpsilon )
237 return -1;
238 if ( pM0->AveFan < pM1->AveFan + p->pPars->fEpsilon )
239 return 1;
240 return 1;
241}
242static inline int Amap_CutCompareArea( Amap_Man_t * p, Amap_Mat_t * pM0, Amap_Mat_t * pM1 )
243{
244 // compare area flows
245 if ( pM0->Area < pM1->Area - p->pPars->fEpsilon )
246 return -1;
247 if ( pM0->Area > pM1->Area + p->pPars->fEpsilon )
248 return 1;
249
250 // compare average fanouts
251 if ( pM0->AveFan > pM1->AveFan - p->pPars->fEpsilon )
252 return -1;
253 if ( pM0->AveFan < pM1->AveFan + p->pPars->fEpsilon )
254 return 1;
255
256 // compare delay
257 if ( pM0->Delay < pM1->Delay - p->pPars->fEpsilon )
258 return -1;
259 if ( pM0->Delay > pM1->Delay + p->pPars->fEpsilon )
260 return 1;
261 return 1;
262}
263
275static inline float Amap_CutAreaDeref( Amap_Man_t * p, Amap_Mat_t * pM )
276{
277 Amap_Obj_t * pFanin;
278 int i, fCompl;
279 float Area = Amap_LibGate( p->pLib, pM->pSet->iGate )->dArea;
280 Amap_MatchForEachFaninCompl( p, pM, pFanin, fCompl, i )
281 {
282 assert( Amap_ObjRefsTotal(pFanin) > 0 );
283 if ( (int)pFanin->fPolar != fCompl && pFanin->nFouts[fCompl] == 1 )
284 Area += p->fAreaInv;
285 if ( --pFanin->nFouts[fCompl] + pFanin->nFouts[!fCompl] == 0 && Amap_ObjIsNode(pFanin) )
286 Area += Amap_CutAreaDeref( p, &pFanin->Best );
287 }
288 return Area;
289}
290
302static inline float Amap_CutAreaRef2( Amap_Man_t * p, Amap_Mat_t * pM, Vec_Ptr_t * vTemp, int Limit )
303{
304 Amap_Obj_t * pFanin;
305 int i, fCompl;
306 float Area = Amap_LibGate( p->pLib, pM->pSet->iGate )->dArea;
307 if ( Limit == 0 ) return Area;
308 Amap_MatchForEachFaninCompl( p, pM, pFanin, fCompl, i )
309 {
310 Vec_PtrPush( vTemp, pFanin->nFouts + fCompl );
311 assert( Amap_ObjRefsTotal(pFanin) >= 0 );
312 if ( (int)pFanin->fPolar != fCompl && pFanin->nFouts[fCompl] == 0 )
313 Area += p->fAreaInv;
314 if ( pFanin->nFouts[fCompl]++ + pFanin->nFouts[!fCompl] == 0 && Amap_ObjIsNode(pFanin) )
315 Area += Amap_CutAreaRef2( p, &pFanin->Best, vTemp, Limit-1 );
316 }
317 return Area;
318}
319
331static inline float Amap_CutAreaDerefed2( Amap_Man_t * p, Amap_Obj_t * pNode, Amap_Mat_t * pM )
332{
333 int nRecurLevels = 8;
334 int fComplNew, i, * pInt;
335 float aResult;
336 Vec_PtrClear( p->vTempP );
337 aResult = Amap_CutAreaRef2( p, pM, p->vTempP, nRecurLevels );
338 //Amap_CutAreaDeref( p, pM );
339 Vec_PtrForEachEntry( int *, p->vTempP, pInt, i )
340 (*pInt)--;
341 // if node is needed in another polarity, add inverter
342 fComplNew = pM->pCut->fInv ^ pM->pSet->fInv;
343 if ( pNode->nFouts[fComplNew] == 0 && pNode->nFouts[!fComplNew] > 0 )
344 aResult += p->fAreaInv;
345 return aResult;
346}
347
359static inline float Amap_CutAreaRef( Amap_Man_t * p, Amap_Mat_t * pM )
360{
361 Amap_Obj_t * pFanin;
362 int i, fCompl;
363 float Area = Amap_LibGate( p->pLib, pM->pSet->iGate )->dArea;
364 Amap_MatchForEachFaninCompl( p, pM, pFanin, fCompl, i )
365 {
366 assert( Amap_ObjRefsTotal(pFanin) >= 0 );
367 if ( (int)pFanin->fPolar != fCompl && pFanin->nFouts[fCompl] == 0 )
368 Area += p->fAreaInv;
369 if ( pFanin->nFouts[fCompl]++ + pFanin->nFouts[!fCompl] == 0 && Amap_ObjIsNode(pFanin) )
370 Area += Amap_CutAreaRef( p, &pFanin->Best );
371 }
372 return Area;
373}
374
386static inline float Amap_CutAreaDerefed( Amap_Man_t * p, Amap_Obj_t * pNode, Amap_Mat_t * pM )
387{
388 float aResult, aResult2;
389 int fComplNew;
390 aResult2 = Amap_CutAreaRef( p, pM );
391 aResult = Amap_CutAreaDeref( p, pM );
392 assert( aResult > aResult2 - p->fEpsilonInternal );
393 assert( aResult < aResult2 + p->fEpsilonInternal );
394 // if node is needed in another polarity, add inverter
395 fComplNew = pM->pCut->fInv ^ pM->pSet->fInv;
396 if ( pNode->nFouts[fComplNew] == 0 && pNode->nFouts[!fComplNew] > 0 )
397 aResult += p->fAreaInv;
398 return aResult;
399}
400
412static inline void Amap_CutAreaTest( Amap_Man_t * p, Amap_Obj_t * pNode )
413{
414 float aResult, aResult2;
415 if ( Amap_ObjRefsTotal(pNode) == 0 )
416 {
417 aResult2 = Amap_CutAreaRef( p, &pNode->Best );
418 aResult = Amap_CutAreaDeref( p, &pNode->Best );
419 assert( aResult > aResult2 - p->fEpsilonInternal );
420 assert( aResult < aResult2 + p->fEpsilonInternal );
421 }
422 else
423 {
424 aResult = Amap_CutAreaDeref( p, &pNode->Best );
425 aResult2 = Amap_CutAreaRef( p, &pNode->Best );
426 assert( aResult > aResult2 - p->fEpsilonInternal );
427 assert( aResult < aResult2 + p->fEpsilonInternal );
428 }
429}
430
442static inline void Amap_ManMatchGetFlows( Amap_Man_t * p, Amap_Mat_t * pM )
443{
444 Amap_Mat_t * pMFanin;
445 Amap_Obj_t * pFanin;
446 Amap_Gat_t * pGate;
447 float AddOn;
448 int i;
449 pGate = Amap_LibGate( p->pLib, pM->pSet->iGate );
450 assert( pGate->nPins == pM->pCut->nFans );
451 assert( pM->Area == 0.0 );
452 pM->Area = pGate->dArea;
453 pM->AveFan = 0.0;
454 pM->Delay = 0.0;
455 Amap_MatchForEachFanin( p, pM, pFanin, i )
456 {
457 pMFanin = &pFanin->Best;
458 pM->Delay = Abc_MaxInt( pM->Delay, pMFanin->Delay );
459 pM->AveFan += Amap_ObjRefsTotal(pFanin);
460// if ( Amap_ObjRefsTotal(pFanin) == 0 )
461// pM->Area += pMFanin->Area;
462// else
463// pM->Area += pMFanin->Area / pFanin->EstRefs;
464 AddOn = Amap_ObjRefsTotal(pFanin) == 0 ? pMFanin->Area : pMFanin->Area / pFanin->EstRefs;
465 if ( pM->Area >= (float)1e32 || AddOn >= (float)1e32 )
466 pM->Area = (float)1e32;
467 else
468 pM->Area += AddOn;
469 }
470 pM->AveFan /= pGate->nPins;
471 pM->Delay += 1.0;
472}
473
485static inline void Amap_ManMatchGetExacts( Amap_Man_t * p, Amap_Obj_t * pNode, Amap_Mat_t * pM )
486{
487 Amap_Mat_t * pMFanin;
488 Amap_Obj_t * pFanin;
489 Amap_Gat_t * pGate;
490 int i;
491 pGate = Amap_LibGate( p->pLib, pM->pSet->iGate );
492 assert( pGate->nPins == pM->pCut->nFans );
493 assert( pM->Area == 0.0 );
494 pM->AveFan = 0.0;
495 pM->Delay = 0.0;
496 Amap_MatchForEachFanin( p, pM, pFanin, i )
497 {
498 pMFanin = &pFanin->Best;
499 pM->Delay = Abc_MaxInt( pM->Delay, pMFanin->Delay );
500 pM->AveFan += Amap_ObjRefsTotal(pFanin);
501 }
502 pM->AveFan /= pGate->nPins;
503 pM->Delay += 1.0;
504 //pM->Area = Amap_CutAreaDerefed( p, pNode, pM );
505 pM->Area = Amap_CutAreaDerefed2( p, pNode, pM );
506}
507
519void Amap_ManMatchNode( Amap_Man_t * p, Amap_Obj_t * pNode, int fFlow, int fRefs )
520{
521 int fVerbose = 0; //(pNode->Level == 2 || pNode->Level == 4);
522 int fVeryVerbose = fVerbose;
523
524 Amap_Mat_t MA = {0}, MD = {0}, M = {0};
525 Amap_Mat_t * pMBestA = &MA, * pMBestD = &MD, * pMThis = &M, * pMBest;
526 Amap_Cut_t * pCut;
527 Amap_Set_t * pSet;
528 Amap_Nod_t * pNod;
529 int i;
530
531 if ( fRefs )
532 pNode->EstRefs = (float)((2.0 * pNode->EstRefs + Amap_ObjRefsTotal(pNode)) / 3.0);
533 else
534 pNode->EstRefs = (float)pNode->nRefs;
535 if ( fRefs && Amap_ObjRefsTotal(pNode) > 0 )
536 Amap_CutAreaDeref( p, &pNode->Best );
537
538 if ( fVerbose )
539 printf( "\nNode %d (%d)\n", pNode->Id, pNode->Level );
540
541 pMBestA->pCut = pMBestD->pCut = NULL;
542 Amap_NodeForEachCut( pNode, pCut, i )
543 {
544 if ( pCut->iMat == 0 )
545 continue;
546 pNod = Amap_LibNod( p->pLib, pCut->iMat );
547 Amap_LibNodeForEachSet( pNod, pSet )
548 {
549 Amap_ManMatchStart( pMThis, pCut, pSet );
550 if ( fFlow )
551 Amap_ManMatchGetFlows( p, pMThis );
552 else
553 Amap_ManMatchGetExacts( p, pNode, pMThis );
554 if ( pMBestD->pCut == NULL || Amap_CutCompareDelay(p, pMBestD, pMThis) == 1 )
555 *pMBestD = *pMThis;
556 if ( pMBestA->pCut == NULL || Amap_CutCompareArea(p, pMBestA, pMThis) == 1 )
557 *pMBestA = *pMThis;
558
559 if ( fVeryVerbose )
560 {
561 printf( "Cut %2d (%d) : ", i, pCut->nFans );
562 printf( "Gate %10s ", Amap_LibGate(p->pLib, pMThis->pSet->iGate)->pName );
563 printf( "%s ", pMThis->pSet->fInv ? "inv" : " " );
564 printf( "Delay %5.2f ", pMThis->Delay );
565 printf( "Area %5.2f ", pMThis->Area );
566 printf( "\n" );
567 }
568 }
569 }
570
571 if ( Abc_AbsFloat(pMBestA->Area - pMBestD->Area) / pMBestD->Area >= p->pPars->fADratio * Abc_AbsFloat(pMBestA->Delay - pMBestD->Delay) / pMBestA->Delay )
572 pMBest = pMBestA;
573 else
574 pMBest = pMBestD;
575
576 if ( fVerbose )
577 {
578 printf( "BEST MATCHA: " );
579 printf( "Gate %10s ", Amap_LibGate(p->pLib, pMBestA->pSet->iGate)->pName );
580 printf( "%s ", pMBestA->pSet->fInv ? "inv" : " " );
581 printf( "Delay %5.2f ", pMBestA->Delay );
582 printf( "Area %5.2f ", pMBestA->Area );
583 printf( "\n" );
584
585 printf( "BEST MATCHD: " );
586 printf( "Gate %10s ", Amap_LibGate(p->pLib, pMBestD->pSet->iGate)->pName );
587 printf( "%s ", pMBestD->pSet->fInv ? "inv" : " " );
588 printf( "Delay %5.2f ", pMBestD->Delay );
589 printf( "Area %5.2f ", pMBestD->Area );
590 printf( "\n" );
591
592 printf( "BEST MATCH : " );
593 printf( "Gate %10s ", Amap_LibGate(p->pLib, pMBest->pSet->iGate)->pName );
594 printf( "%s ", pMBest->pSet->fInv ? "inv" : " " );
595 printf( "Delay %5.2f ", pMBest->Delay );
596 printf( "Area %5.2f ", pMBest->Area );
597 printf( "\n" );
598 }
599
600 pNode->fPolar = pMBest->pCut->fInv ^ pMBest->pSet->fInv;
601 pNode->Best = *pMBest;
602 pNode->Best.pCut = Amap_ManDupCut( p, pNode->Best.pCut );
603 if ( fRefs && Amap_ObjRefsTotal(pNode) > 0 )
604 Amap_CutAreaRef( p, &pNode->Best );
605}
606
618void Amap_ManMatch( Amap_Man_t * p, int fFlow, int fRefs )
619{
620 Aig_MmFlex_t * pMemOld;
621 Amap_Obj_t * pObj;
622 float Area;
623 int i, nInvs;
624 abctime clk = Abc_Clock();
625 pMemOld = p->pMemCutBest;
626 p->pMemCutBest = Aig_MmFlexStart();
627 Amap_ManForEachNode( p, pObj, i )
628 if ( pObj->pData )
629 Amap_ManMatchNode( p, pObj, fFlow, fRefs );
630 Aig_MmFlexStop( pMemOld, 0 );
631 Area = Amap_ManComputeMapping( p );
632 nInvs = Amap_ManCountInverters( p );
633if ( p->pPars->fVerbose )
634{
635 printf( "Area =%9.2f. Gate =%9.2f. Inv =%9.2f. (%6d.) Delay =%6.2f. ",
636 Area + nInvs * p->fAreaInv,
637 Area, nInvs * p->fAreaInv, nInvs,
639ABC_PRT( "Time ", Abc_Clock() - clk );
640}
641 // test procedures
642// Amap_ManForEachNode( p, pObj, i )
643// Amap_CutAreaTest( p, pObj );
644}
645
658{
659 int i;
660 Amap_ManMerge( p );
661 for ( i = 0; i < p->pPars->nIterFlow; i++ )
662 Amap_ManMatch( p, 1, i>0 );
663 for ( i = 0; i < p->pPars->nIterArea; i++ )
664 Amap_ManMatch( p, 0, p->pPars->nIterFlow>0||i>0 );
665/*
666 for ( i = 0; i < p->pPars->nIterFlow; i++ )
667 Amap_ManMatch( p, 1, 1 );
668 for ( i = 0; i < p->pPars->nIterArea; i++ )
669 Amap_ManMatch( p, 0, 1 );
670*/
672}
673
677
678
680
ABC_INT64_T abctime
Definition abc_global.h:332
#define ABC_PRT(a, t)
Definition abc_global.h:255
#define ABC_NAMESPACE_IMPL_START
#define ABC_NAMESPACE_IMPL_END
void Aig_MmFlexStop(Aig_MmFlex_t *p, int fVerbose)
Definition aigMem.c:337
char * Aig_MmFlexEntryFetch(Aig_MmFlex_t *p, int nBytes)
Definition aigMem.c:366
struct Aig_MmFlex_t_ Aig_MmFlex_t
Definition aig.h:53
Aig_MmFlex_t * Aig_MmFlexStart()
Definition aigMem.c:305
struct Amap_Obj_t_ Amap_Obj_t
Definition amapInt.h:71
#define Amap_NodeForEachCut(pNode, pCut, i)
Definition amapInt.h:301
#define Amap_MatchForEachFaninCompl(p, pM, pFanin, fCompl, i)
Definition amapInt.h:310
struct Amap_Man_t_ Amap_Man_t
Definition amapInt.h:70
#define Amap_ManForEachObj(p, pObj, i)
Definition amapInt.h:287
#define Amap_ManForEachNode(p, pObj, i)
Definition amapInt.h:290
struct Amap_Set_t_ Amap_Set_t
Definition amapInt.h:68
void Amap_ManMerge(Amap_Man_t *p)
Definition amapMerge.c:514
struct Amap_Gat_t_ Amap_Gat_t
Definition amapInt.h:66
#define Amap_LibNodeForEachSet(pNod, pSet)
Definition amapInt.h:306
struct Amap_Mat_t_ Amap_Mat_t
Definition amapInt.h:73
struct Amap_Nod_t_ Amap_Nod_t
Definition amapInt.h:67
struct Amap_Cut_t_ Amap_Cut_t
Definition amapInt.h:72
#define Amap_ManForEachPo(p, pObj, i)
Definition amapInt.h:284
#define Amap_MatchForEachFanin(p, pM, pFanin, i)
Definition amapInt.h:317
void Amap_ManMatchNode(Amap_Man_t *p, Amap_Obj_t *pNode, int fFlow, int fRefs)
Definition amapMatch.c:519
void Amap_ManMatch(Amap_Man_t *p, int fFlow, int fRefs)
Definition amapMatch.c:618
float Amap_ManComputeMapping_rec(Amap_Man_t *p, Amap_Obj_t *pObj, int fCompl)
Definition amapMatch.c:144
float Amap_ManMaxDelay(Amap_Man_t *p)
Definition amapMatch.c:102
void Amap_ManCleanData(Amap_Man_t *p)
Definition amapMatch.c:123
ABC_NAMESPACE_IMPL_START Amap_Cut_t * Amap_ManDupCut(Amap_Man_t *p, Amap_Cut_t *pCut)
DECLARATIONS ///.
Definition amapMatch.c:45
float Amap_ManComputeMapping(Amap_Man_t *p)
Definition amapMatch.c:179
int Amap_ManCountInverters(Amap_Man_t *p)
Definition amapMatch.c:201
void Amap_ManMap(Amap_Man_t *p)
Definition amapMatch.c:657
void Amap_ManCleanRefs(Amap_Man_t *p)
Definition amapMatch.c:83
Cube * p
Definition exorList.c:222
word M(word f1, word f2, int n)
Definition kitPerm.c:240
unsigned fInv
Definition amapInt.h:187
unsigned iMat
Definition amapInt.h:186
unsigned nFans
Definition amapInt.h:188
int Fans[0]
Definition amapInt.h:189
double dArea
Definition amapInt.h:157
unsigned nPins
Definition amapInt.h:162
float Delay
Definition amapInt.h:197
float Area
Definition amapInt.h:195
Amap_Set_t * pSet
Definition amapInt.h:194
float AveFan
Definition amapInt.h:196
Amap_Cut_t * pCut
Definition amapInt.h:193
float EstRefs
Definition amapInt.h:217
unsigned fPolar
Definition amapInt.h:206
void * pData
Definition amapInt.h:213
int nFouts[2]
Definition amapInt.h:218
unsigned Id
Definition amapInt.h:202
Amap_Mat_t Best
Definition amapInt.h:219
unsigned Level
Definition amapInt.h:207
unsigned fInv
Definition amapInt.h:169
unsigned iGate
Definition amapInt.h:168
char Ins[AMAP_MAXINS]
Definition amapInt.h:171
#define assert(ex)
Definition util_old.h:213
char * memcpy()
char * memset()
typedefABC_NAMESPACE_HEADER_START struct Vec_Ptr_t_ Vec_Ptr_t
INCLUDES ///.
Definition vecPtr.h:42
#define Vec_PtrForEachEntry(Type, vVec, pEntry, i)
MACRO DEFINITIONS ///.
Definition vecPtr.h:55