<> <> <> <> DIRECTORY Basics, BasicTime, ComputeServerCallbacks, ComputeServerCallbacksRpcControl, ComputeServerInternal, CountedVM, File, FS, FSBackdoor, FSDir, FSName, FSLock, FSFileOps, FSReport, IO, Loader, PrincOps USING [ PDA, PsbIndex, StartPsb], PrincOpsUtils, ProcessBackdoor USING[ParentChildCallback, RegisterEventProcs, SingleCallback], ProcessProps, Rope, RPC, SafeStorage, UnsafeStorage USING [GetSystemUZone], UserCredentials, UserCredentialsBackdoor, UserProfile, UserProfileBackdoor; ComputeServerServicesImpl: CEDAR MONITOR IMPORTS BasicTime, ComputeServerCallbacks, ComputeServerCallbacksRpcControl, ComputeServerInternal, CountedVM, File, FS, FSBackdoor, FSDir, FSFileOps, FSLock, FSName, FSReport, IO, Loader, ProcessBackdoor, ProcessProps, PrincOpsUtils, Rope, RPC, SafeStorage, UnsafeStorage, UserCredentialsBackdoor, UserProfileBackdoor EXPORTS ComputeServerInternal = BEGIN <> ROPE: TYPE = Rope.ROPE; STREAM: TYPE = IO.STREAM; ParentChildCallback: TYPE = ProcessBackdoor.ParentChildCallback; SingleCallback: TYPE = ProcessBackdoor.SingleCallback; StateArrayRec: TYPE ~ RECORD [SEQUENCE length: NAT OF LONG POINTER]; OverrideArrayRec: TYPE ~ RECORD [SEQUENCE length: NAT OF BOOL]; stateArray: LONG POINTER TO StateArrayRec ; fsOverride: LONG POINTER TO OverrideArrayRec; allOverride: LONG POINTER TO OverrideArrayRec; <> forks: INT _ 0 ; joins: INT _ 0 ; detatchs: INT _ 0 ; ends: INT _ 0 ; ActiveServicesItem: TYPE = ComputeServerInternal.ActiveServicesItem; localOpenFile: TYPE = REF localOpenFileObject; localOpenFileObject: TYPE = RECORD[ remoteFile: BOOL _ TRUE, remoteFileID: ComputeServerCallbacks.OpenFile, localFile: FS.OpenFile _ FS.nullOpenFile, serviceItem: ActiveServicesItem _ NIL, interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ NIL ]; LocalOpenFileType: SafeStorage.Type _ CODE[localOpenFile]; <> <> <<>> myFork: ParentChildCallback = TRUSTED { forks _ forks + 1; stateArray[childPsb] _ stateArray[parentPsb]; }; myJoin: ParentChildCallback = TRUSTED { joins _ joins + 1; stateArray[childPsb] _ NIL ; }; myDetatch: SingleCallback = TRUSTED { detatchs _ detatchs + 1; }; myEnd: SingleCallback = TRUSTED { ends _ ends + 1; stateArray[Psb] _ NIL ; }; <> MarkGuestProcess: PUBLIC ENTRY PROC [process: PROCESS, data: LONG POINTER] RETURNS [ok: BOOL _ TRUE, oldData: LONG POINTER] = TRUSTED { psb: PrincOps.PsbIndex = LOOPHOLE[process]; IF psb < PrincOps.StartPsb + PrincOps.PDA.count THEN { stateArray[psb] _ data ; fsOverride[psb] _ FALSE; allOverride[psb] _ FALSE; } ELSE ok _ FALSE; }; GetGuestProcessData: PUBLIC ENTRY PROC [process: PROCESS] RETURNS [data: LONG POINTER] = TRUSTED { psb: PrincOps.PsbIndex = LOOPHOLE[process]; RETURN [stateArray[psb]]; }; MarkProcessNotGuest: PUBLIC ENTRY PROC [process: PROCESS] = TRUSTED { psb: PrincOps.PsbIndex = LOOPHOLE[process]; allOverride[psb] _ TRUE; }; RemoveMarkProcessNotGuest: PUBLIC ENTRY PROC [process: PROCESS] = TRUSTED { psb: PrincOps.PsbIndex = LOOPHOLE[process]; allOverride[psb] _ FALSE; }; MarkProcessUseLocalFS: PUBLIC ENTRY PROC [process: PROCESS] = TRUSTED { psb: PrincOps.PsbIndex = LOOPHOLE[process]; fsOverride[psb] _ TRUE; }; RemoveMarkProcessUseLocalFS: PUBLIC ENTRY PROC [process: PROCESS] = TRUSTED { psb: PrincOps.PsbIndex = LOOPHOLE[process]; fsOverride[psb] _ FALSE; }; <> myFSIsGuestProcess: PROC [] RETURNS [isGuest: BOOL] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; RETURN [~fsOverride[psb] AND ~allOverride[psb] AND stateArray[psb] # NIL] ; }; mySetDefaultWDir: PROC [dir: Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem _ LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[interface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; interface.rSetDefaultWDir[dir]; }; }; myGetDefaultWDir: PROC RETURNS [Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem _ LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[interface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; RETURN[interface.rGetDefaultWDir[]]; }; }; myExpandName: PROC[name: ROPE, wDir: ROPE] RETURNS [useDefault: BOOL _ FALSE, fullFName: ROPE, cp: FS.ComponentPositions, dirOmitted: BOOLEAN _ FALSE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[interface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; RPC.CallFailed => ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; processWDIR: ROPE _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; IF processWDIR # NIL OR (Rope.Length[name] > 0 AND (Rope.Fetch[name, 0] = '[ OR Rope.Fetch[name, 0] = '[ )) OR Rope.Length[wDir] # 0 THEN { <> useDefault _ TRUE; } ELSE { <> [fullFName, cp, dirOmitted] _ interface.rExpandName[name,wDir]; }; }; }; myFileInfo: PROC [name: ROPE, wantedCreatedTime: BasicTime.GMT, remoteCheck: BOOLEAN, wDir: ROPE] RETURNS [fullFName, attachedTo: ROPE, keep: CARDINAL, bytes: INT, created: BasicTime.GMT] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; RPC.CallFailed => ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [fullFName, attachedTo, keep, bytes, created] _ interface.rFileInfo[name, wantedCreatedTime, remoteCheck, wDir]; }; }; myEnumerateForInfo: PROC [pattern: ROPE, proc: FS.InfoProc, wDir: ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; fullFName, attachedTo: ROPE; created: BasicTime.GMT; bytes: INT; keep: CARDINAL; continue: BOOLEAN; IF ~testAndSetDoingEnumerate[serviceItem] THEN ERROR FS.Error[[group: client, code: $nestedEnumerate, explanation: "Enumeration cannot be nested using the Summoner"]]; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [fullFName, attachedTo, created, bytes, keep, continue] _ interface.rStartEnumerateForInfo[serviceItem.listenerPupAddress, pattern, wDir]; WHILE continue DO continue _ proc[fullFName, attachedTo, created, bytes, keep]; IF continue THEN [fullFName, attachedTo, created, bytes, keep, continue] _ interface.rNextEnumerateForInfo[serviceItem.listenerPupAddress] ELSE interface.rDoneEnumerate[serviceItem.listenerPupAddress]; ENDLOOP; clearDoingEnumerate[serviceItem]; }; }; myEnumerateForNames: PROC [pattern: ROPE, proc: FS.NameProc, wDir: ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; fullFName: ROPE; continue: BOOLEAN; IF ~testAndSetDoingEnumerate[serviceItem] THEN ERROR FS.Error[[group: client, code: $nestedEnumerate, explanation: "Enumeration cannot be nested using the Summoner"]]; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [fullFName, continue] _ interface.rStartEnumerateForNames[serviceItem.listenerPupAddress, pattern, wDir]; WHILE continue DO continue _ proc[fullFName]; IF continue THEN [fullFName, continue] _ interface.rNextEnumerateForNames[serviceItem.listenerPupAddress] ELSE interface.rDoneEnumerate[serviceItem.listenerPupAddress]; ENDLOOP; clearDoingEnumerate[serviceItem]; }; }; makeFileFromMyFile: PROC[myOpenFile: localOpenFile] RETURNS [file: FS.OpenFile] = { fileProcs: REF FSBackdoor.FileProcs ; fileProcs _ FSBackdoor.CreateFileProcs [ GetClass: getClassProc, SameFile: sameFileProc, GetName: getNameProc, GetInfo: getInfoProc, SetPageCount: setPageCountProc, SetByteCountAndCreatedTime: setByteCountAndCreatedTimeProc, Read: readProc, Write: writeProc, Close: closeProc ] ; file _ FSBackdoor.CreateProcsOpenFile[clientFile: myOpenFile, fileProcs: fileProcs]; LocalOpenFileType _ SafeStorage.GetReferentType[file]; }; myOpen: PROC [name: ROPE, lock: FS.Lock _ $read, wantedCreatedTime: BasicTime.GMT _ BasicTime.nullGMT, remoteCheck: BOOLEAN _ TRUE, wDir: ROPE _ NIL] RETURNS [file: FS.OpenFile] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; serviceREF: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[serviceItem]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; myOpenFile: localOpenFile _ NEW[localOpenFileObject]; globalNameToOpen: ROPE; localFullFName: ROPE; cp: FS.ComponentPositions; dirOmitted: BOOL; myOpenFile.serviceItem _ serviceREF; myOpenFile.interface _ interface ; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [fullFName: localFullFName, cp: cp, dirOmitted: dirOmitted] _ FS.ExpandName[name: name, wDir: wDir]; IF Rope.Equal[Rope.Substr[base: localFullFName, start: cp.server.start, len: cp.server.length], "SummonerServer"] THEN { IF ComputeServerInternal.OKToUseLocalDisk THEN { localName: ROPE; savedError: FS.ErrorDesc; localOpenOK: BOOL _ TRUE; localName _ Rope.Concat["[]<", Rope.Substr[localFullFName, cp.dir.start]]; fsOverride[psb] _ TRUE; file _ FS.Open[localName, lock, wantedCreatedTime, remoteCheck ! FS.Error => { localOpenOK _ FALSE; savedError _ error; CONTINUE; } ]; fsOverride[psb] _ FALSE; IF localOpenOK THEN { RETURN[file]; } ELSE ERROR FS.Error[savedError]; } ELSE { ERROR FS.Error[[ environment, $SeverMachineWillNotAllowUseOfLocalDisk, Rope.Cat["Attempt to open a file on logical server 'SummonerServer' for file name ", localFullFName, "while the Server was not setup to allow access to it's local file system"]]]; }; }; [globalNameToOpen: globalNameToOpen, openFile: myOpenFile.remoteFileID] _ interface.rOpen[serviceItem.listenerPupAddress, name, lock, wantedCreatedTime, remoteCheck, wDir, FALSE]; IF Rope.Length[globalNameToOpen] > 0 THEN { -- We are trying to open an attachment localOpenFailed: BOOL _ TRUE; gotIt: BOOL _ FALSE; cacheNameProc: FSBackdoor.NameProc = TRUSTED { gotIt _ TRUE; }; FSBackdoor.EnumerateCacheForNames[proc: cacheNameProc, volName: NIL, pattern: globalNameToOpen]; IF gotIt THEN { fsOverride[psb] _ TRUE; localOpenFailed _ FALSE; myOpenFile.localFile _ FS.Open[globalNameToOpen ! FS.Error => {localOpenFailed _ TRUE; CONTINUE;} ]; fsOverride[psb] _ FALSE; }; IF localOpenFailed THEN { IF myOpenFile.remoteFileID = -1 THEN { -- Flag for read file from client's cache into server's cache newFP: File.FP _ File.nullFP; newFile: File.Handle _ NIL; retreiveStarted: BOOL _ FALSE; pn: FSName.ParsedFName; a: FSLock.ActiveFile _ NIL; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => TRUSTED { GOTO skipOnError; }; FS.Error, File.Error, ABORTED => { IF newFile # NIL THEN { File.Delete[newFile ! File.Error => CONTINUE;]; }; IF retreiveStarted THEN { FSReport.ReportRemote[endRetrieving, pn.fullName]; retreiveStarted _ FALSE; }; FSLock.ReleaseRecord[a]; GOTO skipOnError; }; }; remoteFile: FS.OpenFile; bytes: INT; created: BasicTime.GMT; remoteFileStream: STREAM _ NIL; bytesLeft: INT; unsafeDataBlock: Basics.UnsafeBlock ; bufferHandle: CountedVM.Handle; nowPage: File.PageNumber _ [0]; fp: File.FP; pagesInABuffer: INT = 8; bytesInABuffer: INT = FS.BytesForPages[8]; [pn, ] _ FSName.ParseClientName[globalNameToOpen, NIL]; [fp, a] _ FSDir.AcquireOldOrNewGName[pn.volDesc, pn.nameBody, pn.version]; [openFile: myOpenFile.remoteFileID] _ interface.rOpen[serviceItem.listenerPupAddress, name, lock, wantedCreatedTime, remoteCheck, wDir, TRUE]; remoteFile _ makeFileFromMyFile[myOpenFile]; remoteFileStream _ FS.StreamFromOpenFile[openFile: remoteFile, streamOptions: [FALSE, FALSE, FALSE, FALSE, FALSE], streamBufferParms: [pagesInABuffer, 2]]; [bytes: bytes, created: created] _ interface.rGetInfo[serviceItem.listenerPupAddress, myOpenFile.remoteFileID ! ComputeServerCallbacks.Error => {ERROR FS.Error[error]; }]; [newFP, newFile] _ FSFileOps.CreateFile[pn.volDesc.vol, FS.PagesForBytes[bytes]]; bytesLeft _ bytes; bufferHandle _ CountedVM.SimpleAllocate[bytesInABuffer]; unsafeDataBlock.base _ bufferHandle.pointer; FSReport.ReportRemote[startRetrieving, pn.fullName]; retreiveStarted _ TRUE; unsafeDataBlock.count _ bytesInABuffer; WHILE bytesLeft > 0 DO readCount: INT; nPages: File.PageCount; readCount _ remoteFileStream.UnsafeGetBlock[unsafeDataBlock]; IF readCount # MIN[bytesLeft, bytesInABuffer] THEN GOTO skipOnError; bytesLeft _ bytesLeft - readCount ; nPages _ FS.PagesForBytes[readCount]; File.Write[file: newFile, to: nowPage, nPages: nPages, from: bufferHandle.pointer]; nowPage _ [nowPage + nPages]; ENDLOOP; FSReport.ReportRemote[endRetrieving, pn.fullName]; FSFileOps.SetProps[newFile, bytes, 0, created, pn.nameBody, pn.version]; FSDir.UpdateCachedEntry[pn.volDesc, pn.nameBody, pn.version, BasicTime.Now[], newFP, insert]; interface.rClose[serviceItem.listenerPupAddress, myOpenFile.remoteFileID ! ComputeServerCallbacks.Error => {ERROR FS.Error[error]; }]; FSLock.ReleaseRecord[a]; fsOverride[psb] _ TRUE; localOpenFailed _ FALSE; myOpenFile.localFile _ FS.Open[globalNameToOpen ! FS.Error => {localOpenFailed _ TRUE; CONTINUE;} ]; fsOverride[psb] _ FALSE; IF ~localOpenFailed THEN { myOpenFile.remoteFile _ FALSE; RETURN[makeFileFromMyFile[myOpenFile]]; }; EXITS skipOnError => { IF newFile # NIL THEN { File.Delete[newFile ! File.Error => CONTINUE;]; }; IF retreiveStarted THEN FSReport.ReportRemote[endRetrieving, pn.fullName]; FSLock.ReleaseRecord[a]; }; }; } ELSE { -- myOpenFile.remoteFileID # -1 => load cache from file server localOpenFailed _ FALSE; myOpenFile.localFile _ FS.Open[globalNameToOpen ! FS.Error => {localOpenFailed _ TRUE; CONTINUE;} ]; IF ~localOpenFailed THEN myOpenFile.remoteFile _ FALSE; }; IF localOpenFailed THEN [globalNameToOpen: globalNameToOpen, openFile: myOpenFile.remoteFileID] _ interface.rOpen[serviceItem.listenerPupAddress, name, lock, wantedCreatedTime, remoteCheck, wDir, TRUE]; } ELSE myOpenFile.remoteFile _ FALSE; }; file _ makeFileFromMyFile[myOpenFile]; }; }; myCreate: PROC [name: ROPE, setPages: BOOLEAN _ TRUE, pages: INT _ 0, setKeep: BOOLEAN _ FALSE, keep: CARDINAL _ 1, wDir: ROPE _ NIL] RETURNS [file: FS.OpenFile] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; serviceREF: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[serviceItem]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; myOpenFile: localOpenFile _ NEW[localOpenFileObject]; localFullFName: ROPE; cp: FS.ComponentPositions; dirOmitted: BOOL; myOpenFile.serviceItem _ serviceREF; myOpenFile.interface _ interface ; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [fullFName: localFullFName, cp: cp, dirOmitted: dirOmitted] _ FS.ExpandName[name: name, wDir: wDir]; IF Rope.Equal[Rope.Substr[base: localFullFName, start: cp.server.start, len: cp.server.length], "SummonerServer"] THEN { IF ComputeServerInternal.OKToUseLocalDisk THEN { localName: ROPE; savedError: FS.ErrorDesc; localOpenOK: BOOL _ TRUE; localName _ Rope.Concat["[]<", Rope.Substr[localFullFName, cp.dir.start]]; fsOverride[psb] _ TRUE; file _ FS.Create[localName, setPages, pages, setKeep, keep ! FS.Error => { localOpenOK _ FALSE; savedError _ error; CONTINUE; } ]; fsOverride[psb] _ FALSE; IF localOpenOK THEN { RETURN[file]; } ELSE ERROR FS.Error[savedError]; } ELSE { ERROR FS.Error[[ environment, $SeverMachineWillNotAllowUseOfLocalDisk, Rope.Cat["Attempt to open a file on logical server 'SummonerServer' for file name ", localFullFName, "while the Server was not setup to allow access to it's local file system"]]]; }; }; myOpenFile.remoteFileID _ interface.rCreate[serviceItem.listenerPupAddress, name, setPages, pages, setKeep, keep, wDir]; file _ makeFileFromMyFile[myOpenFile]; }; }; myCopy: PROC [from, to: ROPE, setKeep: BOOL, keep: CARDINAL, wantedCreatedTime: BasicTime.GMT, remoteCheck: BOOL, attach: BOOL, wDir: Rope.ROPE] RETURNS [toFName: ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [toFName: toFName] _ interface.rCopy[serviceItem.listenerPupAddress, from, to, setKeep, keep, wantedCreatedTime, remoteCheck, attach, wDir]; }; }; myDelete: PROC [name: ROPE, wantedCreatedTime: BasicTime.GMT, wDir: ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; localFullFName: ROPE; cp: FS.ComponentPositions; dirOmitted: BOOL; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [fullFName: localFullFName, cp: cp, dirOmitted: dirOmitted] _ FS.ExpandName[name: name, wDir: wDir]; IF Rope.Equal[Rope.Substr[base: localFullFName, start: cp.server.start, len: cp.server.length], "SummonerServer"] THEN { IF ComputeServerInternal.OKToUseLocalDisk THEN { localName: ROPE; savedError: FS.ErrorDesc; localOpenOK: BOOL _ TRUE; localName _ Rope.Concat["[]<", Rope.Substr[localFullFName, cp.dir.start]]; fsOverride[psb] _ TRUE; FS.Delete[localName, wantedCreatedTime ! FS.Error => { localOpenOK _ FALSE; savedError _ error; CONTINUE; } ]; fsOverride[psb] _ FALSE; IF localOpenOK THEN { RETURN[]; } ELSE ERROR FS.Error[savedError]; } ELSE { ERROR FS.Error[[ environment, $SeverMachineWillNotAllowUseOfLocalDisk, Rope.Cat["Attempt to open a file on logical server 'SummonerServer' for file name ", localFullFName, "while the Server was not setup to allow access to it's local file system"]]]; }; }; [] _ interface.rDelete[serviceItem.listenerPupAddress, name, wantedCreatedTime, wDir]; }; }; myRename: PROC [from, to: Rope.ROPE, setKeep: BOOLEAN, keep: CARDINAL, wantedCreatedTime: BasicTime.GMT, wDir: Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [] _ interface.rRename[serviceItem.listenerPupAddress, from, to, setKeep, keep, wantedCreatedTime, wDir]; }; }; mySetKeep: PROC [name: Rope.ROPE, keep: CARDINAL, wDir: Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF wDir = NIL THEN wDir _ NARROW [ ProcessProps.GetProp[$WorkingDirectory] ]; [] _ interface.rSetKeep[serviceItem.listenerPupAddress, name, keep, wDir]; }; }; <> testAndSetDoingEnumerate: ENTRY PROC[serviceItem: ComputeServerInternal.ActiveServicesItem] RETURNS [ok: BOOL] = TRUSTED { IF serviceItem.doingEnumerate THEN RETURN[FALSE]; serviceItem.doingEnumerate _ TRUE; RETURN[ TRUE]; }; clearDoingEnumerate: ENTRY PROC[serviceItem: ComputeServerInternal.ActiveServicesItem] = TRUSTED { serviceItem.doingEnumerate _ FALSE; }; <> getClassProc: PROC [clientFile: REF] RETURNS [ATOM _ $NIL] = { myFile: localOpenFile _ NARROW[clientFile]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile.interface, firstCall, myFile.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile.interface _ interface; myFile.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile.remoteFile THEN { IF myFile.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; RETURN[myFile.interface.rGetClass[myFile.serviceItem.listenerPupAddress, myFile.remoteFileID]]; } ELSE { RETURN[FS.GetClass[myFile.localFile]]; }; }; }; sameFileProc: PROC [clientFile1, clientFile2: REF] RETURNS [BOOLEAN _ FALSE] = { myFile1: localOpenFile _ NARROW[clientFile1]; myFile2: localOpenFile _ NARROW[clientFile2]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile1.interface, firstCall, myFile1.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile1.interface _ interface; myFile1.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile1.remoteFile ~= myFile2.remoteFile THEN RETURN [FALSE]; IF myFile1.remoteFile THEN { IF myFile1.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; RETURN[myFile1.interface.rSameFile[myFile1.serviceItem.listenerPupAddress, myFile1.remoteFileID, myFile2.remoteFileID]]; } ELSE { RETURN[FS.SameFile[myFile1.localFile, myFile2.localFile]] }; }; }; getNameProc: PROC [clientFile: REF] RETURNS [fullFName, attachedTo: Rope.ROPE] = { myFile: localOpenFile _ NARROW[clientFile]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile.interface, firstCall, myFile.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile.interface _ interface; myFile.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile.remoteFile THEN { IF myFile.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; [fullFName, attachedTo] _ myFile.interface.rGetName[ myFile.serviceItem.listenerPupAddress, myFile.remoteFileID]; } ELSE { [fullFName, attachedTo] _ FS.GetName[myFile.localFile]; }; }; }; getInfoProc: PROC [clientFile: REF] RETURNS [keep: CARDINAL, pages, bytes: INT, created: BasicTime.GMT, lock: FS.Lock] = { myFile: localOpenFile _ NARROW[clientFile]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile.interface, firstCall, myFile.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile.interface _ interface; myFile.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile.remoteFile THEN { IF myFile.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; [keep, pages, bytes, created, lock] _ myFile.interface.rGetInfo[ myFile.serviceItem.listenerPupAddress, myFile.remoteFileID]; } ELSE { [keep, pages, bytes, created, lock] _ FS.GetInfo[myFile.localFile]; }; }; }; setPageCountProc: PROC [clientFile: REF, pages: INT] = { myFile: localOpenFile _ NARROW[clientFile]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile.interface, firstCall, myFile.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile.interface _ interface; myFile.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile.remoteFile THEN { IF myFile.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; myFile.interface.rSetPageCount[myFile.serviceItem.listenerPupAddress, myFile.remoteFileID, pages]; } ELSE { FS.SetPageCount[myFile.localFile, pages]; }; }; }; setByteCountAndCreatedTimeProc: PROC [clientFile: REF, bytes: INT, created: BasicTime.GMT] = { myFile: localOpenFile _ NARROW[clientFile]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile.interface, firstCall, myFile.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile.interface _ interface; myFile.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile.remoteFile THEN { IF myFile.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; myFile.interface.rSetByteCountAndCreatedTime[myFile.serviceItem.listenerPupAddress, myFile.remoteFileID, bytes, created]; } ELSE { FS.SetByteCountAndCreatedTime[myFile.localFile, bytes, created]; }; }; }; readProc: UNSAFE PROC [clientFile: REF, from, nPages: INT, to: LONG POINTER] = { myFile: localOpenFile _ NARROW[clientFile]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile.interface, firstCall, myFile.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile.interface _ interface; myFile.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile.remoteFile THEN { pageBuffer: ComputeServerCallbacks.RESULTPageBuffer ; IF myFile.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; TRUSTED {pageBuffer _ DESCRIPTOR[to, nPages*File.wordsPerPage]; }; myFile.interface.rRead[myFile.serviceItem.listenerPupAddress, myFile.remoteFileID, from, nPages, pageBuffer]; } ELSE TRUSTED { FS.Read[myFile.localFile, from, nPages, to]; }; }; }; writeProc: PROC [clientFile: REF, to: INT, nPages: INT, from: LONG POINTER] = { myFile: localOpenFile _ NARROW[clientFile]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile.interface, firstCall, myFile.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile.interface _ interface; myFile.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile.remoteFile THEN { pageBuffer: ComputeServerCallbacks.VALUEPageBuffer ; IF myFile.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; TRUSTED {pageBuffer _ DESCRIPTOR[from, nPages*File.wordsPerPage]; }; myFile.interface.rWrite[myFile.serviceItem.listenerPupAddress, myFile.remoteFileID, to, nPages, pageBuffer]; } ELSE { ERROR FS.Error[ [bug, $CannotWriteToServerDisk, "Writing onto the compute servers local file system is illegal"]]; }; }; }; closeProc: PROC [clientFile: REF] = { myFile: localOpenFile _ NARROW[clientFile]; firstCall: BOOL _ TRUE; { ENABLE { ComputeServerCallbacks.Error => ERROR FS.Error[error]; RPC.CallFailed => { interface: ComputeServerCallbacksRpcControl.InterfaceRecord; interface _ TryRPCRecovery[myFile.interface, firstCall, myFile.serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN { myFile.interface _ interface; myFile.serviceItem.callbacksInterface _ interface; RETRY; }; ERROR FS.Error[ [environment, $serverInaccessible ,"remote rpc call failed"]]; }; }; IF myFile.remoteFile THEN { IF myFile.serviceItem.callOver THEN ERROR FS.Error[ [bug, $remoteRequestFinished ,"compute server remote file operation attempted after the end of the request"]]; myFile.interface.rClose[myFile.serviceItem.listenerPupAddress, myFile.remoteFileID ! ComputeServerCallbacks.Error => {ERROR FS.Error[error]; }]; } ELSE TRUSTED { FS.Close[myFile.localFile]; }; }; }; <> IsGuestProcess: PUBLIC PROC [] RETURNS [isGuest: BOOL] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; RETURN [~allOverride[psb] AND stateArray[psb] # NIL] ; }; <> GetState: PROC RETURNS [UserCredentials.State] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; }; }; RETURN[interface.rGetState[serviceItem.listenerPupAddress]]; }; }; ChangeState: PROC [new: UserCredentials.State] RETURNS [old: UserCredentials.State] = { ERROR; }; Login: PROC [startInteraction: PROC RETURNS [in, out: IO.STREAM], endInteraction: PROC [in, out: IO.STREAM], options: UserCredentials.LoginOptions _ UserCredentials.defaultOptions] = { ERROR; }; Get: PROC RETURNS [name, password: Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; }; }; [name, password] _ interface.rGet[serviceItem.listenerPupAddress]; }; }; <> <<>> Boolean: PROC [key: Rope.ROPE, default: BOOLEAN _ FALSE] RETURNS [value: BOOLEAN] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; }; }; RETURN[interface.rBoolean[serviceItem.listenerPupAddress, key, default]]; }; }; Number: PROC [key: Rope.ROPE, default: INT _ 0] RETURNS [value: INT] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; }; }; RETURN[interface.rNumber[serviceItem.listenerPupAddress, key, default]]; }; }; Token: PROC [key: Rope.ROPE, default: Rope.ROPE _ NIL] RETURNS [value: Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; }; }; RETURN[interface.rToken[serviceItem.listenerPupAddress, key, default]]; }; }; ListOfTokens: PROC [key: Rope.ROPE, default: LIST OF Rope.ROPE _ NIL] RETURNS [value: LIST OF Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; }; }; RETURN[interface.rListOfTokens[serviceItem.listenerPupAddress, key, default]]; }; }; Line: PROC [key: Rope.ROPE, default: Rope.ROPE _ NIL] RETURNS [value: Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; }; }; RETURN[interface.rLine[serviceItem.listenerPupAddress, key, default]]; }; }; GetProfileName: PROC RETURNS [Rope.ROPE] = TRUSTED { psb: PrincOps.PsbIndex = PrincOpsUtils.PsbHandleToIndex[PrincOpsUtils.ReadPSB[]]; serviceItem: ComputeServerInternal.ActiveServicesItem = LOOPHOLE[stateArray[psb]]; interface: ComputeServerCallbacksRpcControl.InterfaceRecord _ serviceItem.callbacksInterface; firstCall: BOOL _ TRUE; { ENABLE { RPC.CallFailed => { interface _ TryRPCRecovery[serviceItem.callbacksInterface, firstCall, serviceItem.clientNetAddressRope]; firstCall _ FALSE; IF interface # NIL THEN {serviceItem.callbacksInterface _ interface; RETRY;}; }; }; RETURN[interface.rGetProfileName[serviceItem.listenerPupAddress]]; }; }; CallWhenProfileChanges: PROC [ proc: UserProfile.ProfileChangedProc ] = { ERROR; }; ProfileChanged: PROC [reason: UserProfile.ProfileChangeReason] = { ERROR; }; <> TryRPCRecovery: PROC [oldInterface: ComputeServerCallbacksRpcControl.InterfaceRecord, firstCall: BOOL, clientNetAddressRope: ROPE] RETURNS [newInterface: ComputeServerCallbacksRpcControl.InterfaceRecord _ NIL] = { IF firstCall THEN { newInterface _ ComputeServerInternal.GetClientInterfaceFromCache[clientNetAddressRope, TRUE]; } ELSE { [] _ ComputeServerInternal.DeleteClientInterfaceFromCache[oldInterface]; }; }; <> newFSProcs: REF FSBackdoor.GuestProcsRec _ NEW[FSBackdoor.GuestProcsRec _ [ IsGuestProcess: myFSIsGuestProcess, SetDefaultWDir: mySetDefaultWDir, GetDefaultWDir: myGetDefaultWDir, ExpandName: myExpandName, FileInfo: myFileInfo, EnumerateForInfo: myEnumerateForInfo , EnumerateForNames: myEnumerateForNames, Open: myOpen, Create: myCreate, Copy: myCopy, Delete: myDelete, Rename: myRename, SetKeep: mySetKeep ]]; newCredentialsProcs: REF UserCredentialsBackdoor.GuestProcsRec _ NEW[UserCredentialsBackdoor.GuestProcsRec _ [ IsGuestProcess: IsGuestProcess, GetState: GetState, ChangeState: ChangeState, Login: Login, Get: Get ]]; newProfileProcs: REF UserProfileBackdoor.GuestProcsRec _ NEW[UserProfileBackdoor.GuestProcsRec _ [ IsGuestProcess: IsGuestProcess, Boolean: Boolean, Number: Number, Token: Token, ListOfTokens: ListOfTokens, Line: Line, GetProfileName: GetProfileName, CallWhenProfileChanges: CallWhenProfileChanges, ProfileChanged: ProfileChanged ]]; <> TRUSTED { size: NAT = PrincOps.StartPsb + PrincOps.PDA.count; stateArray _ UnsafeStorage.GetSystemUZone[].NEW[StateArrayRec[size]]; fsOverride _ UnsafeStorage.GetSystemUZone[].NEW[OverrideArrayRec[size]]; allOverride _ UnsafeStorage.GetSystemUZone[].NEW[OverrideArrayRec[size]]; FOR i:NAT IN [0..size) DO stateArray[i] _ NIL; fsOverride[i] _ FALSE; allOverride[i] _ FALSE; ENDLOOP; }; Loader.MakeProcedureResident[myFork]; Loader.MakeProcedureResident[myDetatch]; Loader.MakeGlobalFrameResident[myFork]; [] _ ProcessBackdoor.RegisterEventProcs[forkProc: myFork, joinProc: myJoin, endProc: myEnd, detachProc: myDetatch]; <> FSBackdoor.RegisterGuestProcs[newFSProcs]; UserCredentialsBackdoor.RegisterGuestProcs[newCredentialsProcs]; UserProfileBackdoor.RegisterGuestProcs[newProfileProcs]; END. << >> <> <> <<>> <> <> <<>> <<>> <> <> <> <> <> <> <> <> <> <> <<>> <> <> <> <> <> <> <<>> <> <> <> <> <<>> <> <> <> <> <<>> <<>> <> <> <<>>