DIRECTORY Basics, CirioNubAccess, Rope; CirioMemory: CEDAR DEFINITIONS = BEGIN ROPE: TYPE ~ Rope.ROPE; BitAddr: TYPE ~ RECORD [aus: CARD, bits: INT]; zeroBA: BitAddr ~ [0, 0]; unspecdBA: BitAddr ~ [CARD.LAST, INT.LAST]; bitsPerAu: NAT ~ 8; bitsPerPtr: NAT ~ 32; BaCons: PROC [aus: CARD, bits: INT] RETURNS [BitAddr] ~ INLINE {IF bits/bitsPerAu >= 0 OR aus > ABS[bits/bitsPerAu] THEN RETURN[[aus+bits/bitsPerAu, bits MOD bitsPerAu]] ELSE RETURN[[0, aus*bitsPerAu+bits]]}; BaAsAbs: PROC [ba: BitAddr] RETURNS [BitAddr]; BaAdd: PROC [a, b: BitAddr] RETURNS [BitAddr] ~ INLINE {RETURN BaCons[a.aus+b.aus, a.bits+b.bits]}; BaAddOffset: PROC [ba: BitAddr, bits: INT] RETURNS [BitAddr] ~ INLINE {RETURN BaCons[ba.aus, ba.bits+bits]}; BaSub: PROC [a, b: BitAddr] RETURNS [BitAddr] ~ INLINE {RETURN BaCons[a.aus-b.aus, a.bits-b.bits]}; BaMul: PROC [ba: BitAddr, by: CARD] RETURNS [BitAddr] ~ INLINE {RETURN BaCons[ba.aus*by, ba.bits*by]}; BaCompare: PROC [a, b: BitAddr] RETURNS [Basics.Comparison]; BitsToBa: PROC [bits: INT] RETURNS [BitAddr] ~ INLINE {RETURN BaCons[0, bits]}; BaToBits: PROC [ba: BitAddr] RETURNS [CARD] ~ INLINE {RETURN[ba.aus*bitsPerAu + ba.bits]}; AusToBa: PROC [aus: CARD] RETURNS [BitAddr] ~ INLINE {RETURN[[aus, 0]]}; BaToAus: PROC [ba: BitAddr] RETURNS [CARD] ~ INLINE {IF ba.bits#0 THEN ERROR; RETURN[ba.aus]}; PtrToBa: PROC [ptr: CARD] RETURNS [BitAddr] ~ INLINE {RETURN[[LOOPHOLE[ptr], 0]]}; BaToPtr: PROC [ba: BitAddr] RETURNS [CARD] ~ INLINE {IF ba.bits#0 THEN ERROR; RETURN[LOOPHOLE[ba.aus]]}; BitStretch: TYPE ~ RECORD [start, size: BitAddr]; unspecdBS: BitStretch ~ [unspecdBA, unspecdBA]; BsCompose: PROC [main, inner: BitStretch] RETURNS [within: BOOL, compd: BitStretch]; Mem: TYPE = RECORD[class: MemClass, data: REF ANY]; noMem: Mem = [NIL, NIL]; MemClass: TYPE ~ REF MemClassPrivate; MemClassPrivate: TYPE ~ RECORD [ CreateSimple: PROC [data: REF ANY, stretch: BitStretch, keepFrame: BOOL] RETURNS [Mem], Subfield: PROC [data: REF ANY, rel: BitStretch] RETURNS [Mem], Shift: PROC [data: REF ANY, offset: BitAddr] RETURNS [Mem], GetStretch: PROC [data: REF ANY] RETURNS [BitStretch], Read: PROC [data: REF ANY, bitSize: CARD, offset: BitAddr] RETURNS [CARD], Write: PROC [data: REF ANY, bits: CARD, bitSize: CARD, offset: BitAddr], ReadPtrReg: PROC [data: REF ANY, ptrReg: PtrReg] RETURNS [BitStretch], ReadSegmentReg: PROC [data: REF ANY, segName: ROPE, segNum: INT] RETURNS [BitStretch], SetPtrReg: PROC [data: REF ANY, ptrReg: PtrReg, val: BitStretch] ]; PtrReg: TYPE ~ { fp --frame pointer--, sp --stack pointer--, fe --frame extension pointer-- }; Error: ERROR [msg: ROPE]; MemSubfield: PROC [mem: Mem, rel: BitStretch] RETURNS [Mem] ~ INLINE {RETURN mem.class.Subfield[mem.data, rel]}; MemShift: PROC [mem: Mem, offset: BitAddr] RETURNS [Mem] ~ INLINE {RETURN mem.class.Shift[mem.data, offset]}; MemIndirect: PROC [mem: Mem, size: BitAddr _ unspecdBA, offset: BitAddr _ zeroBA] RETURNS [Mem]; MemGetStretch: PROC [mem: Mem] RETURNS [BitStretch] ~ INLINE {RETURN mem.class.GetStretch[mem.data]}; MemGetSize: PROC [mem: Mem] RETURNS [BitAddr] ~ INLINE {RETURN [mem.class.GetStretch[mem.data].size]}; MemGetStart: PROC [mem: Mem] RETURNS [BitAddr] ~ INLINE {RETURN [mem.class.GetStretch[mem.data].start]}; MemRead: PROC [mem: Mem, bitSize: CARD, offset: BitAddr] RETURNS [CARD] ~ INLINE {RETURN mem.class.Read[mem.data, bitSize, offset]}; MemWrite: PROC [mem: Mem, bits: CARD, bitSize: CARD, offset: BitAddr] ~ INLINE {mem.class.Write[mem.data, bits, bitSize, offset]}; MemPtrRegIndirect: PROC [mem: Mem, ptrReg: PtrReg, size, offset: BitAddr, keepFrame: BOOL] RETURNS [Mem]; MemReadPtrReg: PROC [mem: Mem, ptrReg: PtrReg] RETURNS [BitStretch] ~ INLINE {RETURN mem.class.ReadPtrReg[mem.data, ptrReg]}; MemReadSegReg: PROC [mem: Mem, segName: ROPE, segNum: INT] RETURNS [BitStretch] ~ INLINE {RETURN mem.class.ReadSegmentReg[mem.data, segName, segNum]}; MemSelectSegment: PROC [mem: Mem, segName: ROPE, segNum: INT, keepFrame: BOOL] RETURNS [Mem]; CreateSimpleMem: PROC[addr: CirioNubAccess.RemoteAddress, size: BitAddr _ unspecdBA] RETURNS[Mem]; MakeDualMem: PROC [nub: CirioNubAccess.Handle, fp, sp: CARD _ invalidPtr, text, data, bss, fep, simple: BitStretch _ unspecdBS] RETURNS [mem: Mem]; invalidPtr: CARD = CARD.LAST; END.  CirioMemory.mesa Copyright Ó 1991, 1992 by Xerox Corporation. All rights reserved. Laurie Horton, February 24, 1992 4:36 pm PST Last tweaked by Mike Spreitzer September 19, 1991 9:38 am PDT Philip James, February 25, 1992 9:24 am PST BitAddr A BitAddr represents a position in or length of memory. The first part is in Addressing Units (ie, increments of debuggee pointers). ABS[bits] < bitsPerAu. ptrSize: BitAddr ~ [4, 0]; Result is equivalent to arg, and has non-negative bits. Some BitStretchs may have size=unspecdBA, meaning the length is unknown. inner is interpreted relative to main; compd tells whether all of compd lies within main. Mem Mems are Node time information. They define a piece of memory with perhaps some structure. At the moment, there are two aspects of Memness: Frame and Simple. A Simple Mem represents a contiguous sequence of bits in memory; while the start of the sequence is always definite, the length may not be known (unspecdBA represents the unknown length). A Frame Mem represents a stack frame of a procedure at some level of abstraction. A Mem may be both Simple and Frame (this is needed for global vars, 'cause they are layed out simply, except for procedure constants). When reading and writing less than a whole CARD, the least significant bitSize bits are the significant ones. Every Mem can: Create another one, at the given absolute address, with the given size. If keepFrame, the result has the same Frameness as the argument; if NOT keepFrame, the result is purely simple. A Simple Mem can: Result has same Framness as arg; this is needed so that SelectVarLoc can return a Simple+Frame Mem for Cedar global variables. Used for pointer addition; size and Frameness don't change. A Frame Mem can: Both procedures raise Error when the segment or pointer is undefined. Since Mems are nominally immutable, this should only be called as part of constructing one. Create a Simple Mem. Create a Mem that is Frame and maybe Simple. Caller can decline to define some registers by passing invalidPtr or unspecdBS. Ê,•NewlineDelimiter ™code™K™BK™,K™=K™+—K˜KšÏk œ˜'K˜KšÏn œœ ˜Kšœ˜K˜Kšœœœ˜K˜™K™7K™š œ œœœœ˜.KšœNœ™d—K˜K˜Kš œœœœœ˜+K™Kšœ œ˜Kšœ œ˜K˜š žœœœœœ ˜5š œœœœœœ˜CKšœœ ˜5Kšœ˜!——K˜šžœœœ ˜.Kšœ2Ïeœ™7—K˜šžœœœ ˜-Kšœœœ%˜5K˜—šž œœœœ ˜K™~—š žœœœœœ˜;K™;—Kš ž œœœœœ˜6Kšžœœœœ œœœ˜JKš žœœœœœ œ˜H—™Kš ž œœœœœ˜Fšžœœœœ œ œœ˜VKšœE™E—šž œœœœ"˜@K™[——K˜—K˜šœœ˜KšœÏcœ˜Kšœ œ˜Kšœ ˜K˜—K˜Kšžœœœ˜K˜šž œœœ˜;Kšœœœ$˜4—K˜šžœœœ˜8Kšœœœ$˜4—K˜Kšž œœAœ˜`K˜šž œœ œ ˜3Kšœœœ!˜1—K˜šž œœ œ ˜-Kšœœœ(˜8—K˜šž œœ œ ˜.Kšœœœ)˜9—K˜š žœœœœœ˜GKšœœœ,˜<—K˜šžœœœ œ˜EKšœœ4˜<—K˜Kšžœœ>œœ˜iK˜šž œœœ ˜CKšœœœ)˜9—K˜š ž œœœ œœ ˜OKšœœœ6˜F—K˜Kš žœœœ œ œœ˜]K˜šžœœ@œ˜bK™——˜šž œœ&œEœ ˜“Kšœ}™}——K˜Kšœ œœœ˜K˜Kšœ˜—…—Ò