YggDIDImpl.mesa
Copyright Ó 1988, 1989 by Xerox Corporation. All rights reserved.
Bob Hagmann January 4, 1989 2:48:24 pm PST
Handle all operations on DID's.
DIRECTORY
Basics USING [charsPerWord, Comparison],
PBasics USING [BITAND, BITXOR, bytesPerWord, Comparison, LongNumber, Move],
Rope USING [ROPE],
YggDID USING [],
YggDIDPrivate USING [DIDRep, HighDIDSystemReserved, LowForIndexMaint, LowForNFSRoot, LowForRootDIDs],
YggDIDMap USING [OpenDocumentFromDID],
YggEnvironment USING [nullTransID],
YggRep USING [TimeStamp];
YggDIDImpl: CEDAR PROGRAM
IMPORTS Basics, PBasics, YggDIDMap
EXPORTS YggDID, YggDIDPrivate, YggRep
~ BEGIN
ROPE: TYPE ~ Rope.ROPE;
DID: PUBLIC TYPE ~ REF DIDRep;
DIDRep: PUBLIC TYPE ~ YggDIDPrivate.DIDRep;
FirstDID: PUBLIC DID ;
LastDID: PUBLIC DID ;
DIDForRootDIDs: PUBLIC DID ← NEW[DIDRep ← [didHigh: YggDIDPrivate.HighDIDSystemReserved, didLow: YggDIDPrivate.LowForRootDIDs]];
DIDForIndexMaint: PUBLIC DID ← NEW[DIDRep ← [didHigh: YggDIDPrivate.HighDIDSystemReserved, didLow: YggDIDPrivate.LowForIndexMaint]];
DIDForNFSRoot: PUBLIC DID ← NEW[DIDRep ← [didHigh: YggDIDPrivate.HighDIDSystemReserved, didLow: YggDIDPrivate.LowForNFSRoot]];
AllNulls: PACKED ARRAY [0..Basics.charsPerWord) OF CHARALL[0C];
Exported procedures
ValidateDID: PUBLIC PROC [did: DID] RETURNS [ok: BOOL ← TRUE] = {
Validate the did.
IF YggDIDMap.OpenDocumentFromDID[did: did, tid: YggEnvironment.nullTransID] = NIL THEN RETURN [FALSE];
};
CompareDIDs: PUBLIC PROC [did: DID, stableDID: LONG POINTER] RETURNS [Basics.Comparison] = {
Compare the did and stableDID.
sDID: LONG POINTER TO DIDRep;
IF did = NIL THEN ERROR;
sDID ← LOOPHOLE[stableDID];
IF sDID = NIL THEN ERROR;
TRUSTED {
SELECT did.didHigh FROM
> sDID.didHigh => RETURN [greater];
< sDID.didHigh => RETURN [less];
ENDCASE => SELECT did.didLow FROM
> sDID.didLow => RETURN [greater];
< sDID.didLow => RETURN [less];
ENDCASE => RETURN [equal];
};
};
EqualDIDs: PUBLIC PROC [did1: DID, did2: DID] RETURNS [equal: BOOL] = {
Compare the dids.
IF did1 = NIL AND did2 = NIL THEN RETURN [TRUE];
IF did1 = NIL OR did2 = NIL THEN RETURN [FALSE];
IF did1.didHigh = did2.didHigh AND did1.didLow = did2.didLow THEN RETURN [TRUE] ELSE RETURN [FALSE]
};
SizeForDID: PUBLIC PROC [did: DID] RETURNS [bytes: INT] = {
Return the size of the did. The size in in bytes rounded up to the next word.
ddd: DIDRep;
IF did = NIL THEN ERROR;
ddd ← did^;
bytes ← BYTES[DIDRep];
};
StabilizeDID: PUBLIC PROC [did: DID, buffer: LONG POINTER] = {
Take a DID and write it to a buffer.
IF did = NIL THEN ERROR;
TRUSTED {PBasics.Move[dst: buffer, src: LOOPHOLE[did], nWords: BYTES[DIDRep]/PBasics.bytesPerWord];};
};
VolatilizeDID: PUBLIC PROC [buffer: LONG POINTER] RETURNS [did: DID] = {
Take a buffer and construct a DID.
did ← NEW[DIDRep];
TRUSTED {PBasics.Move[dst: LOOPHOLE[did], src: buffer, nWords: BYTES[DIDRep]/PBasics.bytesPerWord];};
};
HashDID: PUBLIC PROC [did: DID] RETURNS [hash: CARD32] = {
A did always hashes to the same value for any given version of the software (this is only for volatile use!)
IF did = NIL THEN ERROR;
hash ← PBasics.BITXOR[did.didHigh, did.didLow];
};
StableHashDID: PUBLIC PROC [did: DID] RETURNS [hash: CARD32] = {
A did always hashes to the same value for all versions of the software (this is for stable use)
hashTemp: PBasics.LongNumber;
hashTemp.card ← PBasics.BITXOR[did.didHigh, did.didLow];
hash ← hashTemp.hh + hashTemp.hl + hashTemp.lh + hashTemp.ll;
hash ← PBasics.BITAND[hash, 0FFh];
};
NextTimeStamp: PUBLIC PROC [current: YggRep.TimeStamp] RETURNS [next: YggRep.TimeStamp] ~ {
next ← [current + 1];
};
MaxTimeStamp: PUBLIC PROC [ts1: YggRep.TimeStamp, ts2: YggRep.TimeStamp] RETURNS [maxTS: YggRep.TimeStamp] ~ {
maxTS ← IF ts1 > ts2 THEN ts1 ELSE ts2;
};
CompareTimeStamps: PUBLIC PROC [ts1: YggRep.TimeStamp, ts2: YggRep.TimeStamp] RETURNS [PBasics.Comparison] ~ {
SELECT TRUE FROM
ts1 > ts2 => RETURN[greater];
ts1 < ts2 => RETURN[less];
ENDCASE => RETURN[equal];
};
Initialization
FirstDID ← NEW[DIDRep];
FirstDID^ ← [0,0];
LastDID ← NEW[DIDRep];
LastDID^ ← [LAST[CARD32], LAST[CARD32]];
END.