summaryrefslogtreecommitdiffstats
path: root/src/opt/dec/dec.h
blob: 26af6b1cf1512515dba9164314e63573c2eaecfa (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
/**CFile****************************************************************

  FileName    [dec.h]

  SystemName  [ABC: Logic synthesis and verification system.]

  PackageName [A simple decomposition tree/node data structure and its APIs.]

  Synopsis    [External declarations.]

  Author      [Alan Mishchenko]
  
  Affiliation [UC Berkeley]

  Date        [Ver. 1.0. Started - June 20, 2005.]

  Revision    [$Id: dec.h,v 1.00 2005/06/20 00:00:00 alanmi Exp $]

***********************************************************************/
 
#ifndef __DEC_H__
#define __DEC_H__

////////////////////////////////////////////////////////////////////////
///                          INCLUDES                                ///
////////////////////////////////////////////////////////////////////////

////////////////////////////////////////////////////////////////////////
///                         PARAMETERS                               ///
////////////////////////////////////////////////////////////////////////

////////////////////////////////////////////////////////////////////////
///                         BASIC TYPES                              ///
////////////////////////////////////////////////////////////////////////

typedef struct Dec_Node_t_ Dec_Node_t;
struct Dec_Node_t_
{
    // the first child
    unsigned   fCompl0  :  1;    // complemented attribute of the first fanin
    unsigned   iFanin0  : 11;    // the number of the first fanin
    // the second child
    unsigned   fCompl1  :  1;    // complemented attribute of the second fanin
    unsigned   iFanin1  : 11;    // the number of the second fanin
    // other info
    unsigned   fIntern  :  1;    // marks all internal nodes (to distinquish them from elementary vars) 
    unsigned   fConst   :  1;    // marks the constant 1 function (topmost node only)
    unsigned   fCompl   :  1;    // marks the complement of topmost node (topmost node only)
    // printing info (factored forms only)
    unsigned   fNodeOr  :  1;    // marks the original OR node
    unsigned   fEdge0   :  1;    // marks the original complemented edge
    unsigned   fEdge1   :  1;    // marks the original complemented edge
    // some bits are left unused
};

/*
    The decomposition tree data structure is designed to represent relatively small
    (up to 100 nodes) AIGs used for factoring, rewriting, and decomposition.

    For simplicity, the nodes of the decomposition tree are written in DFS order 
    into an integer vector (Vec_Int_t). The decomposition node (Dec_Node_t)
    is typecast into an integer when written into the array.
    
    This representation can be readily translated into the main AIG represented 
    in the ABC network. Because of the linear order of the decomposition nodes 
    in the array, it is easy to put the existing AIG nodes in correspondence with 
    them. This process begins by first putting leaves of the decomposition tree 
    in correpondence with the fanins of the cut used to derive the function, 
    which was decomposed. Next for each internal node of the decomposition tree, 
    we find or create a corresponding node in the AIG. Finally, the root node of 
    the tree replaces the original root node of the cut, which was decomposed.

    To achieve the above scenario, we reserve the first n entries for the array
    to the fanins of the cut (the number of fanins is n). These entries are left
    empty in the array (that is, they are represented by 0 integer). Each entry
    after the fanins is an internal node (flag fIntern is set to 1). The internal
    nodes can have complemented inputs (denoted by flags fComp0 and fCompl1).
    The last node can be complemented (fCompl), which is true if the root node
    of the decomposition tree is represented by a complemented AIG node.

    Two cases have to be specially considered: a constant function and a function
    equal to an elementary variables (possibly complemented). In these two cases,
    the decomposition tree/array has exactly n+1 nodes, where n in the number of 
    fanins. (A constant function may depend on n variable, in which case these
    are redundant variables. Similarly, a function can be a function in n-D space
    but in fact depend only on one variable in this space.)

    When the function is a constant, the last node has a flag fConst set to 1.
    In this case the complemented flag (fCompl) shows the value of the constant.
    (fCompl = 0 means costant 1; fCompl = 1 means constant 0).
    When the function if an elementary variable, the last node has both pointers
    pointing to the same elementary node, while the complemented flag (fCompl)
    shows whether the variable is complemented. For example: x' = Not( AND(x, x) ).

    When manipulating the decomposition tree, it is convenient to return the 
    intermediate results of decomposition as an integer, which includes the number 
    of the Dec_Node_t in the array of decomposition nodes and the complemented flag.
    Factoring is a special case of decomposition, which demonstrates this kind
    of manipulation.
*/

////////////////////////////////////////////////////////////////////////
///                      MACRO DEFITIONS                             ///
////////////////////////////////////////////////////////////////////////

////////////////////////////////////////////////////////////////////////
///                    FUNCTION DECLARATIONS                         ///
////////////////////////////////////////////////////////////////////////

/**Function*************************************************************

  Synopsis    [Cleans the decomposition node.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/ 
static inline void         Dec_NodeClean( Dec_Node_t * pNode )       {  *((int *)pNode) = 0;           }

/**Function*************************************************************

  Synopsis    [Convert between an interger and an decomposition node.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline Dec_Node_t   Dec_Int2Node( int Num )                   {  return *((Dec_Node_t *)&Num);  }
static inline int          Dec_Node2Int( Dec_Node_t Node )           {  return *((int *)&Node);        }

/**Function*************************************************************

  Synopsis    [Returns the pointer to the i-th decomposition node.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline Dec_Node_t * Dec_NodeRead( Vec_Int_t * vDec, int i )   {  return (Dec_Node_t *)vDec->pArray + i;  }

/**Function*************************************************************

  Synopsis    [Returns the pointer to the last decomposition node.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline Dec_Node_t * Dec_NodeReadLast( Vec_Int_t * vDec )      {  return (Dec_Node_t *)vDec->pArray + vDec->nSize - 1;  }

/**Function*************************************************************

  Synopsis    [Returns the pointer to the fanins of the i-th decomposition node.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline Dec_Node_t * Dec_NodeFanin0( Vec_Int_t * vDec, int i ) { assert( Dec_NodeRead(vDec,i)->fIntern ); return (Dec_Node_t *)vDec->pArray + Dec_NodeRead(vDec,i)->iFanin0;  }
static inline Dec_Node_t * Dec_NodeFanin1( Vec_Int_t * vDec, int i ) { assert( Dec_NodeRead(vDec,i)->fIntern ); return (Dec_Node_t *)vDec->pArray + Dec_NodeRead(vDec,i)->iFanin1;  }

/**Function*************************************************************

  Synopsis    [Returns the complemented attributes of the i-th decomposition node.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline bool         Dec_NodeFaninC0( Vec_Int_t * vDec, int i ) { assert( Dec_NodeRead(vDec,i)->fIntern ); return (bool)Dec_NodeRead(vDec,i)->fCompl0;  }
static inline bool         Dec_NodeFaninC1( Vec_Int_t * vDec, int i ) { assert( Dec_NodeRead(vDec,i)->fIntern ); return (bool)Dec_NodeRead(vDec,i)->fCompl1;  }

/**Function*************************************************************

  Synopsis    [Returns the number of leaf variables.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline int Dec_TreeNumVars( Vec_Int_t * vDec )
{
    int i;
    for ( i = 0; i < vDec->nSize; i++ )
        if ( vDec->pArray[i] )
            break;
    return i;
}

/**Function*************************************************************

  Synopsis    [Returns the number of AND nodes in the tree.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static int Dec_TreeNumAnds( Vec_Int_t * vDec )
{
    Dec_Node_t * pNode;
    pNode = Dec_NodeReadLast(vDec);
    if ( pNode->fConst ) // constant
        return 0;
    if ( pNode->iFanin0 == pNode->iFanin1 ) // literal
        return 0;
    return vDec->nSize - Dec_TreeNumVars(vDec);
}

/**Function*************************************************************

  Synopsis    [Returns the number of literals in the factored form.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline int Dec_TreeNumFFLits( Vec_Int_t * vDec )
{
    return 1 + Dec_TreeNumAnds( vDec );
}



/**Function*************************************************************

  Synopsis    [Checks if the output node of the decomposition tree is complemented.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline bool Dec_TreeIsComplement( Vec_Int_t * vForm )  { return Dec_NodeReadLast(vForm)->fCompl;  }

/**Function*************************************************************

  Synopsis    [Complements the output node of the decomposition tree.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline void Dec_TreeComplement( Vec_Int_t * vForm )    {  Dec_NodeReadLast(vForm)->fCompl ^= 1;   }


/**Function*************************************************************

  Synopsis    [Checks if the output node is a constant.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline bool Dec_TreeIsConst( Vec_Int_t * vForm )             {   return Dec_NodeReadLast(vForm)->fConst;  }
static inline bool Dec_TreeIsConst0( Vec_Int_t * vForm )            {   return Dec_NodeReadLast(vForm)->fConst &&  Dec_NodeReadLast(vForm)->fCompl;  }
static inline bool Dec_TreeIsConst1( Vec_Int_t * vForm )            {   return Dec_NodeReadLast(vForm)->fConst && !Dec_NodeReadLast(vForm)->fCompl;  }

/**Function*************************************************************

  Synopsis    [Creates a constant 0 decomposition tree.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline Vec_Int_t * Dec_TreeCreateConst0()
{
    Vec_Int_t * vForm;
    Dec_Node_t * pNode;
    // create the constant node
    vForm = Vec_IntAlloc( 1 );
    Vec_IntPush( vForm, 0 );
    pNode = Dec_NodeReadLast( vForm );
    pNode->fIntern = 1;
    pNode->fConst  = 1;
    pNode->fCompl  = 1;
    return vForm;
}

/**Function*************************************************************

  Synopsis    [Creates a constant 1 decomposition tree.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline Vec_Int_t * Dec_TreeCreateConst1()
{
    Vec_Int_t * vForm;
    Dec_Node_t * pNode;
    // create the constant node
    vForm = Vec_IntAlloc( 1 );
    Vec_IntPush( vForm, 0 );
    pNode = Dec_NodeReadLast( vForm );
    pNode->fIntern = 1;
    pNode->fConst  = 1;
    pNode->fCompl  = 0;
    return vForm;
}


/**Function*************************************************************

  Synopsis    [Checks if the decomposition tree is an elementary var.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline bool Dec_TreeIsVar( Vec_Int_t * vForm )
{
    return Dec_NodeReadLast(vForm)->iFanin0 == Dec_NodeReadLast(vForm)->iFanin1;
}

/**Function*************************************************************

  Synopsis    [Creates the decomposition tree to represent an elementary var.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
static inline Vec_Int_t * Dec_TreeCreateVar( int iVar, int nVars, int fCompl )
{
    Vec_Int_t * vForm;
    Dec_Node_t * pNode;
    // create the elementary variable node
    vForm = Vec_IntAlloc( nVars + 1 );
    Vec_IntFill( vForm, nVars + 1, 0 );
    pNode = Dec_NodeReadLast( vForm );
    pNode->iFanin0 = iVar;
    pNode->iFanin1 = iVar;
    pNode->fIntern = 1;
    pNode->fCompl  = fCompl;
    return vForm;
}

////////////////////////////////////////////////////////////////////////
///                       END OF FILE                                ///
////////////////////////////////////////////////////////////////////////

#endif