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
00032
00033
00034
00035 #ifndef OPAL_OPAL_CONNECTION_H
00036 #define OPAL_OPAL_CONNECTION_H
00037
00038 #ifdef P_USE_PRAGMA
00039 #pragma interface
00040 #endif
00041
00042 #include <opal/buildopts.h>
00043
00044 #include <opal/mediafmt.h>
00045 #include <opal/mediastrm.h>
00046 #include <opal/guid.h>
00047 #include <opal/transports.h>
00048 #include <ptclib/dtmf.h>
00049 #include <ptlib/safecoll.h>
00050 #include <rtp/rtp.h>
00051 #include <im/t140.h>
00052
00053 class OpalEndPoint;
00054 class OpalCall;
00055 class OpalSilenceDetector;
00056 class OpalEchoCanceler;
00057 class OpalRFC2833Proto;
00058 class OpalRFC2833Info;
00059
00060
00061 #define OPAL_OPT_AUTO_START "AutoStart"
00062 #define OPAL_OPT_CALL_IDENTIFIER "Call-Identifier"
00063 #define OPAL_OPT_CALLING_PARTY_URL "Calling-Party-URL"
00064 #define OPAL_OPT_CALLING_PARTY_NUMBER "Calling-Party-Number"
00065 #define OPAL_OPT_CALLING_PARTY_NAME "Calling-Party-Name"
00066 #define OPAL_OPT_CALLING_PARTY_DOMAIN "Calling-Party-Domain"
00067 #define OPAL_OPT_CALLING_DISPLAY_NAME "Calling-Display-Name"
00068 #define OPAL_OPT_ORIGINATOR_ADDRESS "Originator-Address"
00069 #define OPAL_OPT_INTERFACE "Interface"
00070 #define OPAL_OPT_ENABLE_INBAND_DTMF "EnableInbandDTMF"
00071 #define OPAL_OPT_DTMF_MULT "dtmfmult"
00072 #define OPAL_OPT_DTMF_DIV "dtmfdiv"
00073 #define OPAL_OPT_DISABLE_JITTER "Disable-Jitter"
00074 #define OPAL_OPT_MAX_JITTER "Max-Jitter"
00075 #define OPAL_OPT_MIN_JITTER "Min-Jitter"
00076 #define OPAL_OPT_RECORD_AUDIO "Record-Audio"
00077 #define OPAL_OPT_ALERTING_TYPE "Alerting-Type"
00078
00079
00291 class OpalProductInfo
00292 {
00293 public:
00294 OpalProductInfo();
00295
00296 static OpalProductInfo & Default();
00297
00298 PCaselessString AsString() const;
00299
00300 PString vendor;
00301 PString name;
00302 PString version;
00303 PString comments;
00304 BYTE t35CountryCode;
00305 BYTE t35Extension;
00306 WORD manufacturerCode;
00307 };
00308
00309
00327 class OpalConnection : public PSafeObject
00328 {
00329 PCLASSINFO(OpalConnection, PSafeObject);
00330 public:
00335 enum CallEndReason {
00336 EndedByLocalUser,
00337 EndedByNoAccept,
00338 EndedByAnswerDenied,
00339 EndedByRemoteUser,
00340 EndedByRefusal,
00341 EndedByNoAnswer,
00342 EndedByCallerAbort,
00343 EndedByTransportFail,
00344 EndedByConnectFail,
00345 EndedByGatekeeper,
00346 EndedByNoUser,
00347 EndedByNoBandwidth,
00348 EndedByCapabilityExchange,
00349 EndedByCallForwarded,
00350 EndedBySecurityDenial,
00351 EndedByLocalBusy,
00352 EndedByLocalCongestion,
00353 EndedByRemoteBusy,
00354 EndedByRemoteCongestion,
00355 EndedByUnreachable,
00356 EndedByNoEndPoint,
00357 EndedByHostOffline,
00358 EndedByTemporaryFailure,
00359 EndedByQ931Cause,
00360 EndedByDurationLimit,
00361 EndedByInvalidConferenceID,
00362 EndedByNoDialTone,
00363 EndedByNoRingBackTone,
00364 EndedByOutOfService,
00365 EndedByAcceptingCallWaiting,
00366 NumCallEndReasons,
00367
00368 EndedWithQ931Code = 0x100
00369 };
00370
00371 #if PTRACING
00372 friend ostream & operator<<(ostream & o, CallEndReason reason);
00373 #endif
00374
00375 enum AnswerCallResponse {
00376 AnswerCallNow,
00377 AnswerCallDenied,
00378 AnswerCallPending,
00379 AnswerCallDeferred,
00380 AnswerCallAlertWithMedia,
00381 AnswerCallDeferredWithMedia,
00382 AnswerCallProgress,
00383 AnswerCallNowAndReleaseCurrent,
00384 NumAnswerCallResponses
00385 };
00386 #if PTRACING
00387 friend ostream & operator<<(ostream & o, AnswerCallResponse s);
00388 #endif
00389
00392 enum Options {
00393 FastStartOptionDisable = 0x0001,
00394 FastStartOptionEnable = 0x0002,
00395 FastStartOptionMask = 0x0003,
00396
00397 H245TunnelingOptionDisable = 0x0004,
00398 H245TunnelingOptionEnable = 0x0008,
00399 H245TunnelingOptionMask = 0x000c,
00400
00401 H245inSetupOptionDisable = 0x0010,
00402 H245inSetupOptionEnable = 0x0020,
00403 H245inSetupOptionMask = 0x0030,
00404
00405 DetectInBandDTMFOptionDisable = 0x0040,
00406 DetectInBandDTMFOptionEnable = 0x0080,
00407 DetectInBandDTMFOptionMask = 0x00c0,
00408
00409 RTPAggregationDisable = 0x0100,
00410 RTPAggregationEnable = 0x0200,
00411 RTPAggregationMask = 0x0300,
00412
00413 SendDTMFAsDefault = 0x0000,
00414 SendDTMFAsString = 0x0400,
00415 SendDTMFAsTone = 0x0800,
00416 SendDTMFAsRFC2833 = 0x0c00,
00417 SendDTMFMask = 0x0c00
00418 };
00419
00420 class StringOptions : public PStringToString
00421 {
00422 };
00423
00428 OpalConnection(
00429 OpalCall & call,
00430 OpalEndPoint & endpoint,
00431 const PString & token,
00432 unsigned options = 0,
00433 OpalConnection::StringOptions * stringOptions = NULL
00434 );
00435
00438 ~OpalConnection();
00440
00447 void PrintOn(
00448 ostream & strm
00449 ) const;
00451
00468 virtual bool IsNetworkConnection() const = 0;
00469
00473 enum Phases {
00474 UninitialisedPhase,
00475 SetUpPhase,
00476 ProceedingPhase,
00477 AlertingPhase,
00478 ConnectedPhase,
00479 EstablishedPhase,
00480 ReleasingPhase,
00481 ReleasedPhase,
00482 NumPhases
00483 };
00484
00489 inline Phases GetPhase() const { return phase; }
00490
00499 CallEndReason GetCallEndReason() const { return callEndReason; }
00500
00505 virtual void SetCallEndReason(
00506 CallEndReason reason
00507 );
00508
00516 void ClearCall(
00517 CallEndReason reason = EndedByLocalUser
00518 );
00519
00522 virtual void ClearCallSynchronous(
00523 PSyncPoint * sync,
00524 CallEndReason reason = EndedByLocalUser
00525 );
00526
00530 unsigned GetQ931Cause() const { return q931Cause; }
00531
00535 void SetQ931Cause(unsigned v) { q931Cause = v; }
00536
00543 virtual bool TransferConnection(
00544 const PString & remoteParty
00545 );
00546
00549 virtual bool HoldConnection();
00550
00554 virtual bool RetrieveConnection();
00555
00558 virtual PBoolean IsConnectionOnHold();
00559
00564 virtual void OnHold(
00565 bool fromRemote,
00566 bool onHold
00567 );
00569
00597 virtual PBoolean OnIncomingConnection(unsigned int options, OpalConnection::StringOptions * stringOptions);
00598 virtual PBoolean OnIncomingConnection(unsigned int options);
00599 virtual PBoolean OnIncomingConnection();
00600
00607 virtual PBoolean SetUpConnection() = 0;
00608
00612 virtual PBoolean OnSetUpConnection();
00613
00614
00629 virtual void OnProceeding();
00630
00641 virtual void OnAlerting();
00642
00653 virtual PBoolean SetAlerting(
00654 const PString & calleeName,
00655 PBoolean withMedia
00656 ) = 0;
00657
00674 virtual AnswerCallResponse OnAnswerCall(
00675 const PString & callerName
00676 );
00677
00688 virtual void AnsweringCall(
00689 AnswerCallResponse response
00690 );
00691
00706 virtual void OnConnected();
00707
00718 virtual PBoolean SetConnected();
00719
00731 virtual void OnEstablished();
00732
00741 virtual void Release(
00742 CallEndReason reason = EndedByLocalUser
00743 );
00744
00762 virtual void OnReleased();
00764
00775 virtual PString GetDestinationAddress();
00776
00786 virtual PBoolean ForwardCall(
00787 const PString & forwardParty
00788 );
00789
00792 PSafePtr<OpalConnection> GetOtherPartyConnection() const;
00793
00796 template <class cls> PSafePtr<cls> GetOtherPartyConnectionAs() const { return PSafePtrCast<OpalConnection, cls>(GetOtherPartyConnection()); }
00798
00807 virtual OpalMediaFormatList GetMediaFormats() const;
00808
00813 virtual OpalMediaFormatList GetLocalMediaFormats();
00814
00823 virtual void AdjustMediaFormats(
00824 OpalMediaFormatList & mediaFormats
00825 ) const;
00826
00829 virtual OpalMediaStreamPtr OpenMediaStream(
00830 const OpalMediaFormat & mediaFormat,
00831 unsigned sessionID,
00832 bool isSource
00833 );
00834
00839 virtual bool CloseMediaStream(
00840 unsigned sessionId,
00841 bool source
00842 );
00843
00848 virtual bool CloseMediaStream(
00849 OpalMediaStream & stream
00850 );
00851
00859 bool RemoveMediaStream(
00860 OpalMediaStream & strm
00861 );
00862
00865 virtual void StartMediaStreams();
00866
00869 virtual void CloseMediaStreams();
00870
00873 virtual void PauseMediaStreams(PBoolean paused);
00874
00887 virtual OpalMediaStream * CreateMediaStream(
00888 const OpalMediaFormat & mediaFormat,
00889 unsigned sessionID,
00890 PBoolean isSource
00891 );
00892
00896 OpalMediaStreamPtr GetMediaStream(
00897 const PString & streamID,
00898 bool source
00899 ) const;
00900
00906 OpalMediaStreamPtr GetMediaStream(
00907 unsigned sessionId,
00908 bool source
00909 ) const;
00910
00916 OpalMediaStreamPtr GetMediaStream(
00917 const OpalMediaType & mediaType,
00918 bool source
00919 ) const;
00920
00932 virtual PBoolean OnOpenMediaStream(
00933 OpalMediaStream & stream
00934 );
00935
00940 virtual void OnClosedMediaStream(
00941 const OpalMediaStream & stream
00942 );
00943
00948 virtual void OnPatchMediaStream(
00949 PBoolean isSource,
00950 OpalMediaPatch & patch
00951 );
00952
00957 virtual void AttachRFC2833HandlerToPatch(PBoolean isSource, OpalMediaPatch & patch);
00958
00964 virtual PBoolean IsMediaBypassPossible(
00965 unsigned sessionID
00966 ) const;
00967
00968 #if OPAL_VIDEO
00969
00974 virtual void AddVideoMediaFormats(
00975 OpalMediaFormatList & mediaFormats
00976 ) const;
00977
00980 virtual PBoolean CreateVideoInputDevice(
00981 const OpalMediaFormat & mediaFormat,
00982 PVideoInputDevice * & device,
00983 PBoolean & autoDelete
00984 );
00985
00989 virtual PBoolean CreateVideoOutputDevice(
00990 const OpalMediaFormat & mediaFormat,
00991 PBoolean preview,
00992 PVideoOutputDevice * & device,
00993 PBoolean & autoDelete
00994 );
00995 #endif
00996
00999 virtual PBoolean SetAudioVolume(
01000 PBoolean source,
01001 unsigned percentage
01002 );
01003
01007 virtual unsigned GetAudioSignalLevel(
01008 PBoolean source
01009 );
01011
01016 unsigned GetBandwidthAvailable() const { return bandwidthAvailable; }
01017
01022 virtual PBoolean SetBandwidthAvailable(
01023 unsigned newBandwidth,
01024 PBoolean force = PFalse
01025 );
01026
01031 virtual unsigned GetBandwidthUsed() const;
01032
01041 virtual PBoolean SetBandwidthUsed(
01042 unsigned releasedBandwidth,
01043 unsigned requiredBandwidth
01044 );
01046
01049 enum SendUserInputModes {
01050 SendUserInputAsQ931,
01051 SendUserInputAsString,
01052 SendUserInputAsTone,
01053 SendUserInputAsInlineRFC2833,
01054 SendUserInputAsSeparateRFC2833,
01055 SendUserInputAsProtocolDefault,
01056 NumSendUserInputModes
01057 };
01058 #if PTRACING
01059 friend ostream & operator<<(ostream & o, SendUserInputModes m);
01060 #endif
01061
01064 virtual void SetSendUserInputMode(SendUserInputModes mode);
01065
01068 virtual SendUserInputModes GetSendUserInputMode() const { return sendUserInputMode; }
01069
01075 virtual SendUserInputModes GetRealSendUserInputMode() const { return GetSendUserInputMode(); }
01076
01083 virtual PBoolean SendUserInputString(
01084 const PString & value
01085 );
01086
01103 virtual PBoolean SendUserInputTone(
01104 char tone,
01105 unsigned duration = 0
01106 );
01107
01114 virtual void OnUserInputString(
01115 const PString & value
01116 );
01117
01124 virtual void OnUserInputTone(
01125 char tone,
01126 unsigned duration
01127 );
01128
01132 void SendUserInputHookFlash(
01133 unsigned duration = 500
01134 ) { SendUserInputTone('!', duration); }
01135
01138 virtual PString GetUserInput(
01139 unsigned timeout = 30
01140 );
01141
01146 virtual void SetUserInput(
01147 const PString & input
01148 );
01149
01152 virtual PString ReadUserInput(
01153 const char * terminators = "#\r\n",
01154 unsigned lastDigitTimeout = 4,
01155 unsigned firstDigitTimeout = 30
01156 );
01157
01164 virtual PBoolean PromptUserInput(
01165 PBoolean play
01166 );
01168
01173 virtual bool GarbageCollection();
01175
01180 OpalEndPoint & GetEndPoint() const { return endpoint; }
01181
01184 OpalCall & GetCall() const { return ownerCall; }
01185
01188 const PString & GetToken() const { return callToken; }
01189
01192 PBoolean IsOriginating() const { return originating; }
01193
01196 PTime GetSetupUpTime() const { return setupTime; }
01197
01200 PTime GetAlertingTime() const { return alertingTime; }
01201
01204 PTime GetConnectionStartTime() const { return connectedTime; }
01205
01208 PTime GetConnectionEndTime() const { return callEndTime; }
01209
01212 const OpalProductInfo & GetProductInfo() const { return productInfo; }
01213
01216 void SetProductInfo(
01217 const OpalProductInfo & info
01218 ) { productInfo = info; }
01219
01222 virtual PString GetPrefixName() const;
01223
01226 const PString & GetLocalPartyName() const { return localPartyName; }
01227
01230 virtual void SetLocalPartyName(const PString & name);
01231
01234 virtual PString GetLocalPartyURL() const;
01235
01238 const PString & GetDisplayName() const { return displayName; }
01239
01242 void SetDisplayName(const PString & name) { displayName = name; }
01243
01246 const PString & GetRemotePartyName() const { return remotePartyName; }
01247
01250 void SetRemotePartyName(const PString & name) { remotePartyName = name; }
01251
01260 const PString & GetRemotePartyNumber() const { return remotePartyNumber; }
01261
01267 const PString & GetRemotePartyAddress() const { return remotePartyAddress; }
01268
01271 void SetRemotePartyAddress(const PString & addr) { remotePartyAddress = addr; }
01272
01279 virtual PString GetRemotePartyURL() const;
01280
01281
01282 const PString GetRemotePartyCallbackURL() const { return GetRemotePartyURL(); }
01283
01287 PCaselessString GetRemoteApplication() const { return remoteProductInfo.AsString(); }
01288
01291 const OpalProductInfo & GetRemoteProductInfo() const { return remoteProductInfo; }
01292
01293
01300 const PString & GetCalledPartyName() const { return m_calledPartyName; }
01301
01308 const PString & GetCalledPartyNumber() const { return m_calledPartyNumber; }
01309
01317 virtual PString GetCalledPartyURL();
01318
01319
01320
01321
01322
01323
01324 void CopyPartyNames(const OpalConnection & other);
01325
01326
01340 virtual PString GetAlertingType() const;
01341
01355 virtual bool SetAlertingType(const PString & info);
01356
01357
01361 unsigned GetMinAudioJitterDelay() const { return minAudioJitterDelay; }
01362
01366 unsigned GetMaxAudioJitterDelay() const { return maxAudioJitterDelay; }
01367
01370 void SetAudioJitterDelay(
01371 unsigned minDelay,
01372 unsigned maxDelay
01373 );
01374
01377 OpalSilenceDetector * GetSilenceDetector() const { return silenceDetector; }
01378
01381 OpalEchoCanceler * GetEchoCanceler() const { return echoCanceler; }
01382
01386 virtual PString GetIdentifier() const;
01387
01396 virtual PINDEX GetMaxRtpPayloadSize() const;
01397
01398 virtual OpalTransport & GetTransport() const
01399 { return *(OpalTransport *)NULL; }
01400
01401 PDICTIONARY(MediaAddressesDict, POrdinalKey, OpalTransportAddress);
01402 MediaAddressesDict & GetMediaTransportAddresses()
01403 { return mediaTransportAddresses; }
01404
01405 #if OPAL_STATISTICS
01406
01408 unsigned GetVideoUpdateRequestsSent() const { return m_VideoUpdateRequestsSent; }
01409 #endif
01410
01411
01413 const StringOptions & GetStringOptions() const { return m_connStringOptions; }
01414
01416 void SetStringOptions(
01417 const StringOptions & options,
01418 bool overwrite
01419 );
01420
01421 virtual void ApplyStringOptions(OpalConnection::StringOptions & stringOptions);
01422 virtual void OnApplyStringOptions();
01423
01424 virtual void PreviewPeerMediaFormats(const OpalMediaFormatList & fmts);
01425
01426 virtual void EnableRecording();
01427 virtual void DisableRecording();
01428
01429 virtual void OnMediaPatchStart(
01430 unsigned sessionId,
01431 bool isSource
01432 );
01433 virtual void OnMediaPatchStop(
01434 unsigned sessionId,
01435 bool isSource
01436 );
01437
01441 PDECLARE_NOTIFIER(OpalMediaCommand, OpalConnection, OnMediaCommand);
01442
01449 virtual OpalMediaType::AutoStartMode GetAutoStart(
01450 const OpalMediaType & mediaType
01451 ) const;
01452
01453 #if OPAL_HAS_IM
01454 struct IMInfo : public PObject {
01455 unsigned sessionId;
01456 OpalMediaFormat mediaFormat;
01457 T140String body;
01458 };
01459
01460 virtual bool SendIM(const OpalMediaFormat & format, const T140String & body);
01461 virtual bool SendIM(const OpalMediaFormat & format, const RTP_DataFrame & body);
01462 virtual void OnReceiveIM(const IMInfo & im);
01463
01464 void AddIMListener(
01465 const PNotifier & listener
01466 );
01467 #endif
01468
01469 protected:
01470 void OnConnectedInternal();
01471
01472 #if OPAL_PTLIB_DTMF
01473 PDECLARE_NOTIFIER(RTP_DataFrame, OpalConnection, OnUserInputInBandDTMF);
01474 #endif
01475 PDECLARE_NOTIFIER(PThread, OpalConnection, OnReleaseThreadMain);
01476 PDECLARE_NOTIFIER(RTP_DataFrame, OpalConnection, OnRecordAudio);
01477
01478
01479 OpalCall & ownerCall;
01480 OpalEndPoint & endpoint;
01481
01482 private:
01483 PMutex phaseMutex;
01484 Phases phase;
01485
01486 protected:
01487 PString callToken;
01488 PBoolean originating;
01489 PTime setupTime;
01490 PTime alertingTime;
01491 PTime connectedTime;
01492 PTime callEndTime;
01493 OpalProductInfo productInfo;
01494 PString localPartyName;
01495 PString displayName;
01496 PString remotePartyName;
01497 OpalProductInfo remoteProductInfo;
01498 PString remotePartyNumber;
01499 PString remotePartyAddress;
01500 CallEndReason callEndReason;
01501 bool synchronousOnRelease;
01502 PString m_calledPartyNumber;
01503 PString m_calledPartyName;
01504
01505 SendUserInputModes sendUserInputMode;
01506 PString userInputString;
01507 PSyncPoint userInputAvailable;
01508 PBoolean detectInBandDTMF;
01509 unsigned dtmfScaleMultiplier;
01510 unsigned dtmfScaleDivisor;
01511 unsigned q931Cause;
01512
01513 OpalSilenceDetector * silenceDetector;
01514 OpalEchoCanceler * echoCanceler;
01515
01516 MediaAddressesDict mediaTransportAddresses;
01517 PSafeList<OpalMediaStream> mediaStreams;
01518
01519 unsigned minAudioJitterDelay;
01520 unsigned maxAudioJitterDelay;
01521 unsigned bandwidthAvailable;
01522
01523
01524
01525 #if OPAL_PTLIB_DTMF
01526 PDTMFDecoder dtmfDecoder;
01527 #endif
01528
01532 void SetPhase(Phases phaseToSet);
01533
01534 #if PTRACING
01535 friend ostream & operator<<(ostream & o, Phases p);
01536 #endif
01537
01538 StringOptions m_connStringOptions;
01539 PString recordAudioFilename;
01540 PNotifier recordNotifier;
01541
01542 #if OPAL_STATISTICS
01543 unsigned m_VideoUpdateRequestsSent;
01544 #endif
01545
01546 struct AutoStartInfo {
01547 unsigned preferredSessionId;
01548 OpalMediaType::AutoStartMode autoStart;
01549 };
01550
01551 class AutoStartMap : public std::map<OpalMediaType, AutoStartInfo>
01552 {
01553 public:
01554 AutoStartMap();
01555 void Initialise(const OpalConnection::StringOptions & stringOptions);
01556 OpalMediaType::AutoStartMode GetAutoStart(const OpalMediaType & mediaType) const;
01557 void SetAutoStart(const OpalMediaType & mediaType, OpalMediaType::AutoStartMode autoStart);
01558
01559 protected:
01560 bool m_initialised;
01561 PMutex m_mutex;
01562
01563 };
01564 AutoStartMap m_autoStartInfo;
01565
01566 #if OPAL_HAS_IM
01567 mutable PList<PNotifier> m_imListeners;
01568 #endif
01569
01570 };
01571
01572 #endif // OPAL_OPAL_CONNECTION_H
01573
01574
01575