NewRouteTechnologyImpl.mesa
Copyright Ó 1985, 1987 by Xerox Corporation. All rights reserved.
Bryan Preas, July 10, 1985 11:14:39 am PDT
last edited Bryan Preas, July 16, 1987 4:55:54 pm PDT
DIRECTORY
CD, CDAtomicObjects, CDSimpleRules, DABasics, DesignRules, Route, NewRouteTechnology;
NewRouteTechnologyImpl: CEDAR PROGRAM
IMPORTS CD, CDAtomicObjects, CDSimpleRules, DesignRules, Route
EXPORTS NewRouteTechnology = {
Widths and Spacings
GetWidth: PUBLIC PROC [rules: DesignRules.Rules, layer: CD.Layer] RETURNS [CD.Number] = {
RETURN[CDSimpleRules.MinWidth[NIL, layer]]};
GetSpacing: PUBLIC PROC [rules: DesignRules.Rules, layer: CD.Layer] RETURNS [CD.Number] = {
RETURN[CDSimpleRules.MinSpace[NIL, layer, layer]]};
ContactSize: PUBLIC PROC [contact: CD.Object] RETURNS [CD.Number] = {
r: CD.Rect ← CD.InterestRect[contact];
RETURN[MAX[ABS[r.x2 - r.x1], ABS[r.y2 - r.y1]]]};
GetMaterialToContact: PUBLIC PROC [rules: DesignRules.Rules, layer: CD.Layer, contact: CD.Object] RETURNS [dist: CD.Number] = {
This is a hack. It needs to be replaced
matToContact: CD.Number ← DesignRules.MinSpace[rules, layer, layer].s + ContactSize[contact]/2 + DesignRules.MinWidth[rules, layer].w/2;
contactToContact: CD.Number ← DesignRules.MinSpace[rules, layer, layer].s + ContactSize[contact];
RETURN[MAX[matToContact, contactToContact]]};
Layers
LToTech: PUBLIC PROC [layer: CD.Layer] RETURNS [tech: CD.Technology] = {
tech ← CD.LayerTechnology[layer ! CD.Error => GOTO bad];
IF tech=NIL THEN Route.Error[callingError, "Invalid layer"];
EXITS bad => Route.Error[callingError, "Invalid layer"]};
Contacts
GetContact: PUBLIC PROC [layer1, layer2: CD.Layer] RETURNS [CD.Object] = {
-- Create a big contact; may return the same object
-- on multiple calls; the contact object should be considered
-- to be read-only.
RETURN[CDSimpleRules.Contact[NIL, layer1, layer2]]};
GetBigContact: PUBLIC PROC [size: DABasics.Position, layer1, layer2: CD.Layer] RETURNS [obj: CD.Object ← NIL] = {
-- Create a big contact; may return NIL (if big contacts aren't defined
-- may return the same object
-- on multiple calls; the contact object should be considered
-- to be read-only.
l1a: ATOMCD.LayerKey[layer1];
l2a: ATOMCD.LayerKey[layer2];
tech: CD.Technology ← LToTech[layer1];
IF tech # LToTech[layer2] THEN Route.Error[callingError, "Invalid layers"];
SELECT tech.key FROM
$cmos => NULL;
$cmosB => {
SELECT TRUE FROM
(l1a = $met2 AND l2a = $met) OR (l1a = $met AND l2a = $met2) => obj ← CDAtomicObjects.CreateAtomicOb[$C2LargeVia, size, tech];
(l1a = $pol AND l2a = $met) => obj �tomicObjects.CreateAtomicOb[$C2LargeSimpleCon, size, tech, layer1];
(l1a = $met AND l2a = $pol) => obj �tomicObjects.CreateAtomicOb[$C2LargeSimpleCon, size, tech, layer2];
ENDCASE => Route.Error[callingError, "Invalid layers"]};
ENDCASE => Route.Error[callingError, "Unsupported technology"]};
Simple Design Rules
CmosDesignRules: PUBLIC PROC [rules: DesignRules.Rules, designRuleParms: Route.DesignRulesParameters] RETURNS[designRules: Route.DesignRules ← NEW[Route.DesignRulesRec]] = {
Define the routing design rules for CMOS double or single layer metal.
cndObj: CD.Object;
designRules.trunkDirection ← designRuleParms.trunkDirection;
designRules.branchDirection ← IF designRuleParms.trunkDirection = horizontal THEN vertical ELSE horizontal;
designRules.trunkLayer ← IF designRuleParms.trunkDirection = horizontal THEN designRuleParms.horizLayer ELSE designRuleParms.vertLayer;
designRules.branchLayer ← IF designRuleParms.trunkDirection = horizontal THEN designRuleParms.vertLayer ELSE designRuleParms.horizLayer;
cndObj ← GetContact[designRules.trunkLayer, designRules.branchLayer];
designRules.branchWidth ← DesignRules.MinWidth[rules, designRules.branchLayer].w;
designRules.branchSpacing ← DesignRules.MinSpace[rules, designRules.branchLayer, designRules.branchLayer].s;
designRules.branchToContact ← GetMaterialToContact[rules, designRules.branchLayer, cndObj];
designRules.trunkToTrunk ← designRuleParms.trunkToTrunk;
designRules.branchToBranch ← MAX[designRules.branchWidth + designRules.branchSpacing, designRules.branchToContact];
designRules.branchOffset ← designRules.branchSpacing;
designRules.trunkWidth ← DesignRules.MinWidth[rules, designRules.trunkLayer].w;
designRules.trunkSpacing ← DesignRules.MinSpace[rules, designRules.trunkLayer, designRules.trunkLayer].s;
designRules.trunkToContact ← GetMaterialToContact[rules, designRules.trunkLayer, cndObj];
designRules.trunkOffset ← designRules.trunkSpacing;
designRules.contactSize ← ContactSize[cndObj];
designRules.contactToContact ← designRules.contactSize + MAX[designRules.trunkSpacing, designRules.branchSpacing];
designRules.pinSpacing ← designRuleParms.pinSpacing;
designRules.trunkToEdge ← designRuleParms.trunkToEdge};
DesignRulesParameters: PUBLIC PROC [rules: DesignRules.Rules, horizLayer, vertLayer: CD.Layer, trunkDirection: DABasics.Direction] RETURNS[designRuleParms: Route.DesignRulesParameters] = {
Define the routing design rules for CMOS double or single layer metal.
trunkLayer:  CD.Layer ← IF trunkDirection = horizontal THEN horizLayer ELSE vertLayer;
branchLayer: CD.Layer ← IF trunkDirection = horizontal THEN vertLayer ELSE horizLayer;
cndObj:  CD.Object ← GetContact[trunkLayer, branchLayer];
contactToContact: DABasics.Number ← ContactSize[cndObj] + MAX[DesignRules.MinSpace[rules, trunkLayer, trunkLayer].s, DesignRules.MinSpace[rules, branchLayer, branchLayer].s];
trunkToTrunk: DABasics.Number ←
MAX[DesignRules.MinWidth[rules, trunkLayer].w + DesignRules.MinSpace[rules, trunkLayer, trunkLayer].s, GetMaterialToContact[rules, trunkLayer, cndObj], contactToContact];
pinSpacing:  DABasics.Number ← ContactSize[cndObj]/2 + DesignRules.MinWidth[rules, branchLayer].w/2 + DesignRules.MinSpace[rules, branchLayer, branchLayer].s;
trunkToEdge: DABasics.Number ←
MAX[DesignRules.MinSpace[rules, branchLayer, branchLayer].s, DesignRules.MinSpace[rules, trunkLayer, trunkLayer].s] + MAX[ContactSize[cndObj], DesignRules.MinWidth[rules, trunkLayer].w]/2;
designRuleParms ← NEW[Route.DesignRulesParametersRec ← [technology: rules.technology, horizLayer: horizLayer, vertLayer: vertLayer, trunkDirection: trunkDirection, trunkToTrunk: trunkToTrunk, pinSpacing: pinSpacing, trunkToEdge: trunkToEdge]]};
}.