<> <> <> <> DIRECTORY CD, CDDefaultProcs, CDDirectory, CDPinObjects, CDProperties, Core, CoreClasses, CoreOps, CoreProperties, CoreSequence, PW, PWCore, PWObjects, PWPins, RefTab, Rope, SymTab; PWCoreImpl: CEDAR PROGRAM IMPORTS CD, CDDefaultProcs, CDDirectory, CDPinObjects, CDProperties, CoreOps, CoreProperties, PW, PWObjects, PWPins, RefTab, SymTab EXPORTS PWCore SHARES CDDirectory = BEGIN OPEN PWCore; <> ROPE: TYPE = Rope.ROPE; <> layoutProp: PUBLIC ATOM _ CoreProperties.RegisterProperty[$PWCoreLayout, CoreProperties.Props[[CoreProperties.propCopy, CoreProperties.PropDoCopy]]]; SetLayout: PUBLIC PROC [cellType: CellType, cdObject: Object] = { cdNets: RefTab.Ref _ FindNets[cdObject]; nbAtomicWires: INT _ 0; EachWire: CoreOps.EachWireProc = { <<[wire: Wire] RETURNS [notSubWires: BOOL _ FALSE, quit: BOOL _ FALSE]>> IF wire.elements#NIL THEN RETURN; IF RefTab.Fetch[cdNets, wire].val=NIL THEN ERROR; -- wire has no pins nbAtomicWires _ nbAtomicWires + 1; }; CoreOps.VisitWire[cellType.publicWire, EachWire]; IF RefTab.GetSize[cdNets]#nbAtomicWires THEN ERROR; -- Some pins are associated with a non valid wire CoreProperties.PutCellTypeProp[cellType, layoutProp, cdObject]; }; GetLayout: PUBLIC PROC [cellType: CellType] RETURNS [cdObject: Object] = { cdObject _ NARROW [CoreProperties.GetCellTypeProp[cellType, layoutProp]]; }; <> <<-- A Gateway is a CD.Object whose specificRef points to a CellType >> gateWayClass: PUBLIC REF CD.ObjectClass _ CD.RegisterObjectClass[$GateWayClass]; dpGateWayClass: REF CDDirectory.DirectoryProcs = CDDirectory.InstallDirectoryProcs[gateWayClass]; CreateGateWay: PUBLIC PROC [coreInstance: CellInstance] RETURNS [cdObject: Object] = { cdObject _ NEW [CD.ObjectRep _ [class: gateWayClass, specificRef: coreInstance]]; }; ExpandGateWay: CDDirectory.AnotherProc -- [me: CD.Object, from: CD.Design, to: CD.Design] RETURNS [CD.Object] -- = { RETURN [GetLayout[NARROW [me.specificRef, CellInstance].type]]; }; CreateGateWays: PUBLIC PROC [coreInstances: LIST OF CellInstance] RETURNS [cdObjects: LIST OF Object] = { WHILE coreInstances#NIL DO cdObjects _ CONS [CreateGateWay[coreInstances.first], cdObjects]; coreInstances _ coreInstances.rest; ENDLOOP; cdObjects _ PW.Reverse[cdObjects]; }; <> wireOfPin: PUBLIC ATOM _ $PWCoreWireOfPin; -- The property on which the Wire of a pin hangs. SetWire: PUBLIC PROC [pinInstance: CD.Instance, wire: Wire] = { CDProperties.PutPropOnInstance[pinInstance, wireOfPin, wire]; }; GetWire: PUBLIC PROC [pinInstance: CD.Instance] RETURNS [wire: Wire] = { wire _ NARROW [CDProperties.GetPropFromInstance[pinInstance, wireOfPin]]; }; BindPins: PUBLIC PROC [cellType: CellType, cdObject: Object] = { publicNames: SymTab.Ref _ SymTab.Create[]; EachWire: CoreOps.EachWireProc = { <<[wire: Wire] RETURNS [notSubWires: BOOL _ FALSE, quit: BOOL _ FALSE]>> IF wire.elements#NIL THEN RETURN; IF wire.name=NIL THEN ERROR; -- all wires should be named at this point IF ~SymTab.Store[publicNames, wire.name, wire] THEN ERROR; -- Two wires have the same name }; EachPin: PWPins.InstanceEnumerator = { <<[inst: CD.Instance] RETURNS [quit: BOOL _ FALSE]>> name: ROPE _ CDPinObjects.GetName[inst]; wire: Wire _ NARROW [SymTab.Fetch[publicNames, name].val]; IF wire=NIL THEN ERROR; SetWire[inst, wire]; }; CoreOps.VisitWire[cellType.publicWire, EachWire]; [] _ PWPins.EnumerateEdgePins[cdObject, EachPin]; }; <> Each2WireProc: TYPE = PROC [wire1, wire2: Wire] RETURNS [notSubWires: BOOL _ FALSE, quit: BOOL _ FALSE]; Visit2Wire: PUBLIC PROC [wire1, wire2: Wire, eachWire: Each2WireProc]= { RecurseOn2Wire: PROC [wire1, wire2: Wire] RETURNS [quit: BOOL _ FALSE] = { notSubWires: BOOL; [notSubWires, quit] _ eachWire[wire1, wire2]; IF NOT quit AND NOT notSubWires AND wire1.elements#NIL AND wire2.elements#NIL AND wire1.elements.size=wire2.elements.size THEN FOR i:NAT IN [0..wire1.elements.size) DO quit _ RecurseOn2Wire[wire1.elements[i], wire2.elements[i]]; IF quit THEN EXIT; ENDLOOP; }; IF wire1#NIL AND wire2#NIL THEN [] _ RecurseOn2Wire[wire1, wire2]; }; GateWayEnumerateDeepPinsInContext: PWPins.EnumerationProc = { cellInstance: CellInstance _ NARROW [ob.specificRef]; translationTable: RefTab.Ref _ RefTab.Create[]; -- from the public Wire to the actual Each2Wire: Each2WireProc = { IF wire1.elements#NIL OR wire2.elements#NIL THEN RETURN; [] _ RefTab.Store[translationTable, wire1, wire2]; }; TranslateEachPin: PWPins.InstanceEnumerator = { <<[inst: CD.Instance] RETURNS [quit: BOOL _ FALSE]>> wire: Wire _ GetWire[inst]; pin: CD.Instance _ NEW [CD.InstanceRep _ [ob: inst.ob, location: inst.location, orientation: inst.orientation, properties: CDProperties.DangerousCopyProps[inst.properties]]]; IF wire=NIL THEN ERROR; -- pin has no wire attribute SetWire[pin, NARROW [RefTab.Fetch[translationTable, wire].val]]; quit _ eachPin[pin]; }; Visit2Wire[cellInstance.type.publicWire, cellInstance.actualWire, Each2Wire]; quit _ PWPins.EnumerateDeepPinsInContext[GetLayout[cellInstance.type], location, orientation, CDProperties.DangerousCopyProps[ob.properties], TranslateEachPin, stopEnumerateDeepPins, filter]; }; FindNets: PUBLIC PROC [obj: CD.Object] RETURNS [nets: RefTab.Ref] = { EachPin: CDPinObjects.InstanceEnumerator = { <<[inst: CD.Instance] RETURNS [quit: BOOL _ FALSE]>> wire: Wire _ GetWire[inst]; pins: LIST OF CD.Instance; IF wire=NIL THEN ERROR; -- pin has no wire property pins _ CONS [inst, NARROW [RefTab.Fetch[nets, wire].val]]; [] _ RefTab.Store[nets, wire, pins]; }; nets _ RefTab.Create[]; [] _ PWPins.EnumerateEdgePins[obj, EachPin]; }; <> SetGet: PUBLIC PROC [cellType: CellType, source: CD.Design] = { cdObject: Object _ PW.Get[source, cellType.name]; BindPins[cellType, cdObject]; SetLayout[cellType, cdObject]; }; SetAbutX: PUBLIC PROC [cellType: CellType, instances: LIST OF CellInstance] = { SetLayout[cellType, PW.AbutListX[NIL, CreateGateWays[instances]]]; }; SetAbutY: PUBLIC PROC [cellType: CellType, instances: LIST OF CellInstance] = { SetLayout[cellType, PW.AbutListY[NIL, CreateGateWays[instances]]]; }; SetArrayX: PUBLIC PROC [cellType: CellType] = { recasted: CellType _ CoreOps.Recast[cellType]; SetLayout[cellType, PW.AbutListX[NIL, CreateGateWays[NARROW [recasted.data, CoreClasses.RecordCellType].instances]]]; }; SetArrayY: PUBLIC PROC [cellType: CellType] = { recasted: CellType _ CoreOps.Recast[cellType]; SetLayout[cellType, PW.AbutListY[NIL, CreateGateWays[NARROW [recasted.data, CoreClasses.RecordCellType].instances]]]; }; <> <> <> <> <<};>> <> <> <> <<};>> SetFlipX: PUBLIC PROC [cellType: CellType] = { SetLayout[cellType, PW.FlipX[NIL, CreateGateWay[NARROW [cellType.data, CoreClasses.RecordCellType].instances.first]]]; }; SetFlipY: PUBLIC PROC [cellType: CellType] = { SetLayout[cellType, PW.FlipY[NIL, CreateGateWay[NARROW [cellType.data, CoreClasses.RecordCellType].instances.first]]]; }; SetRot90: PUBLIC PROC [cellType: CellType] = { SetLayout[cellType, PW.Rot90[NIL, CreateGateWay[NARROW [cellType.data, CoreClasses.RecordCellType].instances.first]]]; }; SetRot180: PUBLIC PROC [cellType: CellType] = { SetLayout[cellType, PW.Rot180[NIL, CreateGateWay[NARROW [cellType.data, CoreClasses.RecordCellType].instances.first]]]; }; SetRot270: PUBLIC PROC [cellType: CellType] = { SetLayout[cellType, PW.Rot270[NIL, CreateGateWay[NARROW [cellType.data, CoreClasses.RecordCellType].instances.first]]]; }; SetLazy: PUBLIC PROC [cellType: CellType, info: REF, createProc: PWObjects.CreateProc] = { SetLayout[cellType, PWObjects.CreateLazy[info: info, createProc: createProc]]; }; <> gateWayClass.showMeSelected _ CDDefaultProcs.ShowMeSelectedWithExpand; dpGateWayClass.expand _ ExpandGateWay; gateWayClass.showMeSelected _ CDDefaultProcs.ShowMeSelectedWithExpand; gateWayClass.interestRect _ CDDefaultProcs.InterestRectWithExpand; [] _ CDProperties.RegisterAndInstall[wireOfPin, [makeCopy: CDProperties.CopyVal], $PWCore]; CDProperties.PutProp[gateWayClass, PWPins.enumerationProcProp, NEW [PWPins.EnumerationProc _ GateWayEnumerateDeepPinsInContext]]; END. <<>>