DIRECTORY CrRPC USING [Call, CreateClientHandle, DestroyClientHandle, Error, GetCARDINAL, GetFWORD, GetHWORD, GetResultsProc, Handle, PutArgsProc, SetHops, SetTimeout], Endian USING [FWORD, HWORD], XNS USING [Address, broadcastHost, broadcastNet, Socket], XNSServerLocation USING [EachAddressProc]; XNSServerLocationImpl: CEDAR PROGRAM IMPORTS CrRPC EXPORTS XNSServerLocation ~ { FWORD: TYPE ~ Endian.FWORD; HWORD: TYPE ~ Endian.HWORD; maxPermissibleRadius: CARDINAL ~ 6; -- broadcasting to the entire Internet would be antisocial GetXNSAddress: PROC [h: CrRPC.Handle] RETURNS [XNS.Address] ~ { xNet: FWORD; xHost: MACHINE DEPENDENT RECORD [a, b, c: HWORD]; xSocket: HWORD; xNet _ CrRPC.GetFWORD[h]; xHost.a _ CrRPC.GetHWORD[h]; xHost.b _ CrRPC.GetHWORD[h]; xHost.c _ CrRPC.GetHWORD[h]; xSocket _ CrRPC.GetHWORD[h]; TRUSTED { RETURN [ [net~LOOPHOLE[xNet], host~LOOPHOLE[xHost], socket~LOOPHOLE[xSocket]] ] }; }; StopListening: ERROR ~ CODE; LocateServers: PUBLIC PROC [ socket: XNS.Socket, -- destination socket for broadcast maxHops: CARDINAL, -- radius of broadcast remotePgm: CARD, remotePgmVersion: CARDINAL, eachAddress: XNSServerLocation.EachAddressProc, -- called with address of each responding server firstResponseOnly: BOOL _ TRUE ] ~ { h: CrRPC.Handle; PutArgs: CrRPC.PutArgsProc ~ { NULL }; GetResults: CrRPC.GetResultsProc ~ { n: CARDINAL; addr: XNS.Address; n _ CrRPC.GetCARDINAL[h]; IF n > 0 THEN { addr _ GetXNSAddress[h]; eachAddress[addr]; IF firstResponseOnly THEN ERROR StopListening[] } }; maxHops _ MIN[maxHops, maxPermissibleRadius]; h _ CrRPC.CreateClientHandle[ class~$EXCHANGE, remote~[net~XNS.broadcastNet, host~XNS.broadcastHost, socket~socket]]; BEGIN ENABLE StopListening => CONTINUE; FOR hops: CARDINAL IN [0..maxHops] DO h _ CrRPC.SetHops[h~h, low~hops, high~hops]; h _ CrRPC.SetTimeout[h, 200 + 300 * hops]; THROUGH [0..4) DO CrRPC.Call[ h~h, remotePgm~remotePgm, remotePgmVersion~remotePgmVersion, remoteProc~0, putArgs~PutArgs, getResults~GetResults ! CrRPC.Error => CONTINUE]; ENDLOOP; ENDLOOP; END; CrRPC.DestroyClientHandle[h]; }; }. JXNSServerLocationImpl.mesa Demers, October 2, 1986 5:14:34 pm PDT ΚΏ˜code™K™&J™—šΟk ˜ Kšœœ“˜žKšœœœœ˜Kšœœ0˜9Kšœœ˜*K˜—šΟnœœ˜$Kšœ˜ Kšœ˜Kšœ˜K˜Kšœœ œ˜Kšœœ œ˜K˜KšœœΟc:˜_K˜šž œœœœ ˜?Kšœœ˜ Kš œœ œœ œ˜1Kšœ œ˜Kšœ˜Kšœ˜Kšœ˜Kšœ˜Kšœ˜šœœ˜Kšœœ œœ˜I—K˜K˜—Kšž œœœ˜K˜šž œœœ œ Ÿ$œ œŸœ œœ2Ÿ1œœœ˜±K˜Kšžœœ˜&šž œ˜$Kšœœ˜ Kšœœ ˜Kšœ˜šœœ˜Kšœ˜Kšœ˜Kšœœœ˜1—K˜—Kšœ œ ˜-šœ˜Kšœ˜Kšœ œœ ˜F—š˜Kšœœ˜!šœœœ˜%Kšœ,˜,Kšœ*˜*šœ˜šœ ˜ KšœJ˜JK˜&Kšœœ˜—Kšœ˜—Kšœ˜—Kšœ˜—Kšœ˜K˜—K˜——…— )