ABC: A System for Sequential Synthesis and Verification
 
Loading...
Searching...
No Matches
place_bin.c
Go to the documentation of this file.
1/*===================================================================*/
2//
3// place_bin.c
4//
5// Aaron P. Hurst, 2007
6// ahurst@eecs.berkeley.edu
7//
8/*===================================================================*/
9
10#include <stdlib.h>
11#include <stdio.h>
12#include <string.h>
13#include <limits.h>
14#include <assert.h>
15
16//#define DEBUG
17
18#include "place_base.h"
19
21
22
23// --------------------------------------------------------------------
24// Global variables
25//
26// --------------------------------------------------------------------
27
28
29// --------------------------------------------------------------------
30// Function prototypes and local data structures
31//
32// --------------------------------------------------------------------
33
34void spreadDensityX(int numBins, float maxMovement);
35void spreadDensityY(int numBins, float maxMovement);
36
37
38// --------------------------------------------------------------------
39// globalFixDensity()
40//
42// --------------------------------------------------------------------
43void globalFixDensity(int numBins, float maxMovement) {
44
45 printf("QCLN-10 : \tbin-based density correction\n");
46
47 spreadDensityX(numBins, maxMovement);
48 // spreadDensityY(numBins, maxMovement);
49}
50
51
52// --------------------------------------------------------------------
53// spreadDensityX()
54//
55// --------------------------------------------------------------------
56void spreadDensityX(int numBins, float maxMovement) {
57
58 int c, c2, c3, x, y;
59 float totalArea = 0;
60 int moveableCells = 0;
61 float yBinArea = 0, yCumArea = 0;
62 int yBinStart = 0, yBinCount = 0;
63 int xBinCount, xBinStart;
64 float xBinArea, xCumArea;
65 float lastOldEdge;
66 float lastNewEdge;
67 float curOldEdge, curNewEdge;
68 float stretch, w;
69 ConcreteCell *xCell, *yCell;
70 ConcreteCell **binCells;
71 ConcreteCell **allCells;
72
73 binCells = (ConcreteCell **)malloc(sizeof(ConcreteCell*)*g_place_numCells);
74 allCells = (ConcreteCell **)malloc(sizeof(ConcreteCell*)*g_place_numCells);
75
76 for(c=0; c<g_place_numCells; c++) if (g_place_concreteCells[c]) {
78 if (!cell->m_fixed && !cell->m_parent->m_pad) {
79 allCells[moveableCells++] = cell;
80 totalArea += getCellArea(cell);
81 }
82 }
83
84 // spread X
85 qsort(allCells, (size_t)moveableCells, sizeof(ConcreteCell*), cellSortByY);
86
87 y = 0;
88
89 // for each y-bin...
90 for(c=0; c<moveableCells; c++) {
91 yCell = allCells[c];
92 yBinArea += getCellArea(yCell);
93 yCumArea += getCellArea(yCell);
94 yBinCount++;
95
96 // have we filled up a y-bin?
97 if (yCumArea >= totalArea*(y+1)/numBins && yBinArea > 0) {
98 memcpy(binCells, &(allCells[yBinStart]), sizeof(ConcreteCell*)*yBinCount);
99 qsort(binCells, (size_t)yBinCount, sizeof(ConcreteCell*), cellSortByX);
100
101#if defined(DEBUG)
102 printf("y-bin %d count=%d area=%f\n",y,yBinCount, yBinArea);
103#endif
104
105 x = 0;
106 xBinCount = 0, xBinStart = 0;
107 xBinArea = 0, xCumArea = 0;
108 lastOldEdge = g_place_coreBounds.x;
109 lastNewEdge = g_place_coreBounds.x;
110
111 // for each x-bin...
112 for(c2=0; c2<yBinCount; c2++) {
113 xCell = binCells[c2];
114 xBinArea += getCellArea(xCell);
115 xCumArea += getCellArea(xCell);
116 xBinCount++;
117 curOldEdge = xCell->m_x;
118
119 printf("%.3f ", xCell->m_x);
120
121 // have we filled up an x-bin?
122 if (xCumArea >= yBinArea*(x+1)/numBins && xBinArea > 0) {
123 curNewEdge = lastNewEdge + g_place_coreBounds.w*xBinArea/yBinArea;
124
125 if (curNewEdge > g_place_coreBounds.x+g_place_coreBounds.w)
126 curNewEdge = g_place_coreBounds.x+g_place_coreBounds.w;
127 if ((curNewEdge-curOldEdge)>maxMovement) curNewEdge = curOldEdge + maxMovement;
128 if ((curOldEdge-curNewEdge)>maxMovement) curNewEdge = curOldEdge - maxMovement;
129
130#if defined(DEBUG)
131 printf("->\tx-bin %d count=%d area=%f (%f,%f)->(%f,%f)\n",x, xBinCount, xBinArea,
132 curOldEdge, lastOldEdge, curNewEdge, lastNewEdge);
133#endif
134
135 stretch = (curNewEdge-lastNewEdge)/(curOldEdge-lastOldEdge);
136
137 // stretch!
138 for(c3=xBinStart; c3<xBinStart+xBinCount; c3++) {
139 if (curOldEdge == lastOldEdge)
140 binCells[c3]->m_x = lastNewEdge+(c3-xBinStart)*(curNewEdge-lastNewEdge);
141 else
142 binCells[c3]->m_x = lastNewEdge+(binCells[c3]->m_x-lastOldEdge)*stretch;
143
144 // force within core
145 w = binCells[c3]->m_parent->m_width*0.5;
146 if (binCells[c3]->m_x-w < g_place_coreBounds.x)
147 binCells[c3]->m_x = g_place_coreBounds.x+w;
148 if (binCells[c3]->m_x+w > g_place_coreBounds.x+g_place_coreBounds.w)
149 binCells[c3]->m_x = g_place_coreBounds.x+g_place_coreBounds.w-w;
150 }
151
152 lastOldEdge = curOldEdge;
153 lastNewEdge = curNewEdge;
154 x++;
155 xBinCount = 0;
156 xBinArea = 0;
157 xBinStart = c2+1;
158 }
159 }
160
161 y++;
162 yBinCount = 0;
163 yBinArea = 0;
164 yBinStart = c+1;
165 }
166 }
167
168 free(binCells);
169 free(allCells);
170}
171
172
173// --------------------------------------------------------------------
174// spreadDensityY()
175//
176// --------------------------------------------------------------------
177void spreadDensityY(int numBins, float maxMovement) {
178
179 int c, c2, c3, x, y;
180 float totalArea = 0;
181 int moveableCells = 0;
182 float xBinArea = 0, xCumArea = 0;
183 int xBinStart = 0, xBinCount = 0;
184 int yBinCount, yBinStart;
185 float yBinArea, yCumArea;
186 float lastOldEdge;
187 float lastNewEdge;
188 float curOldEdge, curNewEdge;
189 float stretch, h;
190 ConcreteCell *xCell, *yCell;
191 ConcreteCell **binCells;
192 ConcreteCell **allCells;
193
194 binCells = (ConcreteCell **)malloc(sizeof(ConcreteCell*)*g_place_numCells);
195 allCells = (ConcreteCell **)malloc(sizeof(ConcreteCell*)*g_place_numCells);
196
197 for(c=0; c<g_place_numCells; c++) if (g_place_concreteCells[c]) {
199 if (!cell->m_fixed && !cell->m_parent->m_pad) {
200 allCells[moveableCells++] = cell;
201 totalArea += getCellArea(cell);
202 }
203 }
204
205 // spread Y
206 qsort(allCells, moveableCells, sizeof(ConcreteCell*), cellSortByX);
207
208 x = 0;
209
210 // for each x-bin...
211 for(c=0; c<moveableCells; c++) {
212 xCell = allCells[c];
213 xBinArea += getCellArea(xCell);
214 xCumArea += getCellArea(xCell);
215 xBinCount++;
216
217 // have we filled up an x-bin?
218 if (xCumArea >= totalArea*(x+1)/numBins && xBinArea > 0) {
219 memcpy(binCells, &(allCells[xBinStart]), sizeof(ConcreteCell*)*xBinCount);
220 qsort(binCells, (size_t)xBinCount, sizeof(ConcreteCell*), cellSortByY);
221
222 // printf("x-bin %d count=%d area=%f\n",y,yBinCount, yBinArea);
223
224 y = 0;
225 yBinCount = 0, yBinStart = 0;
226 yBinArea = 0, yCumArea = 0;
227 lastOldEdge = g_place_coreBounds.y;
228 lastNewEdge = g_place_coreBounds.y;
229
230 // for each y-bin...
231 for(c2=0; c2<xBinCount; c2++) {
232 yCell = binCells[c2];
233 yBinArea += getCellArea(yCell);
234 yCumArea += getCellArea(yCell);
235 yBinCount++;
236 curOldEdge = yCell->m_y;
237
238 // have we filled up an x-bin?
239 if (yCumArea >= xBinArea*(y+1)/numBins && yBinArea > 0) {
240 curNewEdge = lastNewEdge + g_place_coreBounds.h*yBinArea/xBinArea;
241
242 if (curNewEdge > g_place_coreBounds.y+g_place_coreBounds.h)
243 curNewEdge = g_place_coreBounds.y+g_place_coreBounds.h;
244 if ((curNewEdge-curOldEdge)>maxMovement) curNewEdge = curOldEdge + maxMovement;
245 if ((curOldEdge-curNewEdge)>maxMovement) curNewEdge = curOldEdge - maxMovement;
246
247 if (curOldEdge == lastOldEdge) continue; // hmmm
248 stretch = (curNewEdge-lastNewEdge)/(curOldEdge-lastOldEdge);
249
250 // stretch!
251 for(c3=yBinStart; c3<yBinStart+yBinCount; c3++) {
252 binCells[c3]->m_y = lastNewEdge+(binCells[c3]->m_y-lastOldEdge)*stretch;
253
254 // force within core
255 h = binCells[c3]->m_parent->m_height;
256 if (binCells[c3]->m_y-h < g_place_coreBounds.y)
257 binCells[c3]->m_y = g_place_coreBounds.y+h;
258 if (binCells[c3]->m_y+h > g_place_coreBounds.y+g_place_coreBounds.h)
259 binCells[c3]->m_y = g_place_coreBounds.y+g_place_coreBounds.h-h;
260 }
261
262 lastOldEdge = curOldEdge;
263 lastNewEdge = curNewEdge;
264 y++;
265 yBinCount = 0;
266 yBinArea = 0;
267 yBinStart = c2+1;
268 }
269 }
270
271 x++;
272 xBinCount = 0;
273 xBinArea = 0;
274 xBinStart = c+1;
275 }
276 }
277
278 free(binCells);
279 free(allCells);
280}
282
#define ABC_NAMESPACE_IMPL_START
#define ABC_NAMESPACE_IMPL_END
ConcreteCell ** g_place_concreteCells
Definition place_base.c:33
float getCellArea(const ConcreteCell *cell)
Definition place_base.c:99
int cellSortByY(const void *a, const void *b)
Definition place_base.c:326
ABC_NAMESPACE_IMPL_START int g_place_numCells
Definition place_base.c:26
Rect g_place_coreBounds
Definition place_base.c:30
int cellSortByX(const void *a, const void *b)
Sorts cells by either position coordinate.
Definition place_base.c:314
void globalFixDensity(int numBins, float maxMovement)
Doesn't deal well with fixed cells in the core area.
Definition place_bin.c:43
void spreadDensityY(int numBins, float maxMovement)
Definition place_bin.c:177
ABC_NAMESPACE_IMPL_START void spreadDensityX(int numBins, float maxMovement)
Definition place_bin.c:56
float m_width
Definition place_base.h:45
float m_height
Definition place_base.h:45
AbstractCell * m_parent
Definition place_base.h:57
char * memcpy()
VOID_HACK free()
char * malloc()