<> <> <> DIRECTORY BasicTime USING [ GMT --, nullGMT-- ], DESFace USING [ Key, nullKey ], GVBasics USING [ Password ], Lark USING [ ConnectionSpec, KeyTable, Machine, noMachine, VoiceSocket ], RPC USING [ Conversation, ShortROPE, unencrypted ], SafeStorage USING [ Type, unspecType ], Triples USING [ Any, Item ] ; Thrush: CEDAR DEFINITIONS = { <> PartyHandle: TYPE = ThHandle; ConversationHandle: TYPE = Epoch; nullConvHandle: ConversationHandle = LOOPHOLE[LONG[0]]; SmartsHandle: TYPE = ThHandle; <> VoiceSocket: TYPE = Lark.VoiceSocket; Machine: TYPE = Lark.Machine; noMachine: Machine = Lark.noMachine; Epoch: TYPE = BasicTime.GMT; epoch: Epoch; -- things with this epoch in them were created during this incarnation ROPE: TYPE = RPC.ShortROPE; Rname: TYPE = ROPE; Password: TYPE = GVBasics.Password; nullPassword: Password = ALL[0]; NetAddress: TYPE = Machine; TBD: TYPE=CARDINAL; -- <> Time: TYPE = BasicTime.GMT; Priorities: TYPE = LIST OF REF ANY; pERROR: -- PROGRAMMING -- ERROR; ServerError: ERROR[code: ServerProblem_unknown]; ServerProblem: TYPE = { unknown, inconsistentStructures, hiLevFault }; <> <> StateInConv: TYPE = { idle, -- Not really in the conversation (ever, or any more.) reserved, -- TBD at party level; restrict some operations pending outgoing conn. parsing, -- TBD at party level; may restrict additional operations. <> initiating, -- You are the calling party; attempt to contact the other party is in underway. pending, -- You are the called party; you are deciding whether to bother your user. maybe, -- You are the calling party; an attempt to arouse the other user is in progress. ringing, -- You are the called party; you are attempting to arouse your user. canActivate, -- You may become active in this conversation whenever you can get out of the one you may already be active in. active, -- You are active in this conversation. inactive, -- You have put this conversation on "hold." any -- Used in queries only }; <Party interactions.>> StateID: TYPE = NAT; <Party informational packet.>> Credentials: TYPE = RECORD [ partyID: PartyHandle, smartsID: SmartsHandle, convID: ConversationHandle_nullConvHandle, stateID: StateID_0 ]; <<>> <> ConvEvent: TYPE = REF ConvEventBody; ConvEventBody: TYPE = RECORD [ credentials: Credentials, -- of the initiator of the event; smartsID may be null state: StateInConv _ idle, -- the state of this party in this conversation. reason: Reason _ wontSay, -- for rejection, acceptance, or conditional acceptance urgency: CallUrgency_normal, -- urgency supplied in connection attempt during this event. alertKind: AlertKind _ standard, -- connection type hint spec: Lark.ConnectionSpec _ NIL, -- if StatInConv is active or canActivate. keyTable: Lark.KeyTable _ NIL, -- whenever there's a spec intervalSpec: IntervalSpec _ NIL, -- if non-NIL, a SetInterval is being specified. address: ROPE_NIL, -- calling trunks and the like: external addressing information. time: Time _ NULL, comment: ROPE _ NIL -- any human-sensible comment associated with the event. ]; EventSequence: TYPE = REF EventSequenceBody; EventSequenceBody: TYPE = RECORD [ s: SEQUENCE size: NAT OF ConvEvent ]; Reason: TYPE = { <<(Why things happened)>> wontSay, -- no reason needed. <> terminating, -- there was a reason for this connection, but it's over now, by me. withdrawing, -- would like to leave, with right to return. noAnswer, -- Alert only: we tried, honest. <> notFound, -- called party not found busy, -- called party is active in another conversation and/or doesn't wish to accept this one. absent, -- called party is known to be unavailable for extended period notImportantEnough, -- connection rejected because claimed urgency was too low. noCircuits, -- call rejected due to system resource overload noParticular, -- rejected for good reason, but can't say what it is. error -- System problem caused rejection. -- }; <Party calls>> NB: TYPE = { success, -- call succeeded, party may be in new state. stateMismatch, -- the most common problem; your information's out of date. invalidTransition, -- you can't go from the state you're in to the one you're requesting. notInConv, -- you're not a party to this conversation, and call requires it. noSuchConv, -- named conversation doesn't exist. noSuchParty, -- named (own) party doesn't exist. partyNotEnabled, -- named (own) party does not have a voice path yet. noSuchSmarts, -- get the drift? noSuchParty2, -- second named (called) party doesn't exist. narcissism, -- attempt to connect to self rejected <> convNotActive, -- activity requested that is only satisfiable if requesting party active convStillActive -- can't destroy it if remaining connections are not orphans. }; <Smarts calls to control "distribution".>> Disposition: TYPE = {actedAndStop, actedAndPass--<>--, pass, willAlwaysPassThisRequest}; <> <> <> <> <> <> <> CallUrgency: TYPE= {junk, ifConvenient, normal, important, urgent, fire}; AlertKind: TYPE = { queryOnly, standard, intercom, whoKnows }; <> <> <> <> <> <<>> <> <<>> NumberClass: TYPE = {public, intelnet}; PartyType: TYPE = {individual, trunk, recording}; PhoneNumber: TYPE = --.--ROPE--REF PhoneNumberBody--; -- rope for now PhoneNumberBody: TYPE = RECORD [ extension: ROPE, office: ROPE, region: SELECT numberClass: NumberClass FROM public => [ area: ROPE ], intelnet => NULL, ENDCASE ]; <> Tune: TYPE = INT; -- the index of a "tune" or similar utterance identification. nullTune: Tune = -1; newTune: Tune = -2; VoiceTime: TYPE = INT; -- A sample number or sample count. VoiceInterval: TYPE = RECORD [ start: VoiceTime_0, -- first sample within tune to play or record. length: VoiceTime_-1 -- number of samples: -1 to play to the end. -- ]; VoiceDirection: TYPE = { play, record }; IntSpecType: TYPE = { request, started, finished }; IntervalSpec: TYPE = REF IntervalSpecBody; IntervalSpecBody: TYPE = RECORD [ tune: Tune_newTune, interval: VoiceInterval_[], keyIndex: [0..17B] _ 0, type: IntSpecType _ request, direction: VoiceDirection, intID: StateID _ 0, queueIt: BOOLEAN _ TRUE ]; <> <> <> <> <> ThHandle: TYPE=LONG CARDINAL; <> Enhandle: PROC[r: REF] RETURNS [ThHandle]; -- handle valid until killed. <> <<>> Rehandle, H: PROC[r: REF] RETURNS [ThHandle] = INLINE { RETURN[LOOPHOLE[r]]; }; <> <<>> Dehandle: PROC[h: ThHandle, type: SafeStorage.Type_SafeStorage.unspecType, insist: BOOLEAN_FALSE] RETURNS [LONG UNSPECIFIED]; <> <> KillHandle: PROC[h: ThHandle, type: SafeStorage.Type_SafeStorage.unspecType]; <> <<>> nullHandle: ThHandle = LOOPHOLE[NIL[REF], LONG CARDINAL]; HandleFault: ERROR[h: ThHandle]; <> MakeUnique: PROC[att, obj, val: Triples.Item _ Triples.Any]; <> SHHH: TYPE = RPC.Conversation; unencrypted, none: SHHH = RPC.unencrypted; EncryptionKey: TYPE = DESFace.Key; nullKey: EncryptionKey = DESFace.nullKey; }.