DIRECTORY CD, CDBasics, CDCells, CDDirectory, CDInstances, CDOrient, CDPinObjects, CDProperties, Convert, PWPins, Rope; PWPinsImpl: CEDAR PROGRAM IMPORTS CD, CDBasics, CDCells, CDDirectory, CDInstances, CDOrient, CDPinObjects, CDProperties, Convert, Rope EXPORTS PWPins SHARES CDPinObjects, CDCells = BEGIN OPEN PWPins; GetSide: PUBLIC PROC [ob: CD.Object, pin: CD.Instance] RETURNS [side: Side] = { LargerSide: PROC [hSide, vSide: Side] RETURNS [side: Side] = { delta: INT _ pinRect.x2-pinRect.x1- (pinRect.y2-pinRect.y1); side _ IF delta=0 THEN ERROR ELSE IF delta>0 THEN hSide ELSE vSide; }; rect: CD.Rect _ CD.InterestRect[ob]; -- the border pinRect: CD.Rect _ CDInstances.InstRectO[pin]; -- bbox of the pin side _ SELECT TRUE FROM rect.y1 = pinRect.y1 AND rect.y2 = pinRect.y2 => ERROR, -- pin on 2 opposite sides rect.x1 = pinRect.x1 AND rect.x2 = pinRect.x2 => ERROR, -- pin on 2 opposite sides rect.y2 = pinRect.y2 AND rect.x1 = pinRect.x1 => LargerSide[top, left], rect.y2 = pinRect.y2 AND rect.x2 = pinRect.x2 => LargerSide[top, right], rect.y1 = pinRect.y1 AND rect.x1 = pinRect.x1 => LargerSide[bottom, left], rect.y1 = pinRect.y1 AND rect.x2 = pinRect.x2 => LargerSide[bottom, right], rect.y2 = pinRect.y2 => top, rect.y1 = pinRect.y1 => bottom, rect.x1 = pinRect.x1 => left, rect.x2 = pinRect.x2 => right, ENDCASE => none; }; CopyInstance: PUBLIC PROC [oldInst: CD.Instance] RETURNS [newInst: CD.Instance] = { newInst _ NEW [CD.InstanceRep _ [ob: oldInst.ob, location: oldInst.location, orientation: oldInst.orientation, properties: CDProperties.DangerousCopyProps[oldInst.properties]]]; }; TransformInstance: PUBLIC PROC [instInCell: CD.Instance, cellSize: CD.Position, locationOfCellInWorld: CD.Position, orientationOfCellInWorld: CD.Orientation] RETURNS [instInWorld: CD.Instance] = { instInWorld _ NEW [CD.InstanceRep _ [ ob: instInCell.ob, location: CDBasics.BaseOfRect[ CDOrient.MapRect[ itemInCell: CDInstances.InstRectO[instInCell], cellSize: cellSize, cellInstOrient: orientationOfCellInWorld, cellInstPos: locationOfCellInWorld]], orientation: CDOrient.ComposeOrient[instInCell.orientation, orientationOfCellInWorld], properties: CDProperties.DangerousCopyProps[instInCell.properties]]]; }; EnumerateDeepPinsInContext: PUBLIC EnumerationProc = { value: REF; IF ~filter[CDOrient.MapRect[ itemInCell: CD.InterestRect[ob], cellSize: ob.size, cellInstOrient: orientation, cellInstPos: location]] THEN RETURN; value _ CDProperties.GetPropFromObject[ob, enumerationProcProp]; IF value#NIL THEN RETURN [NARROW [value, REF EnumerationProc]^[ob, location, orientation, properties, eachPin, stopEnumerateDeepPins, filter]]; value _ CDProperties.GetProp[ob.class, enumerationProcProp]; IF value#NIL THEN RETURN [NARROW [value, REF EnumerationProc]^[ob, location, orientation, properties, eachPin, stopEnumerateDeepPins, filter]]; ob _ CDDirectory.Expand[ob, NIL, NIL]; quit _ ob#NIL AND EnumerateDeepPinsInContext[ob, location, orientation, NIL, eachPin, stopEnumerateDeepPins, filter]; }; PinEnumerateDeepPinsInContext: EnumerationProc = { quit _ eachPin[NEW [CD.InstanceRep _ [ob: ob, location: location, orientation: orientation, properties: CDProperties.DangerousCopyProps[properties]]]]; }; CellEnumerateDeepPinsInContext: EnumerationProc = { cellPtr: CD.CellPtr _ NARROW [ob.specificRef]; FOR list: CD.InstanceList _ cellPtr.contents, list.rest WHILE (list#NIL AND ~quit) DO IF ~stopEnumerateDeepPins OR CDProperties.GetPropFromInstance[list.first, $StopEnumerateDeepPins]=NIL THEN quit _ EnumerateDeepPinsInContext[ list.first.ob, CDBasics.BaseOfRect[ CDOrient.MapRect[ itemInCell: CDInstances.InstRectO[list.first], cellSize: ob.size, cellInstOrient: orientation, cellInstPos: location]], CDOrient.ComposeOrient[list.first.orientation, orientation], list.first.properties, eachPin, stopEnumerateDeepPins, filter]; ENDLOOP; }; EnumerateDeepPins: PUBLIC PROC [ob: CD.Object, eachPin: InstanceEnumerator, stopEnumerateDeepPins: BOOL _ TRUE] RETURNS [quit: BOOL] = { DefaultFilter: FilterProc = {}; quit _ EnumerateDeepPinsInContext[ob: ob, eachPin: eachPin, stopEnumerateDeepPins: stopEnumerateDeepPins, filter: DefaultFilter]; }; EnumerateEdgePins: PUBLIC PROC [ob: CD.Object, eachPin: InstanceEnumerator, stopEnumerateDeepPins: BOOL _ TRUE] RETURNS [quit: BOOL] = { iRectShrank: CD.Rect _ CDBasics.Extend[CD.InterestRect[ob], -1]; EdgeFilter: FilterProc = {isSubInteresting _ ~CDBasics.Inside[subRect, iRectShrank]}; EachPinFilter: InstanceEnumerator -- [inst: CD.Instance] RETURNS [quit: BOOL _ FALSE] -- = { IF GetSide[ob, inst]#none THEN quit _ eachPin[inst]; }; quit _ EnumerateDeepPinsInContext[ob: ob, eachPin: EachPinFilter, stopEnumerateDeepPins: stopEnumerateDeepPins, filter: EdgeFilter]; }; ChangePins: PUBLIC PROC [design: CD.Design, ob: CD.Object, changePinProc: ChangePinProc _ DefaultChangePinProc, stopEnumerateDeepPins: BOOL _ TRUE] RETURNS [cell: CD.Object] = BEGIN cellPtr: CD.CellPtr; KeepPinOnEdge: InstanceEnumerator -- [inst: CD.Instance] RETURNS [quit: BOOL _ FALSE] -- = { newInst: CD.Instance _ changePinProc[inst]; IF newInst#NIL THEN cellPtr.contents _ CONS [newInst, cellPtr.contents]; }; inst: CD.Instance _ NEW [CD.InstanceRep _ [ob: ob]]; IF stopEnumerateDeepPins THEN CDProperties.PutPropOnInstance[inst, $StopEnumerateDeepPins, $StopEnumerateDeepPins]; cell _ CDCells.CreateEmptyCell[]; cellPtr _ NARROW [cell.specificRef]; [] _ EnumerateEdgePins[ob, KeepPinOnEdge]; cellPtr.contents _ CONS[inst, cellPtr.contents]; CDCells.SetInterestRect[cell, CD.InterestRect[ob]]; [] _ CDCells.RepositionCell[cell, NIL]; IF design#NIL THEN [] _ CDDirectory.Include[design, cell, "RenamedPins"]; END; DefaultChangePinProc: PUBLIC ChangePinProc = {newPin _ oldPin}; RenamePins: PUBLIC PROC [design: CD.Design, ob: CD.Object, renameProc: RenameProc _ DefaultRenameProc, stopEnumerateDeepPins: BOOL _ TRUE] RETURNS [cell: CD.Object] = { ChangePin: ChangePinProc = { newRope: ROPE _ renameProc[CDPinObjects.GetName[oldPin]]; IF Rope.IsEmpty[newRope] THEN RETURN; newPin _ CopyInstance[oldPin]; CDPinObjects.SetName[newPin, newRope]; }; cell _ ChangePins[design, ob, ChangePin, stopEnumerateDeepPins]; }; DefaultRenameProc: PUBLIC RenameProc = {newRope _ oldRope}; Index: PUBLIC PROC [rope: ROPE, index: INT] RETURNS [indexedRope: ROPE] = { indexedRope _ Rope.Cat[rope, "[", Convert.RopeFromInt[index], "]"]; }; enumerationProcProp: PUBLIC ATOM _ $EnumerationProcPWPins; [] _ CDProperties.RegisterProperty[enumerationProcProp, $PWPins]; CDProperties.InstallProcs[enumerationProcProp, [makeCopy: CDProperties.CopyVal]]; [] _ CDProperties.RegisterProperty[$StopEnumerateDeepPins, $PWPins]; CDProperties.InstallProcs[$StopEnumerateDeepPins, [makeCopy: CDProperties.CopyVal]]; CDProperties.PutProp[CDPinObjects.pinObjectsClass, enumerationProcProp, NEW [EnumerationProc _ PinEnumerateDeepPinsInContext]]; CDProperties.PutProp[CDCells.cellClass, enumerationProcProp, NEW [EnumerationProc _ CellEnumerateDeepPinsInContext]]; END. \PWPinsImpl.mesa Copyright c 1985 by Xerox Corporation. All rights reversed. Created by Bertrand Serlet, June, 1985 10:07:28 am PDT Bertrand Serlet, November 10, 1985 0:37:57 am PST Because we must finally get instances, this one has in its parameters all necessary information for reconstructing the application. Useful in many RenameProcs for indexing names. e.g. Index["foo", 4]="foo[4]" [] _ CDProperties.RegisterAndInstall[enumerationProcProp, [makeCopy: CDProperties.CopyVal], $PWPins]; [] _ CDProperties.RegisterAndInstall[$StopEnumerateDeepPins, [makeCopy: CDProperties.CopyVal], $PWPins]; Κό˜šœ™Jšœ Οmœ1™Jšœžœ2˜