diff --git a/chamsin/etc/technology.hcmos9.dtr.xml b/chamsin/etc/technology.hcmos9.dtr.xml
index a07f4e53..6d24c699 100644
--- a/chamsin/etc/technology.hcmos9.dtr.xml
+++ b/chamsin/etc/technology.hcmos9.dtr.xml
@@ -1,7 +1,23 @@
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/chamsin/src/analogic/Transistor.cpp b/chamsin/src/analogic/Transistor.cpp
index ed9f426f..d5287a60 100644
--- a/chamsin/src/analogic/Transistor.cpp
+++ b/chamsin/src/analogic/Transistor.cpp
@@ -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();
}
diff --git a/chamsin/src/analogic/Transistor.h b/chamsin/src/analogic/Transistor.h
index 0536e843..a6173732 100644
--- a/chamsin/src/analogic/Transistor.h
+++ b/chamsin/src/analogic/Transistor.h
@@ -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);
};
diff --git a/chamsin/src/technology/AEnv.cpp b/chamsin/src/technology/AEnv.cpp
index 206b085d..02599b3d 100644
--- a/chamsin/src/technology/AEnv.cpp
+++ b/chamsin/src/technology/AEnv.cpp
@@ -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("");
}
diff --git a/chamsin/src/technology/ATechnology.cpp b/chamsin/src/technology/ATechnology.cpp
index 9113d9fd..08825bf3 100644
--- a/chamsin/src/technology/ATechnology.cpp
+++ b/chamsin/src/technology/ATechnology.cpp
@@ -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 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 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, "");
diff --git a/chamsin/src/technology/ATechnology.h b/chamsin/src/technology/ATechnology.h
index b7c9ab28..d3deb8c3 100644
--- a/chamsin/src/technology/ATechnology.h
+++ b/chamsin/src/technology/ATechnology.h
@@ -40,28 +40,9 @@ class ATechnology : public PrivateProperty {
typedef pair LayerPair;
- struct LayerPairCompare:
- public std::binary_function {
- 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 PhysicalRules;
typedef map OneLayerPhysicalRules;
- typedef map TwoLayersPhysicalRules;
+ typedef map TwoLayersPhysicalRules;
static ATechnology* create(Hurricane::Technology* technology);
static ATechnology* getATechnology(Hurricane::Technology* technology);
diff --git a/chamsin/src/tests/AnalogicTest.cpp b/chamsin/src/tests/AnalogicTest.cpp
index 888c51f1..e38af41e 100644
--- a/chamsin/src/tests/AnalogicTest.cpp
+++ b/chamsin/src/tests/AnalogicTest.cpp
@@ -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) {