<> <> <> <> <> <> <> DIRECTORY MesaBasics USING [CHARPtr, WORDPtr], Basics; MesaBasicsImpl: PROGRAM IMPORTS Basics EXPORTS MesaBasics = { upw: CARDINAL = UNITS[WORD]; bitsPerWord: CARDINAL = BITS[WORD]; WORDPtr: TYPE ~ MesaBasics.WORDPtr; CHARPtr: TYPE = MesaBasics.CHARPtr; ExternalNames: PROC [] = TRUSTED MACHINE CODE { "^ExternalNames\n"; "MoveWords XR_MoveWords\n"; "MoveWordsDisjoint XR_MoveWordsDisjoint\n"; "EqualWords XR_EqualWords\n"; "MoveBytes XR_MoveBytes\n"; "MoveBytesDisjoint XR_MoveBytesDisjoint\n"; "ExtractField XR_ExtractField\n"; "DepositField XR_DepositField\n"; "MoveField XR_MoveField\n"; "EqualFields XR_EqualFields\n"; "FillFields XR_FillFields\n"; "FillLongFields XR_FillLongFields\n"; "FillWords XR_FillWords\n"; "FillLongWords XR_FillLongWords\n";}; MoveWords: PUBLIC PROC [dst, src: WORDPtr, len: CARDINAL] = { <> Basics.MoveWords[dst: LOOPHOLE[dst], src: LOOPHOLE[src], count: len]; }; <<>> MoveWordsDisjoint: PUBLIC PROC [dst, src: WORDPtr, len: CARDINAL] = { <> IF LOOPHOLE[dst, CARD] MOD 4 + LOOPHOLE[src, CARD] MOD 4 = 0 THEN { <> Basics.CopyWords[dst: LOOPHOLE[dst], src: LOOPHOLE[src], count: len]; } ELSE { <> MoveBytes[LOOPHOLE[dst], LOOPHOLE[src], len * BYTES[WORD]] }; }; <> EqualWords: PUBLIC PROC [src1, src2: WORDPtr, len: CARDINAL] RETURNS[CARD] = { c: Basics.Comparison ~ Basics.CompareBits[ aBase: LOOPHOLE[src1], aStart: 0, bBase: LOOPHOLE[src2], bStart: 0, count: len * BITS[WORD] ]; RETURN [ORD[c=equal]] }; MoveBytes: PUBLIC PROC [dest, src: CHARPtr, len: CARDINAL] = { <> check: [4..4] ~ BYTES[WORD]; dstStart: CARD ~ LOOPHOLE[dest, CARD] MOD BYTES[WORD]; srcStart: CARD ~ LOOPHOLE[src, CARD] MOD BYTES[WORD]; destWP: CARD ~ LOOPHOLE[dest, CARD]-dstStart; srcWP: CARD ~ LOOPHOLE[src, CARD]-srcStart; Basics.MoveBytes[ dstBase: LOOPHOLE[destWP], dstStart: dstStart, srcBase: LOOPHOLE[srcWP], srcStart: srcStart, count: len ] }; MoveBytesDisjoint: PUBLIC PROC [dest, src: CHARPtr, len: CARDINAL] = { <> check: [4..4] ~ BYTES[WORD]; dstStart: CARD ~ LOOPHOLE[dest, CARD] MOD BYTES[WORD]; srcStart: CARD ~ LOOPHOLE[src, CARD] MOD BYTES[WORD]; destWP: CARD ~ LOOPHOLE[dest, CARD]-dstStart; srcWP: CARD ~ LOOPHOLE[src, CARD]-srcStart; Basics.CopyBytes[ dstBase: LOOPHOLE[destWP], dstStart: dstStart, srcBase: LOOPHOLE[srcWP], srcStart: srcStart, count: len ]; }; ExtractField: PUBLIC PROC [base: WORDPtr, offset: INT, bits: CARD] RETURNS [WORD] = { <> w: WORD ¬ 0; WHILE offset < 0 DO offset ¬ offset + BITS[WORD]; base ¬ base - SIZE[WORD]; ENDLOOP; Basics.CopyBits[ dstBase: LOOPHOLE[@w], dstStart: BITS[WORD]-bits, srcBase: LOOPHOLE[base], srcStart: offset, count: bits ]; RETURN[w]; }; DepositField: PUBLIC PROC[base: WORDPtr, offset: INT, bits: CARD, w: WORD] = { <> WHILE offset < 0 DO offset ¬ offset + BITS[WORD]; base ¬ base - SIZE[WORD]; ENDLOOP; Basics.CopyBits[ dstBase: LOOPHOLE[base], dstStart: offset, srcBase: LOOPHOLE[@w], srcStart: BITS[WORD]-bits, count: bits ]; }; MoveField: PUBLIC PROC [dst: WORDPtr, dstOffset: INT, src: WORDPtr, srcOffset: INT, bits: CARD] = { <> WHILE dstOffset < 0 DO dstOffset ¬ dstOffset + BITS[WORD]; dst ¬ dst - SIZE[WORD]; ENDLOOP; WHILE srcOffset < 0 DO srcOffset ¬ srcOffset + BITS[WORD]; src ¬ src - SIZE[WORD]; ENDLOOP; Basics.CopyBits[ dstBase: LOOPHOLE[dst], dstStart: dstOffset, srcBase: LOOPHOLE[src], srcStart: srcOffset, count: bits ]; }; EqualFields: PUBLIC PROC[x: WORDPtr, xOffset: INT, y: WORDPtr, yOffset: INT, bits: CARD] RETURNS [INT] = { <> WHILE xOffset < 0 DO xOffset ¬ xOffset + BITS[WORD]; x ¬ x - SIZE[WORD]; ENDLOOP; WHILE yOffset < 0 DO yOffset ¬ yOffset + BITS[WORD]; y ¬ y - SIZE[WORD]; ENDLOOP; RETURN [ORD[Basics.CompareBits[LOOPHOLE[x], xOffset, LOOPHOLE[y], yOffset, bits]=equal]] }; FillFields: PUBLIC PROC [dst: WORDPtr, dstOffset: INT, bits: CARD, times: CARD, value: CARD] = { FillLongFields[dst, dstOffset, LOOPHOLE[@value], bitsPerWord - bits, bits, times]; }; FillLongFields: PUBLIC PROC [dst: WORDPtr, dstOffset: INT, src: WORDPtr, srcOffset: INT, bits: CARD, times: CARD] = { <> WHILE dstOffset < 0 DO dstOffset ¬ dstOffset + BITS[WORD]; dst ¬ dst - SIZE[WORD]; ENDLOOP; WHILE srcOffset < 0 DO srcOffset ¬ srcOffset + BITS[WORD]; src ¬ src - SIZE[WORD]; ENDLOOP; WHILE times > 0 DO Basics.CopyBits[ dstBase: LOOPHOLE[dst], dstStart: dstOffset, srcBase: LOOPHOLE[src], srcStart: srcOffset, count: bits ]; dstOffset ¬ dstOffset + bits; times ¬ times - 1; ENDLOOP; }; FillWords: PUBLIC PROC[dst: WORDPtr, times: CARD, value: CARD] = { <> IF LOOPHOLE[dst, CARD] MOD 4 # 0 THEN { WHILE times > 0 DO [] ¬ MoveWords[dst, LOOPHOLE[@value], 1]; dst ¬ dst + upw; times ¬ times - 1; ENDLOOP; } ELSE { Basics.FillWords[dst: LOOPHOLE[dst], count: times, value: value]; }; }; FillLongWords: PUBLIC PROC[dst, src: WORDPtr, nWords, times: CARD] = { <> IF (nWords = 1) THEN FillWords[dst, times, src[0]] ELSE WHILE times > 0 DO [] ¬ MoveWords[dst, src, nWords]; dst ¬ dst + nWords*upw; times ¬ times - 1; ENDLOOP; }; ExternalNames[]; }...