<> <> <> <<>> DIRECTORY Basics USING [BITOR, BITSHIFT, bitsPerWord], PupDefs USING [AnyLocalPupAddress, GetMyName, PupAddressToRope], PupTypes USING [PupAddress], ProcessorFace USING [processorID, ProcessorID], RefText USING [AppendChar, AppendRope, ObtainScratch, ReleaseScratch], Rope USING [FromRefText, Find, Length, Substr, ROPE], ThisMachine USING []; ThisMachineImpl: CEDAR PROGRAM IMPORTS Basics, ProcessorFace, PupDefs, RefText, Rope EXPORTS ThisMachine = { ROPE: TYPE = Rope.ROPE; Name: PUBLIC PROC [which: ATOM] RETURNS [rope: ROPE _ NIL] = { SELECT which FROM NIL, $Pup => { rope _ PupDefs.GetMyName[]; IF Rope.Find[rope, "#"] # -1 THEN RETURN[NIL]; }; ENDCASE => RETURN[NIL]; }; <<>> Address: PUBLIC PROC [which: ATOM] RETURNS [rope: ROPE _ NIL] = { SELECT which FROM NIL, $Pup => { me: PupTypes.PupAddress _ PupDefs.AnyLocalPupAddress[[0,0]]; IF me.net = 0 OR me.host = 0 THEN RETURN[NIL]; me.socket _ [0,0]; rope _ PupDefs.PupAddressToRope[me]; rope _ Rope.Substr[rope, 0, Rope.Length[rope]-1]; }; ENDCASE => RETURN[NIL]; }; <<>> ProcessorID: PUBLIC PROC [which: ATOM] RETURNS [rope: ROPE _ NIL] = { text: REF TEXT _ RefText.ObtainScratch[maxDigits]; me: ProcessorFace.ProcessorID _ ProcessorFace.processorID; words: Words; format: Format; TRUSTED { words _ LOOPHOLE[@me]; }; SELECT which FROM NIL, $Octal => format _ octal; $Decimal, $ProductSoftware => format _ productSoftware; $Hex => format _ hex; ENDCASE => RETURN; text _ AppendField[text, words, SIZE[ProcessorFace.ProcessorID], format]; rope _ Rope.FromRefText[text]; RefText.ReleaseScratch[text]; }; <<>> maxDigits: NAT = MAX[16]; Digits: TYPE = ARRAY [0..maxDigits) OF NAT; Format: TYPE = {octal, productSoftware, hex}; Words: TYPE = POINTER TO ARRAY [0..3) OF WORD; UnrecognizedFormatOption: ERROR = CODE; <> AppendField: PROC [text: REF TEXT, words: Words, count: NAT, format: Format] RETURNS [REF TEXT] = { digits: Digits; base: NAT; SELECT format FROM octal => base _ 8; productSoftware => base _ 10; hex => base _ 16; ENDCASE => ERROR UnrecognizedFormatOption; TRUSTED { ConvertToDigits[words, count, base, @digits]; text _ AppendDigits[text, @digits, base = 10]; }; IF base = 16 THEN text _ RefText.AppendChar[text, 'H]; RETURN[text]; }; ConvertToDigits: PROC [words: Words, size, base: NAT, digits: POINTER TO Digits] = TRUSTED { digits^ _ ALL[0]; FOR i: NAT IN [0..size*Basics.bitsPerWord) DO bit: CARDINAL _ ShiftFieldLeft[words, size, 1]; FOR j: NAT DECREASING IN [0..maxDigits) DO digits[j] _ digits[j]*2 + bit; IF digits[j] >= base THEN { digits[j] _ digits[j] - base; bit _ 1; } ELSE bit _ 0; ENDLOOP; ENDLOOP; }; ShiftFieldLeft: PROC [words: Words, count: NAT, shift: INTEGER] RETURNS [left: NAT] = TRUSTED { right: WORD _ 0; FOR i: NAT DECREASING IN [0..count) DO left _ Basics.BITSHIFT[words[i], shift - 16]; words[i] _ Basics.BITOR[Basics.BITSHIFT[words[i], shift], right]; right _ left; ENDLOOP; }; AppendDigits: PROC [text: REF TEXT, digits: POINTER TO Digits, dashes: BOOL] RETURNS [REF TEXT] = TRUSTED { something: BOOL _ FALSE; FOR i: NAT IN [0..maxDigits) DO v: NAT _ digits[i]; IF dashes AND something AND (maxDigits - i) MOD 3 = 0 THEN text _ RefText.AppendChar[text, '-]; IF v # 0 AND ~something THEN { IF dashes THEN { SELECT maxDigits - i FROM 1 => text _ RefText.AppendRope[text, "0-00"]; 2 => text _ RefText.AppendRope[text, "0-0"]; 3 => text _ RefText.AppendRope[text, "0-"]; ENDCASE => NULL; }; IF v > 9 THEN text _ RefText.AppendChar[text, '0]; -- Leading digit for Hex case something _ TRUE; }; IF something THEN { c: CHAR _ IF v > 9 THEN v - 10 + 'A ELSE v + '0; text _ RefText.AppendChar[text, c]; }; ENDLOOP; IF ~something THEN text _ RefText.AppendChar[text, '0]; RETURN[text]; }; }.