getDataBase -> DataBase::getDB()
Transistor layout ... in progress XML DTR technology parsing
This commit is contained in:
parent
f47f6b92e5
commit
2f31e8ef3d
|
@ -1,7 +1,23 @@
|
|||
<technology name="hcmos9">
|
||||
<physical_rules>
|
||||
<rule name="L_TRANS" value="0.13" ref="13-1.a"/>
|
||||
<rule name="RD" layer="diff" value="0.21" ref="2-3"/>
|
||||
<rule name="RE" layer1="nImplant" layer2="GATE" value="0.4" ref="16-6"/>
|
||||
<rule name="minWidth" layer="cut0" value="0.16" ref="19-1"/>
|
||||
<rule name="minExtension" layer1="poly" layer2="cut0" value="0.07" ref="19-3"/>
|
||||
|
||||
<rule name="minExtension" layer1="nImplant" layer2="poly" value="0.2" ref="16-17"/>
|
||||
<rule name="minExtension" layer1="nImplant" layer2="active" value="0.18" ref="16-8"/>
|
||||
|
||||
<rule name="minExtension" layer1="pImplant" layer2="poly" value="0.2" ref="17-17"/>
|
||||
<rule name="minExtension" layer1="pImplant" layer2="active" value="0.18" ref="17-8"/>
|
||||
|
||||
<rule name="minExtension" layer1="active" layer2="cut0" value="0.07" ref="19-4.a"/>
|
||||
<rule name="minExtension" layer1="pImplant" layer2="cut0" value="0.09" ref="19-4.b"/>
|
||||
<rule name="minExtension" layer1="nImplant" layer2="cut0" value="0.09" ref="19-4.c"/>
|
||||
|
||||
<rule name="minSpacing" layer1="active" layer2="cut0" value="0.14" ref="19-5"/>
|
||||
<rule name="minSpacing" layer1="active" layer2="poly" value="0.07" ref="13-5"/>
|
||||
|
||||
<rule name="minGateExtension" layer1="poly" layer2="active" value="0.18" ref="13-7"/>
|
||||
|
||||
|
||||
</physical_rules>
|
||||
</technology>
|
||||
|
|
|
@ -11,12 +11,6 @@ using namespace Hurricane;
|
|||
namespace {
|
||||
|
||||
|
||||
Pad* createPad(Technology* technology, Net* net, const string& layerName) {
|
||||
Layer* layer = technology->getLayer(Name(layerName));
|
||||
Pad* pad = Pad::create(net, layer, Box());
|
||||
return pad;
|
||||
}
|
||||
|
||||
|
||||
void createContactMatrix(Net* net, const Layer* layer, const Box& box, unsigned columns,
|
||||
const DbU::Unit& rwCont, const DbU::Unit& rdCont) {
|
||||
|
@ -45,7 +39,19 @@ void createContactMatrix(Net* net, const Layer* layer, const Box& box, unsigned
|
|||
}
|
||||
}
|
||||
|
||||
Layer* getLayer(const string& layerStr) {
|
||||
Layer* getLayer(Technology* technology, const string& layerStr) {
|
||||
Layer* layer = technology->getLayer(layerStr);
|
||||
if (!layer) {
|
||||
throw Error("Unknown Layer : " + layerStr);
|
||||
}
|
||||
return layer;
|
||||
}
|
||||
|
||||
Pad* createPad(Technology* technology, Net* net, const string& layerName) {
|
||||
static Box emptyBox(0, 0, 0, 0);
|
||||
Layer* layer = getLayer(technology, layerName);
|
||||
Pad* pad = Pad::create(net, layer, emptyBox);
|
||||
return pad;
|
||||
}
|
||||
|
||||
|
||||
|
@ -85,7 +91,7 @@ Transistor* Transistor::create(Library* library, const Name& name, const Polarit
|
|||
|
||||
void Transistor::_postCreate() {
|
||||
Inherit::_postCreate();
|
||||
DataBase* db = getDataBase();
|
||||
DataBase* db = DataBase::getDB();
|
||||
Technology* technology = db->getTechnology();
|
||||
_drain = Net::create(this, DrainName);
|
||||
_drain->setExternal(true);
|
||||
|
@ -105,51 +111,85 @@ void Transistor::_postCreate() {
|
|||
_grid30 = createPad(technology, _grid, "cut0");
|
||||
_grid31 = createPad(technology, _grid, "metal1");
|
||||
_anonymous10 = createPad(technology, _anonymous, "active");
|
||||
_anonymous11 = createPad(technology, _anonymous, "nimp");
|
||||
_anonymous12 = createPad(technology, _anonymous, "nimp");
|
||||
if (_polarity == N) {
|
||||
_anonymous11 = createPad(technology, _anonymous, "nImplant");
|
||||
_anonymous12 = createPad(technology, _anonymous, "nImplant");
|
||||
} else {
|
||||
_anonymous11 = createPad(technology, _anonymous, "pImplant");
|
||||
_anonymous12 = createPad(technology, _anonymous, "pImplant");
|
||||
}
|
||||
}
|
||||
|
||||
void Transistor::createLayout() {
|
||||
ATechnology* techno = AEnv::getATechnology();
|
||||
DataBase* db = DataBase::getDB();
|
||||
if (!db) {
|
||||
throw Error("Error : no DataBase");
|
||||
}
|
||||
Technology* techno = db->getTechnology();
|
||||
if (!techno) {
|
||||
throw Error("Error : no Technology");
|
||||
}
|
||||
ATechnology* atechno = AEnv::getATechnology();
|
||||
|
||||
DbU::Unit rwCont = techno->getPhysicalRule("RW_CONT")->getValue();
|
||||
DbU::Unit rdCont = techno->getPhysicalRule("RD_CONT")->getValue();
|
||||
DbU::Unit reGateActiv = techno->getPhysicalRule("RE", getLayer("poly"), getLayer("active"))->getValue();
|
||||
DbU::Unit rePolyCont = techno->getPhysicalRule("RE", getLayer("poly"), getLayer("cut"))->getValue();
|
||||
DbU::Unit rdActiveCont = techno->getPhysicalRule("RD", getLayer("active"), getLayer("cut"))->getValue();
|
||||
DbU::Unit rdActivePoly = techno->getPhysicalRule("RD", getLayer("active"), getLayer("poly"))->getValue();
|
||||
DbU::Unit widthCut0 = atechno->getPhysicalRule("minWidth", getLayer(techno, "cut0"))->getValue();
|
||||
DbU::Unit extGateActive = atechno->getPhysicalRule("minGateExtension",
|
||||
getLayer(techno, "poly"), getLayer(techno, "active"))->getValue();
|
||||
DbU::Unit extPolyCut0 = atechno->getPhysicalRule("minExtension",
|
||||
getLayer(techno, "poly"), getLayer(techno, "cut0"))->getValue();
|
||||
DbU::Unit spacingActiveCut0 = atechno->getPhysicalRule("minSpacing",
|
||||
getLayer(techno, "active"), getLayer(techno, "cut0"))->getValue();
|
||||
DbU::Unit spacingActivePoly = atechno->getPhysicalRule("minSpacing",
|
||||
getLayer(techno, "active"), getLayer(techno, "poly"))->getValue();
|
||||
DbU::Unit extImplantPoly = 0;
|
||||
DbU::Unit extImplantActive = 0;
|
||||
DbU::Unit extImplantCut0 = 0;
|
||||
if (_polarity == N) {
|
||||
extImplantPoly = atechno->getPhysicalRule("minExtension",
|
||||
getLayer(techno, "nImplant"), getLayer(techno, "poly"))->getValue();
|
||||
extImplantActive = atechno->getPhysicalRule("minExtension",
|
||||
getLayer(techno, "nImplant"), getLayer(techno, "active"))->getValue();
|
||||
extImplantCut0 = atechno->getPhysicalRule("minExtension",
|
||||
getLayer(techno, "nImplant"), getLayer(techno, "cut0"))->getValue();
|
||||
} else {
|
||||
extImplantPoly = atechno->getPhysicalRule("minExtension",
|
||||
getLayer(techno, "pImplant"), getLayer(techno, "poly"))->getValue();
|
||||
extImplantActive = atechno->getPhysicalRule("minExtension",
|
||||
getLayer(techno, "pImplant"), getLayer(techno, "active"))->getValue();
|
||||
extImplantCut0 = atechno->getPhysicalRule("minExtension",
|
||||
getLayer(techno, "pImplant"), getLayer(techno, "cut0"))->getValue();
|
||||
}
|
||||
|
||||
UpdateSession::open();
|
||||
|
||||
//grid 00
|
||||
DbU::Unit x00 = 0;
|
||||
DbU::Unit y00 = -reGateActiv;
|
||||
DbU::Unit y00 = -extGateActive;
|
||||
DbU::Unit dx00 = _l;
|
||||
DbU::Unit dy00 = _w - y00*2;
|
||||
Box box00(x00, y00, dx00, dy00);
|
||||
_grid00->setBoundingBox(box00);
|
||||
|
||||
//grid30
|
||||
DbU::Unit toto = rwCont + 2*rePolyCont;
|
||||
DbU::Unit maxValue = widthCut0 + 2*extPolyCut0;
|
||||
DbU::Unit x30 = 0, dx30 = 0, y30 = 0, dy30 = 0;
|
||||
if (toto > _l) {
|
||||
dx30 = rwCont;
|
||||
if (maxValue > _l) {
|
||||
dx30 = widthCut0;
|
||||
dy30 = dx30;
|
||||
y30 = _w + max(rdActiveCont, rdActivePoly + rePolyCont);
|
||||
y30 = _w + max(spacingActiveCut0, spacingActivePoly + extPolyCut0);
|
||||
} else {
|
||||
dx30 = dx00 - 2*rePolyCont;
|
||||
dy30 = rwCont;
|
||||
y30 = _w + rdActiveCont;
|
||||
dx30 = dx00 - 2*extPolyCut0;
|
||||
dy30 = widthCut0;
|
||||
y30 = _w + spacingActiveCut0;
|
||||
}
|
||||
x30 = x00 + dx00/2 - dx30/2;
|
||||
Box box30(x30, y30, dx30, dy30);
|
||||
_grid30->setBoundingBox(box30);
|
||||
|
||||
//grid31
|
||||
DbU::Unit dx31 = dx30 + 2*rePolyCont;
|
||||
DbU::Unit dy31 = dy30 + 2*rePolyCont;
|
||||
DbU::Unit x31 = x30 - rePolyCont;
|
||||
DbU::Unit y31 = y30 - rePolyCont;
|
||||
DbU::Unit dx31 = dx30 + 2*extPolyCut0;
|
||||
DbU::Unit dy31 = dy30 + 2*extPolyCut0;
|
||||
DbU::Unit x31 = x30 - extPolyCut0;
|
||||
DbU::Unit y31 = y30 - extPolyCut0;
|
||||
Box box31(x31, y31, dx31, dy31);
|
||||
_grid31->setBoundingBox(box31);
|
||||
|
||||
|
@ -163,8 +203,18 @@ void Transistor::createLayout() {
|
|||
dx01 = dx00;
|
||||
dy01 = y31 - (y00 + dy00);
|
||||
}
|
||||
Box box01(x01, y01, dx01, dy01);
|
||||
_grid01->setBoundingBox(box01);
|
||||
|
||||
//12
|
||||
//anonymous12
|
||||
DbU::Unit x12 = min(x31, x00) - extImplantPoly;
|
||||
DbU::Unit y12 = min(0 - extImplantActive, y00 - extImplantPoly);
|
||||
DbU::Unit dx12 = max(dx31, dx00) + 2 * extImplantPoly;
|
||||
DbU::Unit yMax = max( max(y30 + dy30 + extImplantCut0, max(y31 + dy31, y00 + dy00) + extImplantPoly), _w + extImplantActive);
|
||||
DbU::Unit dy12 = yMax - y12;
|
||||
|
||||
Box box12(x12, y12, dx12, dy12);
|
||||
_anonymous12->setBoundingBox(box12);
|
||||
|
||||
UpdateSession::close();
|
||||
}
|
||||
|
|
|
@ -43,7 +43,7 @@ class Transistor : public Cell {
|
|||
Pad *_source20, *_source22;
|
||||
Pad *_drain40, *_drain42;
|
||||
Pad *_grid00, *_grid01, *_grid30, *_grid31;
|
||||
Pad *_anonymous10, *_anonymous11, *_anonymous12, *_anonymous50;
|
||||
Pad *_anonymous10, *_anonymous11, *_anonymous12;
|
||||
|
||||
Transistor(Library* library, const Name& name, const Polarity& polarity);
|
||||
};
|
||||
|
|
|
@ -13,7 +13,7 @@ using namespace CRL;
|
|||
#include "AEnv.h"
|
||||
|
||||
void AEnv::create(const char* technoFilePath, const char* graphicFilePath, const char* analogTechnoFilePath) {
|
||||
DataBase* db = getDataBase();
|
||||
DataBase* db = DataBase::getDB();
|
||||
if (db) {
|
||||
throw Error("");
|
||||
}
|
||||
|
@ -27,7 +27,7 @@ void AEnv::create(const char* technoFilePath, const char* graphicFilePath, const
|
|||
}
|
||||
|
||||
ATechnology* AEnv::getATechnology() {
|
||||
DataBase* db = getDataBase();
|
||||
DataBase* db = DataBase::getDB();
|
||||
if (!db) {
|
||||
throw Error("");
|
||||
}
|
||||
|
|
|
@ -6,7 +6,7 @@ using namespace Hurricane;
|
|||
namespace {
|
||||
static Name ATechnologyPropertyName("ATechnologyProperty");
|
||||
|
||||
void printPhysicalRules(ATechnology::PhysicalRules& physicalRules) {
|
||||
void printPhysicalRules(const ATechnology::PhysicalRules& physicalRules) {
|
||||
for (ATechnology::PhysicalRules::iterator prit = physicalRules.begin();
|
||||
prit != physicalRules.end();
|
||||
prit++) {
|
||||
|
@ -42,8 +42,7 @@ void ATechnology::addPhysicalRule(const Name& name, const Name& layerName, DbU::
|
|||
OneLayerPhysicalRules::iterator olprit = _oneLayerPhysicalRules.find(layer);
|
||||
if (olprit == _oneLayerPhysicalRules.end()) {
|
||||
pair<OneLayerPhysicalRules::iterator, bool> result =
|
||||
_oneLayerPhysicalRules.insert(make_pair(layer, PhysicalRules()));
|
||||
assert(result.second);
|
||||
_oneLayerPhysicalRules.insert(OneLayerPhysicalRules::value_type(layer, PhysicalRules()));
|
||||
olprit = result.first;
|
||||
PhysicalRule* newPhysicalRule = new PhysicalRule(name, value, reference);
|
||||
olprit->second.insert(newPhysicalRule);
|
||||
|
@ -60,6 +59,25 @@ void ATechnology::addPhysicalRule(const Name& name, const Name& layerName, DbU::
|
|||
|
||||
void ATechnology::addPhysicalRule(const Name& name, const Name& layer1Name,
|
||||
const Name& layer2Name, DbU::Unit value, const string& reference) {
|
||||
Layer* layer1 = getLayer(layer1Name);
|
||||
Layer* layer2 = getLayer(layer2Name);
|
||||
LayerPair layerPair(layer1, layer2);
|
||||
TwoLayersPhysicalRules::iterator tlprit = _twoLayersPhysicalRules.find(layerPair);
|
||||
if (tlprit == _twoLayersPhysicalRules.end()) {
|
||||
pair<TwoLayersPhysicalRules::iterator, bool> result =
|
||||
_twoLayersPhysicalRules.insert(TwoLayersPhysicalRules::value_type(layerPair, PhysicalRules()));
|
||||
tlprit = result.first;
|
||||
PhysicalRule* newPhysicalRule = new PhysicalRule(name, value, reference);
|
||||
tlprit->second.insert(newPhysicalRule);
|
||||
} else {
|
||||
PhysicalRules& physicalRules = tlprit->second;
|
||||
PhysicalRule searchPR(name, 0, "");
|
||||
if (physicalRules.find(&searchPR) != physicalRules.end()) {
|
||||
throw Error("duplicate rule");
|
||||
}
|
||||
PhysicalRule* newPhysicalRule = new PhysicalRule(name, value, reference);
|
||||
physicalRules.insert(newPhysicalRule);
|
||||
}
|
||||
}
|
||||
|
||||
ATechnology* ATechnology::create(Technology* technology) {
|
||||
|
@ -141,7 +159,8 @@ const ATechnology::PhysicalRule* ATechnology::getPhysicalRule(
|
|||
throw Error("Cannot find Physical Rules for layers " +
|
||||
getString(layer1->getName()) +
|
||||
" and " +
|
||||
getString(layer2->getName()));
|
||||
getString(layer2->getName()) +
|
||||
" (searching Rule : " + getString(name) +")");
|
||||
}
|
||||
const PhysicalRules& physicalRules = tlprit->second;
|
||||
PhysicalRule searchPR(name, 0, "");
|
||||
|
|
|
@ -40,28 +40,9 @@ class ATechnology : public PrivateProperty {
|
|||
|
||||
typedef pair<const Layer*, const Layer*> LayerPair;
|
||||
|
||||
struct LayerPairCompare:
|
||||
public std::binary_function<const LayerPair&, const LayerPair&, bool> {
|
||||
bool operator()(const LayerPair& lp1, const LayerPair& lp2) const {
|
||||
if (lp1.first < lp2.first) {
|
||||
return -1;
|
||||
}
|
||||
if (lp1.first > lp2.first) {
|
||||
return 1;
|
||||
}
|
||||
if (lp1.second < lp2.second) {
|
||||
return -1;
|
||||
}
|
||||
if (lp1.second > lp2.second) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
};
|
||||
|
||||
typedef set<ATechnology::PhysicalRule*, PhysicalRuleNameCompare> PhysicalRules;
|
||||
typedef map<const Layer*, PhysicalRules> OneLayerPhysicalRules;
|
||||
typedef map<LayerPair, PhysicalRules, LayerPairCompare> TwoLayersPhysicalRules;
|
||||
typedef map<LayerPair, PhysicalRules> TwoLayersPhysicalRules;
|
||||
|
||||
static ATechnology* create(Hurricane::Technology* technology);
|
||||
static ATechnology* getATechnology(Hurricane::Technology* technology);
|
||||
|
|
|
@ -24,7 +24,7 @@ int main(int argc, char* argv[]) {
|
|||
exit(56);
|
||||
}
|
||||
AEnv::create(argv[1], argv[2], argv[3]);
|
||||
DataBase* db = getDataBase();
|
||||
DataBase* db = DataBase::getDB();
|
||||
Library* rootLibrary = db->getRootLibrary();
|
||||
Library* userLibrary = Library::create(rootLibrary, Name("USER"));
|
||||
|
||||
|
@ -34,6 +34,7 @@ int main(int argc, char* argv[]) {
|
|||
}
|
||||
aTechnology->print();
|
||||
Transistor* trans = Transistor::create(userLibrary, Name("TEST"), Transistor::P);
|
||||
trans->createLayout();
|
||||
cerr << trans << endl;
|
||||
exit(0);
|
||||
} catch (Hurricane::Warning& w) {
|
||||
|
|
Loading…
Reference in New Issue