DIRECTORY XNSCHName, Rope, AlpInstance, AlpineEnvironment, AlpineEnvironmentP2201V1, XNS, XNSCH, XNSAuth, AlpineP2202V2, AlpInstanceV2Internal, AuthenticationP14V2, UserCredentials, CrRPC, RPC, Booting; AlpInstanceV2Impl: CEDAR MONITOR IMPORTS XNSCHName, Rope, CrRPC, XNSCH, XNSAuth, AlpineP2202V2, RPC, UserCredentials, Booting, AlpInstance EXPORTS AlpInstance ~ BEGIN OPEN AE: AlpineEnvironment, AlpI: AlpInstance; objectCache: LIST OF CacheRec _ NIL; CacheRec: TYPE = RECORD [ object: AlpI.Handle _ NIL, caller: AE.Principal _ NIL ]; Failed: PRIVATE ERROR [why: AlpInstance.Failure] _ AlpInstance.Failed; FindObjectInCache: INTERNAL PROCEDURE[fileStore: AE.FileStore, caller: AE.Principal, key: RPC.EncryptionKey, pwd: Rope.ROPE, identity: XNSAuth.Identity] RETURNS[handle: AlpI.Handle _ NIL] = BEGIN fileStoreName: XNSCHName.Name; realFileStore: Rope.ROPE _ fileStore; alpinePos: INT _ Rope.FindBackward[s1: fileStore, s2: ".alpine", case: FALSE]; IF fileStore.Length[] - alpinePos = 7 THEN realFileStore _ fileStore.Substr[len: alpinePos]; fileStoreName _ XNSCHName.NameFromRope[realFileStore]; realFileStore _ XNSCHName.RopeFromName[fileStoreName]; FOR list: LIST OF CacheRec _ objectCache, list.rest UNTIL list = NIL DO IF Rope.Equal[list.first.object.fileStore, fileStore, FALSE] THEN BEGIN IF Rope.Equal[list.first.caller, caller, FALSE] AND (key = list.first.object.key) THEN RETURN[list.first.object]; END; ENDLOOP; handle _ NEW[AlpI.Object _ [ trans: NIL, file: NIL, owner: NIL, volume: NIL, otherInterfaces: NIL, conversation: NIL, key: key, fileStore: fileStore]]; { serverAddress: REF XNS.Address ~ NEW[XNS.Address _ XNSCH.LookupAddressFromRope[realFileStore].address]; courierHandle: CrRPC.Handle ~ CrRPC.CreateClientHandle[$SPP, serverAddress]; authenticatedConversation: XNSAuth.Conversation ~ XNSAuth.Initiate[identity, fileStoreName]; credentials: XNSAuth.Credentials ~ XNSAuth.GetCredentials[authenticatedConversation]; verifier: XNSAuth.Verifier _ XNSAuth.GetNextVerifier[authenticatedConversation]; session: AlpineP2202V2.Session; [session, verifier] _ AlpineP2202V2.Logon[courierHandle, fileStoreName, credentials, [caller, pwd], verifier]; handle.otherInterfaces _ LIST[NEW[AlpInstanceV2Internal.InstanceObject _ [ , courierHandle, authenticatedConversation, credentials, session]]]; }; objectCache _ CONS[ [handle, caller], objectCache]; END; Create: PUBLIC ENTRY PROC [fileStore: AE.FileStore, caller: AE.Principal, key: RPC.EncryptionKey] RETURNS [handle: AlpI.Handle] ~ { connectionProblem: AlpineP2202V2.ConnectionProblem; authenticationProblem: AuthenticationP14V2.Problem; crReason: CrRPC.ErrorReason; identity: XNSAuth.Identity; psw: Rope.ROPE; { ENABLE { UNWIND => NULL; AlpineP2202V2.ConnectionError => {connectionProblem _ problem; GOTO connection}; AlpineP2202V2.AuthenticationError => { authenticationProblem _ problem; GOTO auth }; CrRPC.Error => SELECT errorReason FROM unknown, unknownClass, argsError, resultsError, bulkDataError, notImplemented, unknownOperation, notServerHandle, notClientHandle, addressInappropriateForClass, other => REJECT; ENDCASE => { crReason _ errorReason; GOTO rpcErr}; }; BEGIN [caller, psw] _ UserCredentials.Get[]; TRUSTED BEGIN key _ RPC.MakeKey[psw]; END; END; identity _ UserCredentials.GetIdentity[]; handle _ FindObjectInCache[fileStore, caller, key, psw, identity]; EXITS connection => RETURN WITH ERROR Failed[alpineDownOrCommunications]; auth => RETURN WITH ERROR RPC.AuthenticateFailed[badCaller]; -- no appropriate reason available. rpcErr => SELECT crReason FROM rejectedNoSuchProgram => RETURN WITH ERROR Failed[alpineDown]; rejectedNoSuchVersion, rejectedNoSuchProcedure => RETURN WITH ERROR Failed[mismatch]; communicationFailure, remoteClose, cantConnectToRemote => RETURN WITH ERROR Failed[alpineDownOrCommunications]; courierVersionMismatch, rejectedInvalidArgument, rejectedUnspecified, remoteError, protocolError => RETURN WITH ERROR Failed[alpineDownOrCommunications]; ENDCASE => ERROR; }; }; AlpRollbackProcedure: ENTRY Booting.RollbackProc = -- TYPE = PROC[clientData: REF ANY]; BEGIN ENABLE { UNWIND => NULL }; objectCache _ NIL; END; TRUSTED { Booting.RegisterProcs[c: , r: AlpRollbackProcedure]; }; END. AlpInstanceV2Impl.mesa Carl Hauser, November 11, 1987 6:43:24 pm PST Remove any .alpine from the name -- backward compatibility hack First, get a three part name for the fileStore (completing the domain and organization) subsequently, use the Rope version of the fully qualified name This is a terrible abuse of AlpInstance.Objects; for Courier we don't need trans, file, owner, and volume because we are never doing a local import. On the other hand, we need a place to hang our Courier handle and conversation so we'll use otherInterfaces in a stylized way. IF caller = NIL THEN have to ignore caller for now because can't make an RPC password out of a key. Change the Alpine interface so it takes a key instead of a password and this can change back. non system-fatal errors: none. Κα˜šœ™Icode™-—J™šΟk ˜ Kšœ ˜ Kšœ˜Kšœ ˜ Kšœ˜K˜Kšœ˜Kšœ˜Kšœ ˜ Kšœ˜Kšœ˜Kšœ˜Kšœ˜K˜Kšœ˜Kšœ˜K˜—K˜KšΟnœœ˜ Kšœb˜iKšœ ˜šœ˜K˜—Kšœœ'˜.K˜Kšœ œœ œ˜$šœ œœ˜Kšœ˜Kšœœ ˜K˜K˜—Kšžœ œ1˜FK˜š žœœ œ œœ˜YKšœœœœ˜cš˜Kšœ˜Kšœœ ˜%K™?Kšœ œ9œ˜NKšœ$œ2˜\K™WKšœ6˜6K™>Kšœ6˜6š œœœ"œ˜Gšœ4œœ˜GKš œ'œœœœ˜rKšœ˜——Kšœ˜šœ œ˜K™•Kšœœ˜ Kšœœ˜ Kšœœ˜ Kšœœ˜ Kšœœ˜Kšœœ˜K˜ K˜—˜Kš œœœ œœ œ/˜gKšœL˜LKšœ\˜\KšœU˜UKšœP˜PK˜Kšœn˜nKšœœœn˜K˜—Kšœœ!˜3—šœ˜K˜K˜——š žœœœœ œœ˜NKšœœ˜4Kšœ3˜3Kšœ3˜3Kšœ˜K˜Kšœ œ˜K˜˜šœ˜Kšœœ˜Kšœ?œ ˜PKšœ<œœ˜Tšœœ˜&Kšœͺœ˜±Kšœœ ˜2—Kšœ˜—šœ œ™K™­šœ˜K˜&Kšœœœœ˜*Kšœ˜——Kšœ)˜)KšœB˜Bš˜Kšœœœœ$˜CKš œœœœœ!Οc#˜ašœ œ œ˜Kšœœœœ˜?Kšœ2œœœ˜WKšœ:œœœ%˜pKšœdœœœ$˜™Kšœœ˜——K˜—K˜K˜—šœœŸ$˜WKšœ™Kšœ™š˜šœ˜Jšœ˜J˜—Kšœœ˜—šœ˜K˜K˜——Kšœœ8˜AK˜K˜Kšœ˜—…—Š‡