00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042 #include <math.h>
00043 #include "FPcommon.h"
00044 #include "DB.h"
00045 #include "AnalytSolve.h"
00046 #include "CommandLine.h"
00047 using namespace parquetfp;
00048
00049 AnalytSolve::AnalytSolve(Command_Line* params, DB* db)
00050 :_params(params), _db(db)
00051 {}
00052
00053 Point AnalytSolve::getDesignOptLoc()
00054 {
00055 Point finalLoc;
00056 Nodes *nodes = _db->getNodes();
00057 Nets *nets = _db->getNets();
00058 itNode node;
00059 itNodePin nodePin;
00060 itPin netPin;
00061 vector<bool> netsSeen(nets->getNumNets(), 0);
00062
00063 double xSum = 0;
00064 double ySum = 0;
00065 double netXSum = 0;
00066 double netYSum = 0;
00067 unsigned netDegree = 0;
00068 unsigned nodeDegree = 0;
00069 bool pinType=0;
00070 double xOffset;
00071 double yOffset;
00072
00073 for(node = nodes->terminalsBegin(); node != nodes->terminalsEnd(); ++node)
00074 {
00075 for(nodePin = node->pinsBegin(); nodePin != node->pinsEnd(); ++nodePin)
00076 {
00077 unsigned netIndex = nodePin->netIndex;
00078 if(!netsSeen[netIndex])
00079 {
00080 ++nodeDegree;
00081 netsSeen[netIndex] = 1;
00082 Net& net = nets->getNet(netIndex);
00083
00084 netDegree = 0;
00085 netXSum = 0;
00086 netYSum = 0;
00087
00088 for(netPin = net.pinsBegin(); netPin != net.pinsEnd(); ++netPin)
00089 {
00090 pinType = netPin->getType();
00091 int currNodeIndex = netPin->getNodeIndex();
00092
00093 if(!pinType)
00094 {
00095 Node& currNode = nodes->getNode(currNodeIndex);
00096 double width = currNode.getWidth();
00097 double height = currNode.getHeight();
00098 xOffset = netPin->getXOffset()*width + width/2;
00099 yOffset = netPin->getYOffset()*height + height/2;
00100 netXSum -= (currNode.getX() +xOffset);
00101 netYSum -= (currNode.getY() +yOffset);
00102 }
00103 else
00104 {
00105 ++netDegree;
00106 Node& terminal = nodes->getTerminal(currNodeIndex);
00107 netXSum += terminal.getX();
00108 netYSum += terminal.getY();
00109 }
00110 }
00111 if(netDegree > 0)
00112 {
00113 netXSum = netXSum/netDegree;
00114 netYSum = netYSum/netDegree;
00115 xSum += netXSum;
00116 ySum += netYSum;
00117 }
00118 }
00119 }
00120 }
00121 if(nodeDegree != 0)
00122 {
00123 xSum /= nodeDegree;
00124 ySum /= nodeDegree;
00125 finalLoc.x = xSum;
00126 finalLoc.y = ySum;
00127 }
00128 else
00129 {
00130 finalLoc.x = 0;
00131 finalLoc.y = 0;
00132 }
00133
00134
00135
00136
00137
00138
00139 return finalLoc;
00140 }
00141
00142
00143
00144 Point AnalytSolve::getOptLoc(int index, vector<double>& xloc,
00145 vector<double>& yloc)
00146 {
00147 Point finalLoc;
00148 Nodes *nodes = _db->getNodes();
00149 Nets *nets = _db->getNets();
00150 Node& node = nodes->getNode(index);
00151 itNodePin nodePin;
00152 itPin netPin;
00153 double xSum = 0;
00154 double ySum = 0;
00155 double netXSum = 0;
00156 double netYSum = 0;
00157 unsigned netDegree = 0;
00158 unsigned nodeDegree = node.getDegree();
00159 bool pinType=0;
00160 double xOffset;
00161 double yOffset;
00162
00163 double nodeXOffset;
00164 double nodeYOffset;
00165 double nodeWidth = node.getWidth();
00166 double nodeHeight= node.getHeight();
00167
00168 for(nodePin = node.pinsBegin(); nodePin != node.pinsEnd(); ++nodePin)
00169 {
00170 unsigned netIndex = nodePin->netIndex;
00171 Net& net = nets->getNet(netIndex);
00172 unsigned pinIndex = nodePin->pinOffset;
00173 pin& thisPin = net.getPin(pinIndex);
00174 nodeXOffset = thisPin.getXOffset()*nodeWidth + nodeWidth/2;
00175 nodeYOffset = thisPin.getYOffset()*nodeHeight + nodeHeight/2;
00176
00177 netDegree = net.getDegree();
00178 netXSum = 0;
00179 netYSum = 0;
00180
00181 for(netPin = net.pinsBegin(); netPin != net.pinsEnd(); ++netPin)
00182 {
00183 pinType = netPin->getType();
00184 int currNodeIndex = netPin->getNodeIndex();
00185
00186 if(!pinType && currNodeIndex == index)
00187 {
00188 --netDegree;
00189
00190 }
00191 else
00192 {
00193
00194 if(!pinType)
00195 {
00196 Node& currNode = nodes->getNode(currNodeIndex);
00197 double width = currNode.getWidth();
00198 double height = currNode.getHeight();
00199 xOffset = netPin->getXOffset()*width + width/2;
00200 yOffset = netPin->getYOffset()*height + height/2;
00201 netXSum += (xloc[currNodeIndex] +xOffset-nodeXOffset);
00202 netYSum += (yloc[currNodeIndex] +yOffset-nodeYOffset);
00203 }
00204 else
00205 {
00206 Node& terminal = nodes->getTerminal(currNodeIndex);
00207 netXSum += terminal.getX();
00208 netYSum += terminal.getY();
00209 }
00210 }
00211 }
00212 if(netDegree > 0)
00213 {
00214 netXSum = netXSum/netDegree;
00215 netYSum = netYSum/netDegree;
00216 xSum += netXSum;
00217 ySum += netYSum;
00218 }
00219 }
00220
00221 if(nodeDegree != 0)
00222 {
00223 xSum /= nodeDegree;
00224 ySum /= nodeDegree;
00225 finalLoc.x = xSum;
00226 finalLoc.y = ySum;
00227 }
00228 else
00229 {
00230 finalLoc.x = 0;
00231 finalLoc.y = 0;
00232 }
00233 return finalLoc;
00234
00235 }
00236
00237 void AnalytSolve::solveSOR()
00238 {
00239 _xloc = _db->getXLocs();
00240 _yloc = _db->getYLocs();
00241
00242 double epsilon = sqrt(_db->getNodesArea());
00243 Point newLoc;
00244 double change = 1e100;
00245 double indChange=0;
00246 unsigned numIter = 0;
00247 double xchange;
00248 double ychange;
00249 double overshoot;
00250
00251 while(change > epsilon && numIter < 1000000)
00252 {
00253 numIter++;
00254 change = 0;
00255 for(unsigned i=0; i<_xloc.size(); ++i)
00256 {
00257 newLoc = getOptLoc(i, _xloc, _yloc);
00258 xchange = newLoc.x - _xloc[i];
00259 ychange = newLoc.y - _yloc[i];
00260 overshoot = xchange*1.7;
00261 _xloc[i] += overshoot;
00262
00263 overshoot = ychange*1.7;
00264 _yloc[i] += overshoot;
00265
00266 indChange = fabs(xchange) + fabs(ychange);
00267
00268 change += indChange;
00269 }
00270
00271 }
00272 }