DIRECTORY Convert, Rope, Real, SC, SCChanUtil, SCInitialPlace, SCInstUtil, SCPlaceUtil, SCPrivate, SCRowUtil, TerminalIO; SCPrePlaceImpl: CEDAR PROGRAM IMPORTS Convert, Real, Rope, SC, SCChanUtil, SCInstUtil, SCPlaceUtil, SCRowUtil, TerminalIO EXPORTS SCInitialPlace SHARES SC = BEGIN debug: BOOLEAN _ FALSE; ChooseNonZero: PROCEDURE [num1, num2, num3: SC.Number _ 0] RETURNS[ result: SC.Number] = { IF num1 # 0 THEN result _ num1 ELSE IF num2 # 0 THEN result _ num2 ELSE result _ num3}; InitBpSide: PROCEDURE [handle: SC.Handle] = { SideProc: SCRowUtil.EachSideProc = { bpRow.maxBpsOnSide _ bpRow.initMaxBpsOnSide; bpRow.size.p _ 0; bpRow.size.q _ 0; bpRow.dimInvalid _ FALSE; bpRow.nBpsOnSide _ 0; bpRow.fnlBpFxd _ FALSE; bpRow.initBpFxd _ FALSE}; [] _ SCRowUtil.EnumerateSides[handle, SideProc]}; InitLgRow: PROCEDURE [handle: SC.Handle] = { RowProc: SCRowUtil.EachRowProc = { lgRow.size.p _ 0; lgRow.size.q _ 0; lgRow.dimInvalid _ FALSE; lgRow.nLgsOnRow _ 0; lgRow.nFtsOnRow _ 0; lgRow.fnlLgFxd _ FALSE; lgRow.initLgFxd _ FALSE}; [] _ SCRowUtil.EnumerateRows[handle, RowProc]}; PrePlaceComps: PROCEDURE [handle: SC.Handle, initialized: BOOLEAN] = { IntBounds: PROCEDURE[checkNum, lowLimit, upLimit, default: SC.Number, name: Rope.ROPE] RETURNS[ result: SC.Number] = { IF lowLimit <= checkNum AND checkNum <= upLimit THEN result _ checkNum ELSE { result _ default; TerminalIO.WriteRope[Rope.Cat[Rope.Cat[" instance: ", name, " variable: ", Convert.RopeFromInt[checkNum], " limits = "], Rope.Cat[Convert.RopeFromInt[lowLimit], Convert.RopeFromInt[upLimit], "\n"]]]}}; SideBounds: PROCEDURE[checkNum, lowLimit, upLimit, default: SC.SideOrNone, name: Rope.ROPE] RETURNS[ result: SC.SideOrNone] = { IF lowLimit <= checkNum AND checkNum <= upLimit THEN result _ checkNum ELSE { result _ default; TerminalIO.WriteRope[Rope.Cat[Rope.Cat[" instance: ", name, " variable: ", SCRowUtil.sideName[checkNum], " limits: "], Rope.Cat[SCRowUtil.sideName[lowLimit], " .. ", SCRowUtil.sideName[upLimit], "\n"]]]}}; PrePlacLg: PROCEDURE[handle: SC.Handle, instance: SCPrivate.Instance, initialized: BOOLEAN] = { layoutData: SCPrivate.LayoutData _ NARROW[handle.layoutData]; lgRows: SCPrivate.LgRows _ layoutData.lgRows; iRow, fRow: SCPrivate.ZMaxRowSr; IF initialized THEN { instance.curRow _ instance.initRow; instance.curPos _ instance.initPos; instance.curOrien _ instance.initOrien}; fRow _ IntBounds[instance.fnlRow, 0, SCPrivate.maxLgRows, 0, instance.name]; iRow _ IntBounds[instance.initRow, 0, SCPrivate.maxLgRows, 0, instance.name]; IF instance.preRow > 0 THEN { instance.preRow _ IntBounds[instance.preRow, 1, SCPrivate.maxLgRows, 0, instance.name]; instance.prePos _ IntBounds[instance.prePos, 1, SCPrivate.maxPos, 0, instance.name]; instance.preOrien _ IntBounds[instance.preOrien, 1, SCPrivate.maxOrien, SCInstUtil.defltLgOrien, instance.name]; IF instance.preRow = 0 OR instance.prePos = 0 OR instance.preOrien = 0 THEN { instance.preRow _ 0; instance.prePos _ 0; instance.preOrien _ 0}} ELSE IF fRow > 0 THEN { instance.preRow _ fRow; instance.prePos _ IntBounds[ChooseNonZero[instance.fnlPos, instance.initPos], 0, SCPrivate.maxPos, 0, instance.name]; instance.preOrien _ IntBounds[ChooseNonZero[instance.fnlOrien, instance.initOrien, SCInstUtil.defltLgOrien], 1, SCPrivate.maxOrien, SCInstUtil.defltLgOrien, instance.name]} ELSE IF iRow > 0 THEN { instance.preRow _ iRow; instance.prePos _ IntBounds[ChooseNonZero[instance.fnlPos, instance.initPos], 0, SCPrivate.maxPos, 0, instance.name]; instance.preOrien _ IntBounds[ChooseNonZero[instance.fnlOrien, instance.initOrien, SCInstUtil.defltLgOrien], 1, SCPrivate.maxOrien, SCInstUtil.defltLgOrien, instance.name]}; IF instance.preRow > 0 THEN SCPlaceUtil.PutLgRow[handle, instance, instance.preRow, instance.preOrien] ELSE {instance.curRow _ 0; instance.curPos _ 0; instance.curOrien _ 0}; IF instance.preRow > 0 AND instance.prePos > 0 THEN { IF fRow > 0 AND instance.fnlPos > 0 THEN lgRows.rows[fRow].fnlLgFxd _ TRUE; IF iRow > 0 AND instance.initPos > 0 THEN lgRows.rows[iRow].initLgFxd _ TRUE}}; PrePlacBp: PROCEDURE[handle: SC.Handle, instance: SCPrivate.Instance, initialized:BOOLEAN] = { layoutData: SCPrivate.LayoutData _ NARROW[handle.layoutData]; bpRows: SCPrivate.BpRows _ layoutData.bpRows; iSide, fSide: SC.SideOrNone; IF initialized THEN { instance.curSide _ instance.initSide; instance.curPos _ instance.initPos; instance.curOrien _ instance.initOrien}; iSide _ SideBounds[instance.initSide, bottom, none, none, instance.name]; fSide _ SideBounds[instance.fnlSide, bottom, none, none, instance.name]; IF instance.preSide # none THEN { instance.preSide _ SideBounds[instance.preSide, bottom, right, none, instance.name]; instance.prePos _ IntBounds[instance.prePos, 1, SCPrivate.maxPos, 0, instance.name]; instance.preOrien _ IntBounds[instance.preOrien, 1, SCPrivate.maxOrien, SCInstUtil.defltBpOrien[instance.preSide], instance.name]; IF instance.preSide = none OR instance.prePos = 0 OR instance.preOrien = 0 THEN { instance.preSide _ none; instance.prePos _ 0; instance.preOrien _ 0}} ELSE IF fSide # none THEN { instance.preSide _ fSide; instance.prePos _ IntBounds[ChooseNonZero[instance.fnlPos, instance.initPos], 0, SCPrivate.maxPos, 0, instance.name]; instance.preOrien _ IntBounds[ChooseNonZero[instance.fnlOrien, instance.initOrien, SCInstUtil.defltBpOrien[instance.preSide]], 1, SCPrivate.maxOrien, SCInstUtil.defltBpOrien[instance.preSide], instance.name]} ELSE IF iSide # none THEN { instance.preSide _ iSide; instance.prePos _ IntBounds[ChooseNonZero[instance.fnlPos, instance.initPos], 0, SCPrivate.maxPos, 0, instance.name]; instance.preOrien _ IntBounds[ChooseNonZero[instance.fnlOrien, instance.initOrien, SCInstUtil.defltBpOrien[iSide]], 1, SCPrivate.maxOrien, SCInstUtil.defltBpOrien[iSide], instance.name]}; IF instance.preSide # none THEN SCPlaceUtil.PutBpSide[handle, instance, instance.preSide] ELSE {instance.curSide _ none; instance.curPos _ 0; instance.curOrien _ 0}; IF instance.preSide # none AND instance.prePos > 0 THEN { IF fSide # none AND instance.fnlPos > 0 THEN bpRows[fSide].fnlBpFxd _ TRUE; IF iSide # none AND instance.initPos >0 THEN bpRows[iSide].initBpFxd _ TRUE}}; EachInstance: SCInstUtil.EachInstanceProc = { SELECT instance.whichClass FROM logic, ft => PrePlacLg[handle, instance, initialized]; io => PrePlacBp[handle, instance, initialized]; ENDCASE}; [] _ SCInstUtil.EnumerateAllInstances[handle, EachInstance]}; DetermineRows: PROCEDURE [handle: SC.Handle, numRows: NAT _ 0] = { EachInstance: SCInstUtil.EachInstanceProc = { IF instance.whichClass = logic THEN { maxRowSpec _ MAX[instance.initRow, MAX[maxRowSpec, instance.fnlRow]]; totLinComps _ totLinComps + SCInstUtil.InstWidth[instance]; avgHeight _ avgHeight + SCInstUtil.InstHeight[instance]}}; layoutData: SCPrivate.LayoutData _ NARROW[handle.layoutData]; lgRows: SCPrivate.LgRows _ layoutData.lgRows; structureData: SCPrivate.StructureData _ NARROW[handle.structureData]; instances: SCPrivate.Instances _ structureData.instances; routFact: REAL = 2.5; detRow: NAT; maxRowSpec, avgHeight, totLinComps: SC.Number _ 0; [] _ SCInstUtil.EnumerateAllInstances[handle, EachInstance]; avgHeight _ avgHeight /MAX[1, instances.numLogics]; IF avgHeight > 0 THEN detRow _ MAX[1, Real.RoundI[Real.SqRt[totLinComps * avgHeight* routFact] / (avgHeight * routFact)]] ELSE detRow _ 0; IF numRows > 0 THEN lgRows.count _ MIN[SC.Number[SCPrivate.maxLgRows], MAX[maxRowSpec, numRows]] ELSE IF maxRowSpec > 0 THEN lgRows.count _ MIN[SC.Number[SCPrivate.maxLgRows], MAX[maxRowSpec, detRow]] ELSE lgRows.count _ MIN[SCPrivate.maxLgRows, detRow]; lgRows.count _ MAX[1, lgRows.count]; layoutData.rowChans.count _ lgRows.count +1; TerminalIO.WriteRope[" number of rows calculation:\n"]; TerminalIO.WriteRope[" maximum row specified = "]; TerminalIO.WriteInt[maxRowSpec]; TerminalIO.WriteRope["\n computed number of rows = "]; TerminalIO.WriteInt[detRow]; TerminalIO.WriteRope["\n number of rows specified = "]; TerminalIO.WriteInt[numRows]; TerminalIO.WriteRope["\n number of rows used = "]; TerminalIO.WriteInt[lgRows.count]; TerminalIO.WriteLn[]}; DetermineSides: PROCEDURE [handle: SC.Handle] = { SideSlots: SCRowUtil.EachSideProc = { bpRow.maxBpsOnSide _ MAX[bpRow.initMaxBpsOnSide, bpRow.nBpsOnSide]; IF bpRow.maxBpsOnSide > 0 THEN { totBpSlots _ totBpSlots + bpRow.maxBpsOnSide; nSidesAvail _ nSidesAvail -1}}; SetSlots: SCRowUtil.EachSideProc = { IF bpRow.maxBpsOnSide <= 0 THEN bpRow.maxBpsOnSide _ nBps}; structureData: SCPrivate.StructureData _ NARROW[handle.structureData]; instances: SCPrivate.Instances _ structureData.instances; nSidesAvail: NAT[0..4] _ 4; totBpSlots: NAT _ 0; nBps: NAT; [] _ SCRowUtil.EnumerateSides[handle, SideSlots]; IF nSidesAvail > 0 THEN nBps _ MAX[0, (instances.numIOs - totBpSlots +3) /nSidesAvail] ELSE { nBps _ 0; IF instances.numIOs > totBpSlots THEN SC.Error[callingError, "Too many IO's"]}; [] _ SCRowUtil.EnumerateSides[handle, SetSlots]}; PrePlace: PUBLIC PROCEDURE[handle: SC.Handle, numRows: NAT _ 0, initialized: BOOLEAN _ TRUE] = { TerminalIO.WriteRope["Pre placement\n"]; InitBpSide[handle]; InitLgRow[handle]; SCChanUtil.ClearRouteDat[handle]; PrePlaceComps[handle, initialized]; DetermineRows[handle, numRows]; DetermineSides[handle]; TerminalIO.WriteRope["End pre placement\n"]; IF debug THEN SCPlaceUtil.WriteCurPlace[handle]}; END. l///StdCell/SCPrePlaceImpl.mesa Choose non zero num in priority order make the bonding pad rows empty make the interior rows empty pre place the components preplace the logic component instance check if this instance has a currently defined position check if the final position is specified check for initial position specified check if this instance restricts a row by specifying a position on a row preplace the bonding pad component instance check if this instance has a currently defined position check if the final position is specified check for initial position specified check to see if this bp restricts this side by having a position assigned determine the number of rows to use must use direct data access, no placement exists yet determine the number of Bps on sides to use compute number of slots to put on currently empty sides Ê÷˜Jšœ™J˜šÏk ˜ J˜Jšœ˜Jšœ˜Jšœ˜J˜ J˜Jšœ ˜ Jšœ ˜ J˜ Jšœ ˜ Jšœ ˜ J˜—šœœ˜Jšœœ<˜[Jšœ˜Jšœœ˜ J˜Jš˜Jšœœœ˜J˜šÏn œ œœ ˜:Jšœ œ ˜Jšœ™Jšœ%™%Jšœ œ˜Jšœœ œ˜#Jšœ˜—J˜šž œ œ œ ˜-Jšœ™Jšœ™šœ$˜$Jšœ,˜,Jšœ˜Jšœ˜Jšœœ˜Jšœ˜Jšœœ˜Jšœœ˜J˜—Jšœ1˜1—J˜šž œ œ œ ˜,Jšœ™Jšœ™šœ"˜"Jšœ˜Jšœ˜Jšœœ˜Jšœ˜Jšœ˜Jšœœ˜Jšœœ˜J˜—Jšœ/˜/J˜—šž œ œ œœ˜GJšœ™J˜šž œ œ'œœ˜VJšœ œ ˜—˜šœœ˜4Jšœ˜—šœ˜Jšœ˜Jšœ´˜É——J˜šž œ œ'œœ˜[Jšœ œ˜#—˜šœœ˜4Jšœ˜—šœ˜Jšœ˜Jšœ¸˜Í——J˜šž œ œ œ4œ˜_Jšœ&™&J˜Jšœ#œ˜=J˜-Jšœ ˜ J˜šœ œ˜Jšœ#˜#Jšœ#˜#Jšœ(˜(—J˜Jšœ8™8JšœL˜LJšœM˜MJ™šœœ˜JšœW˜WJšœT˜TJšœp˜pšœœœœ˜MJšœ˜Jšœ˜Jšœ˜——J™Jšœ)™)šœœ œ˜Jšœ˜Jšœu˜uJšœ¬˜¬—J™Jšœ%™%šœœ œ˜Jšœ˜Jšœu˜uJšœ­˜­—J˜JšœœK˜fJšœC˜GJ™JšœI™Išœœœ˜5Jšœ œœœ˜KJšœ œœœ˜O——J˜šž œ œ œ3œ˜^Jšœ,™,J˜Jšœ#œ˜=J˜-Jšœœ ˜J˜šœ œ˜J˜%J˜#Jšœ(˜(J™—Jšœ8™8JšœI˜IJšœH˜HJ˜šœœ˜!JšœT˜TJšœT˜TJšœ‚˜‚šœœœœ˜QJšœ˜Jšœ˜Jšœ˜——J™Jšœ)™)šœœœ˜Jšœ˜Jšœu˜uJšœÐ˜ÐJ™—Jšœ%™%šœœœ˜Jšœ˜Jšœu˜uJšœ»˜»—J˜Jšœœ:˜YJšœG˜KJ™JšœJ™Jšœœœ˜9Jšœœœœ˜KJšœœœœ˜N——J˜˜-šœ˜Jšœ6˜6Jšœ/˜/Jšœ˜ J˜——Jšœ>˜>—J˜šž œ œ œœ ˜BJšœ$™$J˜šœ-˜-šœœ˜%Jšœ œœ˜EJšœ4™4Jšœ;˜;Jšœ:˜:—J˜—Jšœ#œ˜=Jšœ-˜-Jšœ)œ˜FJšœ9˜9Jšœ œ˜J˜Jšœœ˜ Jšœ$œ ˜2J˜Jšœ<˜—šœ˜Jšœ ˜ šœ˜%Jšœ'˜)J˜——Jšœ2˜2—J˜J˜š žœœ œ œœœ˜`J˜Jšœ(˜(Jšœ˜Jšœ˜Jšœ!˜!Jšœ#˜#Jšœ˜Jšœ˜Jšœ,˜,Jšœœ%˜2—šœ˜J˜J˜———…—$¾1!