# peclient.h

Go to the documentation of this file.

    00001 /*
    00002  * peclient.h
    00003  *
    00004  * H.323 Annex G Peer Element client protocol 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  * $Revision: 21028 $
    00027  * $Author: csoutheren $
    00028  * $Date: 2008-09-16 23:32:30 +0000 (Tue, 16 Sep 2008) $
    00029  */
    00030
    00031 #ifndef __OPAL_PECLIENT_H
    00032 #define __OPAL_PECLIENT_H
    00033
    00034 #ifdef P_USE_PRAGMA
    00035 #pragma interface
    00036 #endif
    00037
    00038 #include <opal/buildopts.h>
    00039
    00040 #include <h323/h323annexg.h>
    00041 #include <h323/h323ep.h>
    00042
    00043 #include <ptlib/safecoll.h>
    00044
    00045
    00046 class H323PeerElement;
    00047
    00048
    00050
    00051 class H501Transaction : public H323Transaction
    00052 {
    00053     PCLASSINFO(H501Transaction, H323Transaction);
    00054   public:
    00055     H501Transaction(
    00056       H323PeerElement & pe,
    00057       const H501PDU & pdu,
    00058       PBoolean hasReject
    00059     );
    00060
    00061     virtual H323TransactionPDU * CreateRIP(
    00062       unsigned sequenceNumber,
    00063       unsigned delay
    00064     ) const;
    00065
    00066     virtual H235Authenticator::ValidationResult ValidatePDU() const;
    00067
    00068     H501_MessageCommonInfo & requestCommon;
    00069     H501_MessageCommonInfo & confirmCommon;
    00070
    00071   protected:
    00072     H323PeerElement & peerElement;
    00073 };
    00074
    00075
    00077
    00078 class H501ServiceRequest : public H501Transaction
    00079 {
    00080     PCLASSINFO(H501ServiceRequest, H501Transaction);
    00081   public:
    00082     H501ServiceRequest(
    00083       H323PeerElement & pe,
    00084       const H501PDU & pdu
    00085     );
    00086
    00087 #if PTRACING
    00088     virtual const char * GetName() const;
    00089 #endif
    00090     virtual void SetRejectReason(
    00091       unsigned reasonCode
    00092     );
    00093
    00094     H501_ServiceRequest & srq;
    00095     H501_ServiceConfirmation & scf;
    00096     H501_ServiceRejection  & srj;
    00097
    00098   protected:
    00099     virtual Response OnHandlePDU();
    00100 };
    00101
    00102
    00104
    00105 class H501DescriptorUpdate : public H501Transaction
    00106 {
    00107     PCLASSINFO(H501DescriptorUpdate, H501Transaction);
    00108   public:
    00109     H501DescriptorUpdate(
    00110       H323PeerElement & pe,
    00111       const H501PDU & pdu
    00112     );
    00113
    00114 #if PTRACING
    00115     virtual const char * GetName() const;
    00116 #endif
    00117     virtual void SetRejectReason(
    00118       unsigned reasonCode
    00119     );
    00120
    00121     H501_DescriptorUpdate & du;
    00122     H501_DescriptorUpdateAck & ack;
    00123
    00124   protected:
    00125     virtual Response OnHandlePDU();
    00126 };
    00127
    00128
    00130
    00131 class H501AccessRequest : public H501Transaction
    00132 {
    00133     PCLASSINFO(H501AccessRequest, H501Transaction);
    00134   public:
    00135     H501AccessRequest(
    00136       H323PeerElement & pe,
    00137       const H501PDU & pdu
    00138     );
    00139
    00140 #if PTRACING
    00141     virtual const char * GetName() const;
    00142 #endif
    00143     virtual void SetRejectReason(
    00144       unsigned reasonCode
    00145     );
    00146
    00147     H501_AccessRequest & arq;
    00148     H501_AccessConfirmation & acf;
    00149     H501_AccessRejection  & arj;
    00150
    00151   protected:
    00152     virtual Response OnHandlePDU();
    00153 };
    00154
    00155
    00157
    00158 class H323PeerElementDescriptor : public PSafeObject
    00159 {
    00160   PCLASSINFO(H323PeerElementDescriptor, PSafeObject);
    00161   public:
    00162     H323PeerElementDescriptor(const OpalGloballyUniqueID & _descriptorID)
    00163       : descriptorID(_descriptorID), state(Dirty), creator(0)
    00164     { }
    00165
    00166     Comparison Compare(const PObject & obj) const;
    00167
    00168     enum Options {
    00169       Protocol_H323            = 0x0001,
    00170       Protocol_Voice           = 0x0002,
    00171       Protocol_Max             = 0x0002,
    00172       Option_WildCard          = 0x0004,
    00173       Option_SendAccessRequest = 0x0008,
    00174       Option_NotAvailable      = 0x0010,
    00175       Option_PrioritySet       = 0x0020,
    00176       Option_PriorityMask      = 0x1fc0,
    00177     };
    00178
    00179     enum {
    00180       HighestPriority          = 0,
    00181       DefaultPriority          = 80,
    00182       LowestPriority           = 127
    00183     };
    00184
    00185     static inline unsigned SetPriorityOption(unsigned pri)     { return Option_PrioritySet | ((pri & 0x7f) << 6); }
    00186     static inline unsigned GetPriorityOption(unsigned options) { return (options & Option_PrioritySet) != 0 ? ((options >> 6) & 0x7f) : (int)DefaultPriority; }
    00187
    00188     void CopyTo(H501_Descriptor & descriptor);
    00189     static PBoolean CopyToAddressTemplate(H501_AddressTemplate & addressTemplates,
    00190                                    const H225_EndpointType & ep,
    00191                            const H225_ArrayOf_AliasAddress & aliases,
    00192                            const H225_ArrayOf_AliasAddress & transportAddress,
    00193                                                     unsigned options = H323PeerElementDescriptor::Protocol_H323);
    00194
    00195     static void SetProtocolList(H501_ArrayOf_SupportedProtocols & h501Protocols, unsigned protocols);
    00196     static unsigned GetProtocolList(const H501_ArrayOf_SupportedProtocols & h501Protocols);
    00197
    00198     OpalGloballyUniqueID descriptorID;
    00199
    00200     PBoolean ContainsNonexistent();
    00201
    00202     enum States {
    00203       Clean,
    00204       Dirty,
    00205       Deleted
    00206     } state;
    00207
    00208     H501_ArrayOf_AddressTemplate addressTemplates;
    00209     PString gatekeeperID;
    00210     PTime lastChanged;
    00211     POrdinalKey creator;
    00212 };
    00213
    00214
    00216
    00217 class H323PeerElementServiceRelationship : public PSafeObject
    00218 {
    00219     PCLASSINFO(H323PeerElementServiceRelationship, PSafeObject);
    00220   public:
    00221     H323PeerElementServiceRelationship()
    00222       : ordinal(0)
    00223       { }
    00224
    00225     H323PeerElementServiceRelationship(const OpalGloballyUniqueID & _serviceID)
    00226       : serviceID(_serviceID), ordinal(0)
    00227       { }
    00228
    00229     Comparison Compare(const PObject & obj) const
    00230       { return serviceID.Compare(((H323PeerElementServiceRelationship&)obj).serviceID); }
    00231
    00232     OpalGloballyUniqueID serviceID;
    00233     POrdinalKey ordinal;
    00234     H323TransportAddress peer;
    00235     PString name;
    00236     PTime createdTime;
    00237     PTime lastUpdateTime;
    00238     PTime expireTime;
    00239 };
    00240
    00241
    00243
    00246 class H323PeerElement : public H323_AnnexG
    00247 {
    00248     PCLASSINFO(H323PeerElement, H323_AnnexG);
    00249   public:
    00254     H323PeerElement(
    00255       H323EndPoint & endpoint,
    00256       H323Transport * transport = NULL
    00257     );
    00258     H323PeerElement(
    00259       H323EndPoint & endpoint,
    00260       const H323TransportAddress & addr
    00261     );
    00262
    00265     ~H323PeerElement();
    00267
    00268     enum Error {
    00269       Confirmed,
    00270       Rejected,
    00271       NoResponse,
    00272       NoServiceRelationship,
    00273       ServiceRelationshipReestablished
    00274     };
    00275
    00276     enum {
    00277       LocalServiceRelationshipOrdinal  = 0,
    00278       NoServiceRelationshipOrdinal     = 1,
    00279       RemoteServiceRelationshipOrdinal = 2
    00280     };
    00281
    00286     void PrintOn(
    00287       ostream & strm
    00288     ) const;
    00290
    00291     PSafePtr<H323PeerElementDescriptor> GetFirstDescriptor(
    00292       PSafetyMode mode = PSafeReference
    00293     ) { return PSafePtr<H323PeerElementDescriptor>(descriptors, mode); }
    00294
    00295     PSafePtr<H323PeerElementServiceRelationship> GetFirstLocalServiceRelationship(
    00296       PSafetyMode mode = PSafeReference
    00297     ) { return PSafePtr<H323PeerElementServiceRelationship>(localServiceRelationships, mode); }
    00298
    00299     PSafePtr<H323PeerElementServiceRelationship> GetFirstRemoteServiceRelationship(
    00300       PSafetyMode mode = PSafeReference
    00301     ) { return PSafePtr<H323PeerElementServiceRelationship>(remoteServiceRelationships, mode); }
    00302
    00303     void SetLocalName(const PString & name);
    00304     PString GetLocalName() const;
    00305
    00306     void SetDomainName(const PString & name);
    00307     PString GetDomainName() const;
    00308
    00309     /*********************************************************
    00310       functions to establish and break service relationships
    00311       */
    00312
    00315     PBoolean SetOnlyServiceRelationship(const PString & peer, PBoolean keepTrying = PTrue);
    00316     PBoolean AddServiceRelationship(const H323TransportAddress & peer, PBoolean keepTrying = PTrue);
    00317     PBoolean AddServiceRelationship(const H323TransportAddress & peer, OpalGloballyUniqueID & serviceID, PBoolean keepTrying = PTrue);
    00318     PBoolean RemoveServiceRelationship(const OpalGloballyUniqueID & serviceID, int reason = H501_ServiceReleaseReason::e_terminated);
    00319     PBoolean RemoveServiceRelationship(const H323TransportAddress & peer, int reason = H501_ServiceReleaseReason::e_terminated);
    00320     PBoolean RemoveAllServiceRelationships();
    00321
    00322     Error ServiceRequestByAddr(const H323TransportAddress & peer);
    00323     Error ServiceRequestByAddr(const H323TransportAddress & peer, OpalGloballyUniqueID & serviceID);
    00324     Error ServiceRequestByID(OpalGloballyUniqueID & serviceID);
    00325
    00328     PBoolean ServiceRelease(const OpalGloballyUniqueID & serviceID, unsigned reason);
    00329
    00330     /*********************************************************
    00331       functions to manipulate the local descriptor table
    00332      */
    00333
    00334     PBoolean AddDescriptor(
    00335       const OpalGloballyUniqueID & descriptorID,
    00336       const PStringArray & aliases,
    00337       const H323TransportAddressArray & transportAddrs,
    00338       unsigned options = H323PeerElementDescriptor::Protocol_H323,
    00339       PBoolean now = PFalse
    00340     );
    00341
    00342     PBoolean AddDescriptor(
    00343       const OpalGloballyUniqueID & descriptorID,
    00344       const H225_ArrayOf_AliasAddress & aliases,
    00345       const H323TransportAddressArray & transportAddrs,
    00346       unsigned options = H323PeerElementDescriptor::Protocol_H323,
    00347       PBoolean now = PFalse
    00348     );
    00349
    00350     PBoolean AddDescriptor(
    00351       const OpalGloballyUniqueID & descriptorID,
    00352       const H225_ArrayOf_AliasAddress & aliases,
    00353       const H225_ArrayOf_AliasAddress & transportAddr,
    00354       unsigned options = H323PeerElementDescriptor::Protocol_H323,
    00355       PBoolean now = PFalse
    00356     );
    00357
    00358     PBoolean AddDescriptor(
    00359       const OpalGloballyUniqueID & descriptorID,
    00360       const POrdinalKey & creator,
    00361       const H225_ArrayOf_AliasAddress & alias,
    00362       const H225_ArrayOf_AliasAddress & transportAddresses,
    00363       unsigned options = H323PeerElementDescriptor::Protocol_H323,
    00364       PBoolean now = PFalse
    00365     );
    00366
    00367     PBoolean AddDescriptor(
    00368       const OpalGloballyUniqueID & descriptorID,
    00369       const POrdinalKey & creator,
    00370       const H501_ArrayOf_AddressTemplate & addressTemplates,
    00371       const PTime & updateTime,
    00372       PBoolean now = PFalse
    00373     );
    00374
    00377     PBoolean DeleteDescriptor(const PString & alias, PBoolean now = PFalse);
    00378     PBoolean DeleteDescriptor(const H225_AliasAddress & alias, PBoolean now = PFalse);
    00379     PBoolean DeleteDescriptor(const OpalGloballyUniqueID & descriptorID, PBoolean now = PFalse);
    00380
    00383     PBoolean AccessRequest(
    00384       const PString & searchAlias,
    00385       PStringArray & destAliases,
    00386       H323TransportAddress & transportAddress,
    00387       unsigned options = H323PeerElementDescriptor::Protocol_H323
    00388     );
    00389
    00390     PBoolean AccessRequest(
    00391       const PString & searchAlias,
    00392       H225_ArrayOf_AliasAddress & destAliases,
    00393       H323TransportAddress & transportAddress,
    00394       unsigned options = H323PeerElementDescriptor::Protocol_H323
    00395     );
    00396
    00397     PBoolean AccessRequest(
    00398       const H225_AliasAddress & searchAlias,
    00399       H225_ArrayOf_AliasAddress & destAliases,
    00400       H323TransportAddress & transportAddress,
    00401       unsigned options = H323PeerElementDescriptor::Protocol_H323
    00402     );
    00403
    00404     PBoolean AccessRequest(
    00405       const H225_AliasAddress & alias,
    00406       H225_ArrayOf_AliasAddress & destAliases,
    00407       H225_AliasAddress & transportAddress,
    00408       unsigned options = H323PeerElementDescriptor::Protocol_H323
    00409     );
    00410
    00411     /*********************************************************
    00412       functions to send send descriptors to another peer element
    00413       */
    00414     PBoolean UpdateDescriptor(H323PeerElementDescriptor * descriptor);
    00415     PBoolean UpdateDescriptor(H323PeerElementDescriptor * descriptor, H501_UpdateInformation_updateType::Choices updateType);
    00416
    00417
    00418     Error SendUpdateDescriptorByID(const OpalGloballyUniqueID & serviceID,
    00419                                     H323PeerElementDescriptor * descriptor,
    00420                      H501_UpdateInformation_updateType::Choices updateType);
    00421
    00422     Error SendUpdateDescriptorByAddr(const H323TransportAddress & peer,
    00423                                       H323PeerElementDescriptor * descriptor,
    00424                        H501_UpdateInformation_updateType::Choices updateType);
    00425
    00426     Error SendAccessRequestByID(const OpalGloballyUniqueID & peerID,
    00427                                                    H501PDU & request,
    00428                                                    H501PDU & confirmPDU);
    00429
    00430     Error SendAccessRequestByAddr(const H323TransportAddress & peerAddr,
    00431                                                      H501PDU & request,
    00432                                                      H501PDU & confirmPDU);
    00433
    00434
    00435     /*********************************************************
    00436       low level request functions
    00437       */
    00438
    00439     PBoolean MakeRequest(H323_AnnexG::Request & request);
    00440
    00441     virtual void OnAddServiceRelationship(const H323TransportAddress &) { }
    00442     virtual void OnRemoveServiceRelationship(const H323TransportAddress &) { }
    00443
    00444     virtual void OnNewDescriptor(const H323PeerElementDescriptor &) { }
    00445     virtual void OnUpdateDescriptor(const H323PeerElementDescriptor &) { }
    00446     virtual void OnRemoveDescriptor(const H323PeerElementDescriptor &) { }
    00447
    00448     virtual H323Transaction::Response OnServiceRequest(H501ServiceRequest & info);
    00449     virtual H323Transaction::Response OnDescriptorUpdate(H501DescriptorUpdate & info);
    00450     virtual H323Transaction::Response OnAccessRequest(H501AccessRequest & info);
    00451
    00452     PBoolean OnReceiveServiceRequest(const H501PDU & pdu, const H501_ServiceRequest & pduBody);
    00453     PBoolean OnReceiveServiceConfirmation(const H501PDU & pdu, const H501_ServiceConfirmation & pduBody);
    00454
    00455     PBoolean OnReceiveDescriptorUpdate(const H501PDU & pdu, const H501_DescriptorUpdate & pduBody);
    00456     PBoolean OnReceiveDescriptorUpdateACK(const H501PDU & pdu, const H501_DescriptorUpdateAck & pduBody);
    00457
    00458     PBoolean OnReceiveAccessRequest(const H501PDU & pdu, const H501_AccessRequest & pduBody);
    00459     PBoolean OnReceiveAccessConfirmation (const H501PDU & pdu, const H501_AccessConfirmation & pduBody);
    00460     PBoolean OnReceiveAccessRejection(const H501PDU & pdu,     const H501_AccessRejection & pduBody);
    00461
    00462     class AliasKey : public H225_AliasAddress
    00463     {
    00464       public:
    00465         AliasKey(const H225_AliasAddress & _alias, const OpalGloballyUniqueID & _id, PINDEX _pos, PBoolean _wild = PFalse)
    00466           : H225_AliasAddress(_alias), id(_id), pos(_pos), wild(_wild)
    00467         { }
    00468
    00469         OpalGloballyUniqueID id;
    00470         PINDEX pos;
    00471         PBoolean wild;
    00472     };
    00473
    00474   protected:
    00475     void Construct();
    00476
    00477     Error SendUpdateDescriptor(              H501PDU & pdu,
    00478                           const H323TransportAddress & peer,
    00479                            H323PeerElementDescriptor * descriptor,
    00480             H501_UpdateInformation_updateType::Choices updateType);
    00481
    00482     PBoolean OnRemoteServiceRelationshipDisappeared(OpalGloballyUniqueID & serviceID, const H323TransportAddress & peer);
    00483     void InternalRemoveServiceRelationship(const H323TransportAddress & peer);
    00484     H323Transaction::Response HandleServiceRequest(H501ServiceRequest & info);
    00485
    00486     virtual H323PeerElementDescriptor          * CreateDescriptor(const OpalGloballyUniqueID & descriptorID);
    00487     virtual H323PeerElementServiceRelationship * CreateServiceRelationship();
    00488     virtual AliasKey                           * CreateAliasKey(const H225_AliasAddress & alias, const OpalGloballyUniqueID & id, PINDEX pos, PBoolean wild = PFalse);
    00489
    00490     void RemoveDescriptorInformation(const H501_ArrayOf_AddressTemplate & addressTemplates);
    00491
    00492     PDECLARE_NOTIFIER(PThread, H323PeerElement, MonitorMain);
    00493     PDECLARE_NOTIFIER(PThread, H323PeerElement, UpdateAllDescriptors);
    00494     PDECLARE_NOTIFIER(PTimer, H323PeerElement, TickleMonitor);
    00495
    00496     PMutex localNameMutex;
    00497     PString localIdentifier;
    00498     PString domainName;
    00499
    00500     PSemaphore requestMutex;
    00501     PThread  * monitor;
    00502     PBoolean       monitorStop;
    00503     PSyncPoint monitorTickle;
    00504
    00505     PMutex basePeerOrdinalMutex;
    00506     PINDEX basePeerOrdinal;
    00507
    00508     // structures needed to maintain local service relationships (for which we receive a ServiceRequest)
    00509     PSafeSortedList<H323PeerElementServiceRelationship> localServiceRelationships;
    00510     PMutex localPeerListMutex;
    00511     POrdinalSet localServiceOrdinals;
    00512
    00513     // structures needed to maintain remote service relationships (for which we send a ServiceRequest)
    00514     PMutex remotePeerListMutex;
    00515     PSafeSortedList<H323PeerElementServiceRelationship> remoteServiceRelationships;
    00516     PStringToString remotePeerAddrToServiceID;
    00517     PDICTIONARY(StringToOrdinalKey, PString, POrdinalKey);
    00518     StringToOrdinalKey remotePeerAddrToOrdinalKey;
    00519
    00520     PSafeSortedList<H323PeerElementDescriptor> descriptors;
    00521
    00522     PSORTED_LIST(AliasKeyList, H225_AliasAddress);
    00523
    00524     PMutex aliasMutex;
    00525     AliasKeyList transportAddressToDescriptorID;
    00526     AliasKeyList specificAliasToDescriptorID;
    00527     AliasKeyList wildcardAliasToDescriptorID;
    00528 };
    00529
    00530
    00531 #endif // __OPAL_PECLIENT_H
    00532
    00533