<<-- File: IPCB.mesa>> <<-- Last Edited by: CSChow, February 2, 1985 2:31:10 am PST>> <<--Note: IPCB = ChannelBoundary>> <<>> <<--This is an abstration of all the intersection information of a channel. It records all the (Channel) >> <<-- intersections, and neighboring components. These interface is separated from CTG to make>> <<-- CTG independent of it.>> <<>> <<--This can be considered part of the 'underground world' so the code are quite sensitive >> <<-- to changes.>> DIRECTORY IP; IPCB: CEDAR DEFINITIONS = BEGIN Ref: TYPE = REF Rep; Rep: TYPE = IP.ChBoundaryRep; IntersectionNode: TYPE = REF IntersectionNodeRep; IntersectionNodeRep: TYPE = IP.IntersectionNodeRep; Intersection: TYPE = REF IP.IntersectionRep; Channel: TYPE = REF IP.ChannelRep; Component: TYPE = REF IP.ComponentRep; IntersectionType: TYPE = IP.IntersectionType; PIntersectionType: TYPE = [0..1]; NIntersectionType: TYPE = [-1..0]; <<>> Cross, TEnd: IntersectionType = 0; TNeg, LNeg: IntersectionType = -1; TPos, LPos: IntersectionType = 1; Side: TYPE = IP.PolarityTypes; EachINodeAction: TYPE = PROC [iNd: IntersectionNode] RETURNS [quit: BOOL _ FALSE]; EachIntersectionAction: TYPE = PROC[i: Intersection] RETURNS[quit: BOOL _ FALSE]; EachComponentAction: TYPE = PROC[co: Component] RETURNS[quit: BOOL _ FALSE]; EachChSegAction: TYPE = PROC [r: Ref, negIntNd, posIntNd: IntersectionNode] RETURNS [quit: BOOL _ FALSE]; <<--Client should only access IPCB with the operations given below -->> SideEmpty: ERROR; NotFound: ERROR; Create: PROC[owner: Channel] RETURNS[r: Ref]; Destroy: PROC[r: Ref]; CheckSelf: PROC[r: Ref]; GetOwner: PROC[r: Ref] RETURNS [Channel] = INLINE {RETURN [r.owner]}; End: PROC[r: Ref, which: Side] RETURNS[Intersection]; NthINode: PROC [r: Ref, which: Side, n: INT] RETURNS[IntersectionNode]; NthIntersection: PROC[r: Ref, which: Side, n: INT] RETURNS[Intersection]; NthComponent: PROC [r: Ref, which: Side, n: INT] RETURNS[Component]; NoIntersection: PROC[r: Ref, which: Side] RETURNS[BOOL]; NoComponent: PROC[r: Ref, which: Side] RETURNS[BOOL]; ComponentOn: PROC[r: Ref, comp: Component, which: Side] RETURNS[BOOL]; EndCh: PROC[r: Ref, ch: Channel] RETURNS [BOOL] = INLINE{RETURN [r.negEnd.intersection.ch = ch OR r.posEnd.intersection.ch = ch]}; --EndCh-- GetChNbr: PROC[r:Ref, ch: Channel, whichNbr, hint: Side] RETURNS [Channel]; SetBoundary: PROC[r: Ref, negEnd, posEnd: Intersection, negSide, posSide: LIST OF Intersection]; InsertCoBetween: PROC[r: Ref, co: Component, negBnd, posBnd: Channel, which: Side]; InsertCoAt: PROC[r: Ref, co: Component, whichSide, whichEnd: Side]; Components: PROC[r: Ref, which: Side, p: EachComponentAction] RETURNS[BOOL]; Intersections: PROC[r: Ref, which: Side, p: EachIntersectionAction] RETURNS[BOOL]; IntersectionNodes: PROC[r: Ref, p: EachINodeAction, which: Side] ; AllIntersectionNodes: PROC [r: Ref, p: PROC [iNd: IntersectionNode]]; AllInteriorIntersections: PROC [r: Ref] RETURNS[LIST OF IntersectionNode]; ChannelSegments: PROC[r: Ref, p: EachChSegAction] RETURNS[BOOL]; <> <<--######Used mainly by EditOpsImpl######-->> GetINode: PROC[r: Ref, ch: Channel, hint: Side] RETURNS [IntersectionNode]; IntersectsCh: PROC[r: Ref, ch: Channel] RETURNS [BOOL]; ArmOn: PROC[r: Ref, ch: Channel, which: Side] RETURNS [BOOL]; SideAddl: PROC [r: Ref, iNd: IntersectionNode, which: Side] RETURNS [IntersectionNode]; SideAddh: PROC [r: Ref, iNd: IntersectionNode, which: Side] RETURNS [IntersectionNode]; SideInsert: PROC[r:Ref, iNd: IntersectionNode, negBnd, posBnd: Channel, which: Side] RETURNS [IntersectionNode]; SetEnd: PROC [r: Ref, iNd: IntersectionNode, whichEnd: Side] RETURNS [IntersectionNode]; GetEnd: PROC [r: Ref, whichEnd: Side] RETURNS [IntersectionNode] = INLINE { RETURN [(SELECT whichEnd FROM neg => r.negEnd, pos => r.posEnd, ENDCASE => ERROR)]};--GetEnd-- SideRemovel: PROC [r: Ref, which: Side] RETURNS [iNd: IntersectionNode]; --! Raise SideEmpty error-- SideRemoveh: PROC [r: Ref, which: Side] RETURNS [iNd: IntersectionNode]; --! Raise SideEmpty error-- SideRem: PROC[r: Ref, ch: Channel, which: Side, repCo: Component] RETURNS [iNd: IntersectionNode]; --! Raise NotFound -- SideRem2: PROC[r: Ref, iNd: IntersectionNode, repCo: Component] RETURNS [IntersectionNode]; --! Raise NotFound -- Fragment: PROC [r: Ref, co1, co2: Component, negCh, posCh: Channel]; Merge: PROC [negR, posR: Ref, owner: Channel]; XingCount: PROC[r: Ref, ch: Channel, which: Side] RETURNS [INT]; <<--returns 'Crossing count' of ch with respect to owner of r>> InCount: PROC[r: Ref, ch: Channel, which: Side] RETURNS [INT]; <<--returns 'intersection count' of ch with respect to owner of r>> SetUpDuals: PROC [iNd: IntersectionNode, hint: Side] ; SideGet: PROC [r: Ref, which: Side] RETURNS [Hd, Tl: LIST OF IntersectionNode]; SideSetComp: PROC [r: Ref, comp: Component, which: Side]; SideGetComp: PROC [r: Ref, which: Side] RETURNS [Component]; SetINodeComps: PROC [iNd: IntersectionNode, negComp, posComp: Component] = INLINE{ iNd.negComp _ negComp; iNd.posComp _ posComp}; SetINodeComp: PROC[iNd: IntersectionNode, comp: Component, which: Side] = INLINE { SELECT which FROM neg => iNd.negComp _ comp; pos => iNd.posComp _ comp; ENDCASE => ERROR}; --SetINodeComp-- INodeDual: PROC[iNd: IntersectionNode] RETURNS [IntersectionNode] = INLINE {RETURN [iNd.dual]}; --INodeDual-- SetINodeDual: PROC[iNd, iNdDual: IntersectionNode] = INLINE{iNd.dual _ iNdDual}; --SetINodeDual-- DestroyINode: PROC[iNd: IntersectionNode] = INLINE {iNd.dual _ NIL}; --DestroyINode-- ItoINode: PROC [i: Intersection, o: Channel] RETURNS [IntersectionNode]; SideOpenHole1: PROC[mainR, sideR: Ref, negBnd, posBnd: Channel, sideToOp: Side]; SideOpenHole2: PROC[mainR, sideR: Ref, negBnd, posBnd: Channel, sideToOp: Side]; SideCloseHole1: PROC[mainR, sideR: Ref, negBnd, posBnd: Channel, sideToCl: Side]; SideCloseHole2: PROC[mainR, sideR: Ref, negBnd, posBnd: Channel, sideToCl: Side]; END.