OpenH323 1.18.0
|
00001 /* 00002 * h323trans.h 00003 * 00004 * H.323 Transactor handler 00005 * 00006 * Open H323 Library 00007 * 00008 * Copyright (c) 2003 Equivalence Pty. Ltd. 00009 * 00010 * The contents of this file are subject to the Mozilla Public License 00011 * Version 1.0 (the "License"); you may not use this file except in 00012 * compliance with the License. You may obtain a copy of the License at 00013 * http://www.mozilla.org/MPL/ 00014 * 00015 * Software distributed under the License is distributed on an "AS IS" 00016 * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See 00017 * the License for the specific language governing rights and limitations 00018 * under the License. 00019 * 00020 * The Original Code is Open H323 Library. 00021 * 00022 * The Initial Developer of the Original Code is Equivalence Pty. Ltd. 00023 * 00024 * Contributor(s): ______________________________________. 00025 * 00026 * $Log: h323trans.h,v $ 00027 * Revision 1.17 2005/11/30 13:05:01 csoutheren 00028 * Changed tags for Doxygen 00029 * 00030 * Revision 1.16 2004/08/24 08:11:24 csoutheren 00031 * Added initial support for receiving broadcasts on Linux 00032 * 00033 * Revision 1.15 2003/12/11 05:39:04 csoutheren 00034 * Added storage of H.225 version in endpoint structure 00035 * Disabled sending RIPs to endpoints that cannot handle them 00036 * 00037 * Revision 1.14 2003/04/30 07:50:58 robertj 00038 * Redesigned the alternate credentials in ARQ system as old implementation 00039 * was fraught with concurrency issues, most importantly it can cause false 00040 * detection of replay attacks taking out an endpoint completely. 00041 * 00042 * Revision 1.13 2003/04/10 09:40:05 robertj 00043 * Added associated transport to new GetInterfaceAddresses() function so 00044 * interfaces can be ordered according to active transport links. Improves 00045 * interoperability. 00046 * 00047 * Revision 1.12 2003/04/10 01:03:58 craigs 00048 * Added functions to access to lists of interfaces 00049 * 00050 * Revision 1.11 2003/04/09 03:08:06 robertj 00051 * Fixed race condition in shutting down transactor (pure virtual call) 00052 * 00053 * Revision 1.10 2003/04/01 05:59:30 robertj 00054 * Fixed H.501 transaction code setting members for m_common PDU part. 00055 * 00056 * Revision 1.9 2003/04/01 04:47:48 robertj 00057 * Abstracted H.225 RAS transaction processing (RIP and secondary thread) in 00058 * server environment for use by H.501 peer elements. 00059 * 00060 * Revision 1.8 2003/03/26 00:46:25 robertj 00061 * Had another go at making H323Transactor being able to be created 00062 * without having a listener running. 00063 * 00064 * Revision 1.7 2003/03/25 04:56:17 robertj 00065 * Fixed issues to do with multiple inheritence in transaction reply cache. 00066 * 00067 * Revision 1.6 2003/03/21 05:26:45 robertj 00068 * Added setting of remote port in UDP transport constructor. 00069 * 00070 * Revision 1.5 2003/03/20 01:51:07 robertj 00071 * More abstraction of H.225 RAS and H.501 protocols transaction handling. 00072 * 00073 * Revision 1.4 2003/03/01 00:23:42 craigs 00074 * New PeerElement implementation 00075 * 00076 * Revision 1.3 2003/02/25 06:48:15 robertj 00077 * More work on PDU transaction abstraction. 00078 * 00079 * Revision 1.2 2003/02/25 03:14:58 robertj 00080 * Added missing virtual destructor. 00081 * 00082 * Revision 1.1 2003/02/21 05:28:39 craigs 00083 * Factored out code for user with peer elements 00084 * 00085 */ 00086 00087 #ifndef __OPAL_H323TRANS_H 00088 #define __OPAL_H323TRANS_H 00089 00090 #ifdef P_USE_PRAGMA 00091 #pragma interface 00092 #endif 00093 00094 #include "transports.h" 00095 #include "h235auth.h" 00096 00097 #include <ptclib/asner.h> 00098 00099 00100 class H323TransactionPDU { 00101 public: 00102 H323TransactionPDU(); 00103 H323TransactionPDU(const H235Authenticators & auth); 00104 00105 virtual ~H323TransactionPDU() { } 00106 00107 virtual BOOL Read(H323Transport & transport); 00108 virtual BOOL Write(H323Transport & transport); 00109 00110 virtual PASN_Object & GetPDU() = 0; 00111 virtual PASN_Choice & GetChoice() = 0; 00112 virtual const PASN_Object & GetPDU() const = 0; 00113 virtual const PASN_Choice & GetChoice() const = 0; 00114 virtual unsigned GetSequenceNumber() const = 0; 00115 virtual unsigned GetRequestInProgressDelay() const = 0; 00116 #if PTRACING 00117 virtual const char * GetProtocolName() const = 0; 00118 #endif 00119 virtual H323TransactionPDU * ClonePDU() const = 0; 00120 virtual void DeletePDU() = 0; 00121 00122 const H235Authenticators & GetAuthenticators() const { return authenticators; } 00123 void SetAuthenticators( 00124 const H235Authenticators & auth 00125 ) { authenticators = auth; } 00126 00127 H235Authenticator::ValidationResult Validate( 00128 const PASN_Array & clearTokens, 00129 unsigned clearOptionalField, 00130 const PASN_Array & cryptoTokens, 00131 unsigned cryptoOptionalField 00132 ) const { return authenticators.ValidatePDU(*this, clearTokens, clearOptionalField, cryptoTokens, cryptoOptionalField, rawPDU); } 00133 00134 void Prepare( 00135 PASN_Array & clearTokens, 00136 unsigned clearOptionalField, 00137 PASN_Array & cryptoTokens, 00138 unsigned cryptoOptionalField 00139 ) { authenticators.PreparePDU(*this, clearTokens, clearOptionalField, cryptoTokens, cryptoOptionalField); } 00140 00141 protected: 00142 H235Authenticators authenticators; 00143 PPER_Stream rawPDU; 00144 }; 00145 00146 00148 00149 class H323Transactor : public PObject 00150 { 00151 PCLASSINFO(H323Transactor, PObject); 00152 public: 00155 00158 H323Transactor( 00159 H323EndPoint & endpoint, 00160 H323Transport * transport, 00161 WORD localPort, 00162 WORD remotePort 00163 ); 00164 H323Transactor( 00165 H323EndPoint & endpoint, 00166 const H323TransportAddress & iface, 00167 WORD localPort, 00168 WORD remotePort 00169 ); 00170 00173 ~H323Transactor(); 00175 00180 void PrintOn( 00181 ostream & strm 00182 ) const; 00184 00189 BOOL SetTransport( 00190 const H323TransportAddress & iface 00191 ); 00192 00195 H323TransportAddressArray GetInterfaceAddresses( 00196 BOOL excludeLocalHost = TRUE, 00197 H323Transport * associatedTransport = NULL 00199 ); 00200 00203 virtual BOOL StartChannel(); 00204 00208 virtual void StopChannel(); 00209 00212 virtual H323TransactionPDU * CreateTransactionPDU() const = 0; 00213 00216 virtual BOOL HandleTransaction( 00217 const PASN_Object & rawPDU 00218 ) = 0; 00219 00222 virtual void OnSendingPDU( 00223 PASN_Object & rawPDU 00224 ) = 0; 00225 00228 virtual BOOL WritePDU( 00229 H323TransactionPDU & pdu 00230 ); 00231 00234 virtual BOOL WriteTo( 00235 H323TransactionPDU & pdu, 00236 const H323TransportAddressArray & addresses, 00237 BOOL callback = TRUE 00238 ); 00240 00245 H323EndPoint & GetEndPoint() const { return endpoint; } 00246 00249 H323Transport & GetTransport() const { return *transport; } 00250 00253 void SetCheckResponseCryptoTokens( 00254 BOOL value 00255 ) { checkResponseCryptoTokens = value; } 00256 00259 BOOL GetCheckResponseCryptoTokens() { return checkResponseCryptoTokens; } 00261 00262 protected: 00263 void Construct(); 00264 00265 unsigned GetNextSequenceNumber(); 00266 BOOL SetUpCallSignalAddresses( 00267 H225_ArrayOf_TransportAddress & addresses 00268 ); 00269 00270 //Background thread handler. 00271 PDECLARE_NOTIFIER(PThread, H323Transactor, HandleTransactions); 00272 00273 class Request : public PObject 00274 { 00275 PCLASSINFO(Request, PObject); 00276 public: 00277 Request( 00278 unsigned seqNum, 00279 H323TransactionPDU & pdu 00280 ); 00281 Request( 00282 unsigned seqNum, 00283 H323TransactionPDU & pdu, 00284 const H323TransportAddressArray & addresses 00285 ); 00286 00287 BOOL Poll(H323Transactor &); 00288 void CheckResponse(unsigned, const PASN_Choice *); 00289 void OnReceiveRIP(unsigned milliseconds); 00290 00291 // Inter-thread transfer variables 00292 unsigned rejectReason; 00293 void * responseInfo; 00294 00295 H323TransportAddressArray requestAddresses; 00296 00297 unsigned sequenceNumber; 00298 H323TransactionPDU & requestPDU; 00299 PTimeInterval whenResponseExpected; 00300 PSyncPoint responseHandled; 00301 PMutex responseMutex; 00302 00303 enum { 00304 AwaitingResponse, 00305 ConfirmReceived, 00306 RejectReceived, 00307 TryAlternate, 00308 BadCryptoTokens, 00309 RequestInProgress, 00310 NoResponseReceived 00311 } responseResult; 00312 }; 00313 00314 virtual BOOL MakeRequest( 00315 Request & request 00316 ); 00317 BOOL CheckForResponse( 00318 unsigned, 00319 unsigned, 00320 const PASN_Choice * = NULL 00321 ); 00322 BOOL HandleRequestInProgress( 00323 const H323TransactionPDU & pdu, 00324 unsigned delay 00325 ); 00326 BOOL CheckCryptoTokens( 00327 const H323TransactionPDU & pdu, 00328 const PASN_Array & clearTokens, 00329 unsigned clearOptionalField, 00330 const PASN_Array & cryptoTokens, 00331 unsigned cryptoOptionalField 00332 ); 00333 00334 void AgeResponses(); 00335 BOOL SendCachedResponse( 00336 const H323TransactionPDU & pdu 00337 ); 00338 00339 class Response : public PString 00340 { 00341 PCLASSINFO(Response, PString); 00342 public: 00343 Response(const H323TransportAddress & addr, unsigned seqNum); 00344 ~Response(); 00345 00346 void SetPDU(const H323TransactionPDU & pdu); 00347 BOOL SendCachedResponse(H323Transport & transport); 00348 00349 PTime lastUsedTime; 00350 PTimeInterval retirementAge; 00351 H323TransactionPDU * replyPDU; 00352 }; 00353 00354 // Configuration variables 00355 H323EndPoint & endpoint; 00356 WORD defaultLocalPort; 00357 WORD defaultRemotePort; 00358 H323Transport * transport; 00359 BOOL checkResponseCryptoTokens; 00360 00361 unsigned nextSequenceNumber; 00362 PMutex nextSequenceNumberMutex; 00363 00364 PDictionary<POrdinalKey, Request> requests; 00365 PMutex requestsMutex; 00366 Request * lastRequest; 00367 00368 PMutex pduWriteMutex; 00369 PSortedList<Response> responses; 00370 }; 00371 00372 00374 00375 class H323Transaction : public PObject 00376 { 00377 PCLASSINFO(H323Transaction, PObject); 00378 public: 00383 H323Transaction( 00384 H323Transactor & transactor, 00385 const H323TransactionPDU & requestToCopy, 00386 H323TransactionPDU * confirm, 00387 H323TransactionPDU * reject 00388 ); 00389 ~H323Transaction(); 00391 00392 enum Response { 00393 Ignore = -2, 00394 Reject = -1, 00395 Confirm = 0 00396 }; 00397 inline static Response InProgress(unsigned time) { return (Response)(time&0xffff); } 00398 00399 virtual H323TransactionPDU * CreateRIP( 00400 unsigned sequenceNumber, 00401 unsigned delay 00402 ) const = 0; 00403 00404 BOOL HandlePDU(); 00405 00406 virtual BOOL WritePDU( 00407 H323TransactionPDU & pdu 00408 ); 00409 00410 BOOL CheckCryptoTokens( 00411 const H235Authenticators & authenticators 00412 ); 00413 00414 #if PTRACING 00415 virtual const char * GetName() const = 0; 00416 #endif 00417 virtual H235Authenticator::ValidationResult ValidatePDU() const = 0; 00418 virtual void SetRejectReason( 00419 unsigned reasonCode 00420 ) = 0; 00421 00422 BOOL IsFastResponseRequired() const { return fastResponseRequired && canSendRIP; } 00423 BOOL CanSendRIP() const { return canSendRIP; } 00424 H323TransportAddress GetReplyAddress() const { return replyAddresses[0]; } 00425 const H323TransportAddressArray & GetReplyAddresses() const { return replyAddresses; } 00426 BOOL IsBehindNAT() const { return isBehindNAT; } 00427 H323Transactor & GetTransactor() const { return transactor; } 00428 H235Authenticator::ValidationResult GetAuthenticatorResult() const { return authenticatorResult; } 00429 00430 protected: 00431 virtual Response OnHandlePDU() = 0; 00432 PDECLARE_NOTIFIER(PThread, H323Transaction, SlowHandler); 00433 00434 H323Transactor & transactor; 00435 unsigned requestSequenceNumber; 00436 H323TransportAddressArray replyAddresses; 00437 BOOL fastResponseRequired; 00438 H323TransactionPDU * request; 00439 H323TransactionPDU * confirm; 00440 H323TransactionPDU * reject; 00441 00442 H235Authenticators authenticators; 00443 H235Authenticator::ValidationResult authenticatorResult; 00444 BOOL isBehindNAT; 00445 BOOL canSendRIP; 00446 }; 00447 00448 00450 00451 class H323TransactionServer : public PObject 00452 { 00453 PCLASSINFO(H323TransactionServer, PObject); 00454 public: 00459 H323TransactionServer( 00460 H323EndPoint & endpoint 00461 ); 00462 00465 ~H323TransactionServer(); 00467 00468 virtual WORD GetDefaultUdpPort() = 0; 00469 00474 H323EndPoint & GetOwnerEndPoint() const { return ownerEndPoint; } 00475 00489 BOOL AddListeners( 00490 const H323TransportAddressArray & ifaces 00491 ); 00492 00496 BOOL AddListener( 00497 const H323TransportAddress & interfaceName 00498 ); 00499 00506 BOOL AddListener( 00507 H323Transport * transport 00508 ); 00509 00516 BOOL AddListener( 00517 H323Transactor * listener 00518 ); 00519 00528 virtual H323Transactor * CreateListener( 00529 H323Transport * transport 00530 ) = 0; 00531 00535 BOOL RemoveListener( 00536 H323Transactor * listener 00537 ); 00538 00539 BOOL SetUpCallSignalAddresses(H225_ArrayOf_TransportAddress & addresses); 00541 00542 protected: 00543 H323EndPoint & ownerEndPoint; 00544 00545 PThread * monitorThread; 00546 PSyncPoint monitorExit; 00547 00548 PMutex mutex; 00549 PLIST(ListenerList, H323Transactor); 00550 ListenerList listeners; 00551 BOOL usingAllInterfaces; 00552 }; 00553 00554 00555 #endif // __OPAL_H323TRANS_H 00556 00557