00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031 #ifndef __OPAL_H323TRANS_H
00032 #define __OPAL_H323TRANS_H
00033
00034 #ifdef P_USE_PRAGMA
00035 #pragma interface
00036 #endif
00037
00038 #include <h323/transaddr.h>
00039 #include <h323/h235auth.h>
00040
00041 #include <ptclib/asner.h>
00042
00043
00044 class H323EndPoint;
00045
00046
00047 class H323TransactionPDU {
00048 public:
00049 H323TransactionPDU();
00050 H323TransactionPDU(const H235Authenticators & auth);
00051
00052 virtual ~H323TransactionPDU() { }
00053
00054 virtual PBoolean Read(H323Transport & transport);
00055 virtual PBoolean Write(H323Transport & transport);
00056
00057 virtual PASN_Object & GetPDU() = 0;
00058 virtual PASN_Choice & GetChoice() = 0;
00059 virtual const PASN_Object & GetPDU() const = 0;
00060 virtual const PASN_Choice & GetChoice() const = 0;
00061 virtual unsigned GetSequenceNumber() const = 0;
00062 virtual unsigned GetRequestInProgressDelay() const = 0;
00063 #if PTRACING
00064 virtual const char * GetProtocolName() const = 0;
00065 #endif
00066 virtual H323TransactionPDU * ClonePDU() const = 0;
00067 virtual void DeletePDU() = 0;
00068
00069 const H235Authenticators & GetAuthenticators() const { return authenticators; }
00070 H235Authenticators & GetAuthenticators() { return authenticators; }
00071 void SetAuthenticators(
00072 const H235Authenticators & auth
00073 ) { authenticators = auth; }
00074
00075 H235Authenticator::ValidationResult Validate(
00076 const PASN_Array & clearTokens,
00077 unsigned clearOptionalField,
00078 const PASN_Array & cryptoTokens,
00079 unsigned cryptoOptionalField
00080 ) const { return authenticators.ValidatePDU(*this, clearTokens, clearOptionalField, cryptoTokens, cryptoOptionalField, rawPDU); }
00081
00082 void Prepare(
00083 PASN_Array & clearTokens,
00084 unsigned clearOptionalField,
00085 PASN_Array & cryptoTokens,
00086 unsigned cryptoOptionalField
00087 ) { authenticators.PreparePDU(*this, clearTokens, clearOptionalField, cryptoTokens, cryptoOptionalField); }
00088
00089 protected:
00090 mutable H235Authenticators authenticators;
00091 PPER_Stream rawPDU;
00092 };
00093
00094
00096
00097 class H323Transactor : public PObject
00098 {
00099 PCLASSINFO(H323Transactor, PObject);
00100 public:
00103
00106 H323Transactor(
00107 H323EndPoint & endpoint,
00108 H323Transport * transport,
00109 WORD localPort,
00110 WORD remotePort
00111 );
00112 H323Transactor(
00113 H323EndPoint & endpoint,
00114 const H323TransportAddress & iface,
00115 WORD localPort,
00116 WORD remotePort
00117 );
00118
00121 ~H323Transactor();
00123
00128 void PrintOn(
00129 ostream & strm
00130 ) const;
00132
00137 PBoolean SetTransport(
00138 const H323TransportAddress & iface
00139 );
00140
00143 H323TransportAddressArray GetInterfaceAddresses(
00144 PBoolean excludeLocalHost = PTrue,
00145 H323Transport * associatedTransport = NULL
00147 );
00148
00151 virtual PBoolean StartChannel();
00152
00156 virtual void StopChannel();
00157
00160 virtual H323TransactionPDU * CreateTransactionPDU() const = 0;
00161
00164 virtual PBoolean HandleTransaction(
00165 const PASN_Object & rawPDU
00166 ) = 0;
00167
00170 virtual void OnSendingPDU(
00171 PASN_Object & rawPDU
00172 ) = 0;
00173
00176 virtual PBoolean WritePDU(
00177 H323TransactionPDU & pdu
00178 );
00179
00182 virtual PBoolean WriteTo(
00183 H323TransactionPDU & pdu,
00184 const H323TransportAddressArray & addresses,
00185 PBoolean callback = PTrue
00186 );
00188
00193 H323EndPoint & GetEndPoint() const { return endpoint; }
00194
00197 H323Transport & GetTransport() const { return *transport; }
00198
00201 void SetCheckResponseCryptoTokens(
00202 PBoolean value
00203 ) { checkResponseCryptoTokens = value; }
00204
00207 PBoolean GetCheckResponseCryptoTokens() { return checkResponseCryptoTokens; }
00209
00210 protected:
00211 void Construct();
00212
00213 unsigned GetNextSequenceNumber();
00214 PBoolean SetUpCallSignalAddresses(
00215 H225_ArrayOf_TransportAddress & addresses
00216 );
00217
00218
00219 PDECLARE_NOTIFIER(PThread, H323Transactor, HandleTransactions);
00220
00221 class Request : public PObject
00222 {
00223 PCLASSINFO(Request, PObject);
00224 public:
00225 Request(
00226 unsigned seqNum,
00227 H323TransactionPDU & pdu
00228 );
00229 Request(
00230 unsigned seqNum,
00231 H323TransactionPDU & pdu,
00232 const H323TransportAddressArray & addresses
00233 );
00234
00235 PBoolean Poll(H323Transactor &);
00236 void CheckResponse(unsigned, const PASN_Choice *);
00237 void OnReceiveRIP(unsigned milliseconds);
00238
00239
00240 unsigned rejectReason;
00241 void * responseInfo;
00242
00243 H323TransportAddressArray requestAddresses;
00244
00245 unsigned sequenceNumber;
00246 H323TransactionPDU & requestPDU;
00247 PTimeInterval whenResponseExpected;
00248 PSyncPoint responseHandled;
00249 PMutex responseMutex;
00250
00251 enum {
00252 AwaitingResponse,
00253 ConfirmReceived,
00254 RejectReceived,
00255 TryAlternate,
00256 BadCryptoTokens,
00257 RequestInProgress,
00258 NoResponseReceived
00259 } responseResult;
00260 };
00261
00262 virtual PBoolean MakeRequest(
00263 Request & request
00264 );
00265 PBoolean CheckForResponse(
00266 unsigned,
00267 unsigned,
00268 const PASN_Choice * = NULL
00269 );
00270 PBoolean HandleRequestInProgress(
00271 const H323TransactionPDU & pdu,
00272 unsigned delay
00273 );
00274 PBoolean CheckCryptoTokens(
00275 const H323TransactionPDU & pdu,
00276 const PASN_Array & clearTokens,
00277 unsigned clearOptionalField,
00278 const PASN_Array & cryptoTokens,
00279 unsigned cryptoOptionalField
00280 );
00281
00282 void AgeResponses();
00283 PBoolean SendCachedResponse(
00284 const H323TransactionPDU & pdu
00285 );
00286
00287 class Response : public PString
00288 {
00289 PCLASSINFO(Response, PString);
00290 public:
00291 Response(const H323TransportAddress & addr, unsigned seqNum);
00292 ~Response();
00293
00294 void SetPDU(const H323TransactionPDU & pdu);
00295 PBoolean SendCachedResponse(H323Transport & transport);
00296
00297 PTime lastUsedTime;
00298 PTimeInterval retirementAge;
00299 H323TransactionPDU * replyPDU;
00300 };
00301
00302
00303 H323EndPoint & endpoint;
00304 WORD defaultLocalPort;
00305 WORD defaultRemotePort;
00306 H323Transport * transport;
00307 PBoolean checkResponseCryptoTokens;
00308
00309 unsigned nextSequenceNumber;
00310 PMutex nextSequenceNumberMutex;
00311
00312 PDictionary<POrdinalKey, Request> requests;
00313 PMutex requestsMutex;
00314 Request * lastRequest;
00315
00316 PMutex pduWriteMutex;
00317 PSortedList<Response> responses;
00318 };
00319
00320
00322
00323 class H323Transaction : public PObject
00324 {
00325 PCLASSINFO(H323Transaction, PObject);
00326 public:
00331 H323Transaction(
00332 H323Transactor & transactor,
00333 const H323TransactionPDU & requestToCopy,
00334 H323TransactionPDU * confirm,
00335 H323TransactionPDU * reject
00336 );
00337 ~H323Transaction();
00339
00340 enum Response {
00341 Ignore = -2,
00342 Reject = -1,
00343 Confirm = 0
00344 };
00345 inline static Response InProgress(unsigned time) { return (Response)(time&0xffff); }
00346
00347 virtual H323TransactionPDU * CreateRIP(
00348 unsigned sequenceNumber,
00349 unsigned delay
00350 ) const = 0;
00351
00352 PBoolean HandlePDU();
00353
00354 virtual PBoolean WritePDU(
00355 H323TransactionPDU & pdu
00356 );
00357
00358 PBoolean CheckCryptoTokens(
00359 const H235Authenticators & authenticators
00360 );
00361
00362 #if PTRACING
00363 virtual const char * GetName() const = 0;
00364 #endif
00365 virtual H235Authenticator::ValidationResult ValidatePDU() const = 0;
00366 virtual void SetRejectReason(
00367 unsigned reasonCode
00368 ) = 0;
00369
00370 PBoolean IsFastResponseRequired() const { return fastResponseRequired && canSendRIP; }
00371 PBoolean CanSendRIP() const { return canSendRIP; }
00372 H323TransportAddress GetReplyAddress() const { return replyAddresses[0]; }
00373 const H323TransportAddressArray & GetReplyAddresses() const { return replyAddresses; }
00374 PBoolean IsBehindNAT() const { return isBehindNAT; }
00375 H323Transactor & GetTransactor() const { return transactor; }
00376 H235Authenticator::ValidationResult GetAuthenticatorResult() const { return authenticatorResult; }
00377
00378 protected:
00379 virtual Response OnHandlePDU() = 0;
00380 PDECLARE_NOTIFIER(PThread, H323Transaction, SlowHandler);
00381
00382 H323Transactor & transactor;
00383 unsigned requestSequenceNumber;
00384 H323TransportAddressArray replyAddresses;
00385 PBoolean fastResponseRequired;
00386 H323TransactionPDU * request;
00387 H323TransactionPDU * confirm;
00388 H323TransactionPDU * reject;
00389
00390 H235Authenticators authenticators;
00391 H235Authenticator::ValidationResult authenticatorResult;
00392 PBoolean isBehindNAT;
00393 PBoolean canSendRIP;
00394 };
00395
00396
00398
00399 class H323TransactionServer : public PObject
00400 {
00401 PCLASSINFO(H323TransactionServer, PObject);
00402 public:
00407 H323TransactionServer(
00408 H323EndPoint & endpoint
00409 );
00410
00413 ~H323TransactionServer();
00415
00416 virtual WORD GetDefaultUdpPort() = 0;
00417
00422 H323EndPoint & GetOwnerEndPoint() const { return ownerEndPoint; }
00423
00437 PBoolean AddListeners(
00438 const H323TransportAddressArray & ifaces
00439 );
00440
00444 PBoolean AddListener(
00445 const H323TransportAddress & interfaceName
00446 );
00447
00454 PBoolean AddListener(
00455 H323Transport * transport
00456 );
00457
00464 PBoolean AddListener(
00465 H323Transactor * listener
00466 );
00467
00476 virtual H323Transactor * CreateListener(
00477 H323Transport * transport
00478 ) = 0;
00479
00483 PBoolean RemoveListener(
00484 H323Transactor * listener
00485 );
00486
00487 PBoolean SetUpCallSignalAddresses(H225_ArrayOf_TransportAddress & addresses);
00489
00490 protected:
00491 H323EndPoint & ownerEndPoint;
00492
00493 PThread * monitorThread;
00494 PSyncPoint monitorExit;
00495
00496 PMutex mutex;
00497 PLIST(ListenerList, H323Transactor);
00498 ListenerList listeners;
00499 };
00500
00501
00502 #endif // __OPAL_H323TRANS_H
00503
00504