Yate

yateiax.h

00001 
00024 #ifndef __YATEIAX_H
00025 #define __YATEIAX_H
00026 
00027 #include <yateclass.h>
00028 
00029 #ifdef _WINDOWS
00030 
00031 #ifdef LIBYIAX_EXPORTS
00032 #define YIAX_API __declspec(dllexport)
00033 #else
00034 #ifndef LIBYIAX_STATIC
00035 #define YIAX_API __declspec(dllimport)
00036 #endif
00037 #endif
00038 
00039 #endif /* _WINDOWS */
00040 
00041 #ifndef YIAX_API
00042 #define YIAX_API
00043 #endif
00044 
00048 namespace TelEngine {
00049 
00050 class IAXInfoElement;
00051 class IAXInfoElementString;
00052 class IAXInfoElementNumeric;
00053 class IAXInfoElementBinary;
00054 class IAXFullFrame;
00055 class IAXFrameOut;
00056 class IAXEvent;
00057 class IAXEngine;
00058 
00059 #define IAX_PROTOCOL_VERSION         0x0002           // Protocol version
00060 #define IAX2_MAX_CALLNO              32767            // Max call number value
00061 #define IAX2_MAX_TRANSINFRAMELIST    127              // Max transaction incoming frame list
00062 
00067 class YIAX_API IAXInfoElement : public RefObject
00068 {
00069 public:
00073     enum Type {
00074         textframe = 0x00,        // Text        Used internally only to generate an event of type Text
00075         CALLED_NUMBER = 0x01,    // Text
00076         CALLING_NUMBER = 0x02,   // Text
00077         CALLING_ANI = 0x03,      // Text
00078         CALLING_NAME = 0x04,     // Text
00079         CALLED_CONTEXT = 0x05,   // Text
00080         USERNAME = 0x06,         // Text
00081         PASSWORD = 0x07,         // Text
00082         CAPABILITY = 0x08,       // DW
00083         FORMAT = 0x09,           // DW
00084         LANGUAGE = 0x0a,         // Text
00085         VERSION = 0x0b,          // W           Value: IAX_PROTOCOL_VERSION
00086         ADSICPE = 0x0c,          // W
00087         DNID = 0x0d,             // Text
00088         AUTHMETHODS = 0x0e,      // W
00089         CHALLENGE = 0x0f,        // Text
00090         MD5_RESULT = 0x10,       // Text
00091         RSA_RESULT = 0x11,       // Text
00092         APPARENT_ADDR = 0x12,    // BIN
00093         REFRESH = 0x13,          // W
00094         DPSTATUS = 0x14,         // W
00095         CALLNO = 0x15,           // W           Max value: IAX2_MAX_CALLNO
00096         CAUSE = 0x16,            // Text
00097         IAX_UNKNOWN = 0x17,      // B
00098         MSGCOUNT = 0x18,         // W
00099         AUTOANSWER = 0x19,       // Null
00100         MUSICONHOLD = 0x1a,      // Text
00101         TRANSFERID = 0x1b,       // DW
00102         RDNIS = 0x1c,            // Text
00103         PROVISIONING = 0x1d,     // BIN
00104         AESPROVISIONING = 0x1e,  // BIN
00105         DATETIME = 0x1f,         // DW
00106         DEVICETYPE = 0x20,       // Text
00107         SERVICEIDENT = 0x21,     // BIN
00108         FIRMWAREVER = 0x22,      // W
00109         FWBLOCKDESC = 0x23,      // DW
00110         FWBLOCKDATA = 0x24,      // BIN
00111         PROVVER = 0x25,          // DW
00112         CALLINGPRES = 0x26,      // B
00113         CALLINGTON = 0x27,       // B
00114         CALLINGTNS = 0x28,       // W
00115         SAMPLINGRATE = 0x29,     // DW
00116         CAUSECODE = 0x2a,        // B
00117         ENCRYPTION = 0x2b,       // B
00118         ENKEY = 0x2c,            // BIN
00119         CODEC_PREFS = 0x2d,      // Text
00120         RR_JITTER = 0x2e,        // DW
00121         RR_LOSS = 0x2f,          // DW
00122         RR_PKTS = 0x30,          // DW
00123         RR_DELAY = 0x31,         // W
00124         RR_DROPPED = 0x32,       // DW
00125         RR_OOO = 0x33,           // DW
00126     };
00127 
00132     inline IAXInfoElement(Type type) : m_type(type) {}
00133 
00137     virtual ~IAXInfoElement() {}
00138 
00143     inline Type type() const
00144         { return m_type; }
00145 
00150     virtual void toBuffer(DataBlock& buf);
00151 
00156     virtual void toString(String& buf);
00157 
00163     static inline const char* ieText(u_int8_t ieCode)
00164         { return lookup(ieCode,s_ieData); }
00165 
00166 
00167 private:
00168     static TokenDict s_ieData[];// Association between IE type and text
00169     Type m_type;                // Type of this IE
00170 };
00171 
00176 class YIAX_API IAXInfoElementString : public IAXInfoElement
00177 {
00178 public:
00185     inline IAXInfoElementString(Type type, const char* buf, unsigned len) : IAXInfoElement(type), m_strData(buf,(int)len)
00186         {}
00187 
00191     virtual ~IAXInfoElementString() {}
00192 
00197     inline int length() const
00198         { return m_strData.length(); }
00199 
00204     inline String& data()
00205         { return m_strData; }
00206 
00211     virtual void toBuffer(DataBlock& buf);
00212 
00217     virtual void toString(String& buf)
00218         { buf << m_strData; }
00219 
00220 private:
00221     String m_strData;           // IE text data
00222 };
00223 
00228 class IAXInfoElementNumeric : public IAXInfoElement
00229 {
00230 public:
00237     IAXInfoElementNumeric(Type type, u_int32_t val, u_int8_t len);
00238 
00242     virtual ~IAXInfoElementNumeric() {}
00243 
00248     inline int length() const
00249         { return m_length; }
00250 
00255     inline u_int32_t data() const
00256         { return m_numericData; }
00257 
00262     virtual void toBuffer(DataBlock& buf);
00263 
00268     virtual void toString(String& buf);
00269 
00270 private:
00271     u_int8_t m_length;          // IE data length
00272     u_int32_t m_numericData;    // IE numeric data
00273 };
00274 
00279 class YIAX_API IAXInfoElementBinary : public IAXInfoElement
00280 {
00281 public:
00288     IAXInfoElementBinary(Type type, unsigned char* buf, unsigned len) : IAXInfoElement(type), m_data(buf,len)
00289         {}
00290 
00294     virtual ~IAXInfoElementBinary() {}
00295 
00300     inline int length() const
00301         { return m_data.length(); }
00302 
00307     inline DataBlock& data()
00308         { return m_data; }
00309 
00314     virtual void toBuffer(DataBlock& buf);
00315 
00321     static IAXInfoElementBinary* packIP(const SocketAddr& addr);
00322 
00329     static bool unpackIP(SocketAddr& addr, IAXInfoElementBinary* ie);
00330 
00335     virtual void toString(String& buf);
00336 
00337 private:
00338     DataBlock m_data;           // IE binary data
00339 };
00340 
00345 class YIAX_API IAXIEList
00346 {
00347 public:
00351     inline IAXIEList() : m_invalidIEList(false)
00352         {}
00353 
00359     inline IAXIEList(const IAXFullFrame* frame, bool incoming = true) : m_invalidIEList(false)
00360         { createFromFrame(frame,incoming); }
00361 
00365     inline ~IAXIEList()
00366         {}
00367 
00372     inline bool invalidIEList() const
00373         { return m_invalidIEList; }
00374 
00378     inline void clear()
00379         { m_list.clear(); }
00380 
00384     void insertVersion();
00385 
00390     inline bool validVersion() {
00391             u_int32_t ver = 0xFFFF;
00392             getNumeric(IAXInfoElement::VERSION,ver);
00393             return ver == IAX_PROTOCOL_VERSION;
00394         }
00395 
00400     inline void appendIE(IAXInfoElement* ie)
00401         { m_list.append(ie); }
00402 
00407     inline void appendNull(IAXInfoElement::Type type)
00408         { m_list.append(new IAXInfoElement(type)); }
00409 
00415     inline void appendString(IAXInfoElement::Type type, const String& src)
00416         { m_list.append(new IAXInfoElementString(type,src.c_str(),src.length())); }
00417 
00424     inline void appendString(IAXInfoElement::Type type, unsigned char* src, unsigned len)
00425         { m_list.append(new IAXInfoElementString(type,(char*)src,len)); }
00426 
00433     inline void appendNumeric(IAXInfoElement::Type type, u_int32_t value, u_int8_t len)
00434         { m_list.append(new IAXInfoElementNumeric(type,value,len)); }
00435 
00442     inline void appendBinary(IAXInfoElement::Type type, unsigned char* data, unsigned len)
00443         { m_list.append(new IAXInfoElementBinary(type,data,len)); }
00444 
00452     bool createFromFrame(const IAXFullFrame* frame, bool incoming = true);
00453 
00458     void toBuffer(DataBlock& buf);
00459 
00465     void toString(String& dest, const char* indent = 0);
00466 
00472     IAXInfoElement* getIE(IAXInfoElement::Type type);
00473 
00480     bool getString(IAXInfoElement::Type type, String& dest);
00481 
00488     bool getNumeric(IAXInfoElement::Type type, u_int32_t& dest);
00489 
00496     bool getBinary(IAXInfoElement::Type type, DataBlock& dest);
00497 
00498 private:
00499     bool m_invalidIEList;       // Invalid IE flag
00500     ObjList m_list;             // The IE list
00501 };
00502 
00507 class YIAX_API IAXAuthMethod
00508 {
00509 public:
00513     enum Type {
00514         Text = 1,
00515         MD5  = 2,
00516         RSA  = 4,
00517     };
00518 
00525     static void authList(String& dest, u_int16_t auth, char sep);
00526 
00527     static TokenDict s_texts[];
00528 };
00529 
00534 class YIAX_API IAXFormat
00535 {
00536 public:
00540     enum Audio {
00541         G723_1 = (1 <<  0),
00542         GSM    = (1 <<  1),
00543         ULAW   = (1 <<  2),
00544         ALAW   = (1 <<  3),
00545         MP3    = (1 <<  4),
00546         ADPCM  = (1 <<  5),
00547         SLIN   = (1 <<  6),
00548         LPC10  = (1 <<  7),
00549         G729A  = (1 <<  8),
00550         SPEEX  = (1 <<  9),
00551         ILBC   = (1 << 10),
00552     };
00553 
00557     enum Video {
00558         JPEG   = (1 << 16),
00559         PNG    = (1 << 17),
00560         H261   = (1 << 18),
00561         H263   = (1 << 19),
00562     };
00563 
00570     static void formatList(String& dest, u_int32_t formats, char sep = ',');
00571 
00577     static inline const char* audioText(u_int32_t audio)
00578         { return lookup(audio,audioData); }
00579 
00585     static inline const char* videoText(u_int32_t video)
00586         { return lookup(video,videoData); }
00587 
00591     static TokenDict audioData[];
00592 
00596     static TokenDict videoData[];
00597 };
00598 
00603 class YIAX_API IAXControl
00604 {
00605 public:
00609     enum Type {
00610         New       = 0x01,
00611         Ping      = 0x02,
00612         Pong      = 0x03,
00613         Ack       = 0x04,
00614         Hangup    = 0x05,
00615         Reject    = 0x06,
00616         Accept    = 0x07,
00617         AuthReq   = 0x08,
00618         AuthRep   = 0x09,
00619         Inval     = 0x0a,
00620         LagRq     = 0x0b,
00621         LagRp     = 0x0c,
00622         RegReq    = 0x0d,
00623         RegAuth   = 0x0e,
00624         RegAck    = 0x0f,
00625         RegRej    = 0x10,
00626         RegRel    = 0x11,
00627         VNAK      = 0x12,
00628         DpReq     = 0x13,
00629         DpRep     = 0x14,
00630         Dial      = 0x15,
00631         TxReq     = 0x16,
00632         TxCnt     = 0x17,
00633         TxAcc     = 0x18,
00634         TxReady   = 0x19,
00635         TxRel     = 0x1a,
00636         TxRej     = 0x1b,
00637         Quelch    = 0x1c,
00638         Unquelch  = 0x1d,
00639         Poke      = 0x1e,
00640         //Reserved  = 0x1f,
00641         MWI       = 0x20,
00642         Unsupport = 0x21,
00643         Transfer  = 0x22,
00644         Provision = 0x23,
00645         FwDownl   = 0x24,
00646         FwData    = 0x25,
00647     };
00648 
00654     static inline const char* typeText(int type)
00655         { return lookup(type,s_types,0); }
00656 
00657 private:
00658     static TokenDict s_types[]; // Keep the association between IAX control codes and their name
00659 };
00660 
00665 class YIAX_API IAXFrame : public RefObject
00666 {
00667 public:
00671     enum Type {
00672         DTMF    = 0x01,
00673         Voice   = 0x02,
00674         Video   = 0x03,
00675         Control = 0x04,
00676         Null    = 0x05,
00677         IAX     = 0x06,
00678         Text    = 0x07,
00679         Image   = 0x08,
00680         HTML    = 0x09,
00681         Noise   = 0x0a,
00682     };
00683 
00693     IAXFrame(Type type, u_int16_t sCallNo, u_int32_t tStamp, bool retrans,
00694              const unsigned char* buf, unsigned int len);
00695 
00699     virtual ~IAXFrame();
00700 
00705     inline Type type() const
00706         { return m_type; }
00707 
00712     inline DataBlock& data()
00713         { return m_data; }
00714 
00719     inline bool retrans() const
00720         { return m_retrans; }
00721 
00726     inline u_int16_t sourceCallNo() const
00727         { return m_sCallNo; }
00728 
00733     inline u_int32_t timeStamp() const
00734         { return m_tStamp; }
00735 
00740     virtual const IAXFullFrame* fullFrame() const;
00741 
00750     static IAXFrame* parse(const unsigned char* buf, unsigned int len, IAXEngine* engine = 0, const SocketAddr* addr = 0);
00751 
00757     static u_int8_t packSubclass(u_int32_t value);
00758 
00764     static u_int32_t unpackSubclass(u_int8_t value);
00765 
00771     static inline const char* typeText(int type)
00772         { return lookup(type,s_types,0); }
00773 
00774 protected:
00778     DataBlock m_data;
00779 
00783     bool m_retrans;
00784 
00785 private:
00786     static TokenDict s_types[]; // Keep the association between IAX frame types and their names
00787     Type m_type;                // Frame type
00788     u_int16_t m_sCallNo;        // Source call number
00789     u_int32_t m_tStamp;         // Frame timestamp
00790 };
00791 
00796 class YIAX_API IAXFullFrame : public IAXFrame
00797 {
00798 public:
00802     enum ControlType {
00803         Hangup = 0x01,
00804         //Ring = 0x02,
00805         Ringing = 0x03,
00806         Answer = 0x04,
00807         Busy = 0x05,
00808         Congestion = 0x08,
00809         FlashHook = 0x09,
00810         Option = 0x0b,
00811         KeyRadio = 0x0c,
00812         UnkeyRadio = 0x0d,
00813         Progressing = 0x0e,
00814         Proceeding = 0x0f,
00815         Hold = 0x10,
00816         Unhold = 0x11,
00817         VidUpdate = 0x12,
00818     };
00819 
00833     IAXFullFrame(Type type, u_int32_t subclass, u_int16_t sCallNo, u_int16_t dCallNo,
00834                  unsigned char oSeqNo, unsigned char iSeqNo,
00835                  u_int32_t tStamp, bool retrans,
00836                  const unsigned char* buf, unsigned int len);
00837 
00850     IAXFullFrame(Type type, u_int32_t subclass, u_int16_t sCallNo, u_int16_t dCallNo,
00851                  unsigned char oSeqNo, unsigned char iSeqNo,
00852                  u_int32_t tStamp,
00853                  const unsigned char* buf = 0, unsigned int len = 0);
00854 
00858     virtual ~IAXFullFrame();
00859 
00864     inline u_int16_t destCallNo() const
00865         { return m_dCallNo; }
00866 
00871     inline unsigned char oSeqNo() const
00872         { return m_oSeqNo; }
00873 
00878     inline unsigned char iSeqNo() const
00879         { return m_iSeqNo; }
00880 
00885     inline u_int32_t subclass() const
00886         { return m_subclass; }
00887 
00892     virtual const IAXFullFrame* fullFrame() const;
00893 
00901     void toString(String& dest, const SocketAddr& local, const SocketAddr& remote,
00902         bool incoming) const;
00903 
00909     static inline const char* controlTypeText(int type)
00910         { return lookup(type,s_controlTypes,0); }
00911 
00912 private:
00913     static TokenDict s_controlTypes[]; // Keep the association between control types and their names
00914     u_int16_t m_dCallNo;        // Destination call number
00915     unsigned char m_oSeqNo;     // Out sequence number
00916     unsigned char m_iSeqNo;     // In sequence number
00917     u_int32_t m_subclass;       // Subclass
00918 };
00919 
00924 class YIAX_API IAXFrameOut : public IAXFullFrame
00925 {
00926 public:
00942     inline IAXFrameOut(Type type, u_int32_t subclass, u_int16_t sCallNo, u_int16_t dCallNo,
00943                        unsigned char oSeqNo, unsigned char iSeqNo, u_int32_t tStamp, const unsigned char* buf, unsigned int len,
00944                        u_int16_t retransCount, u_int32_t retransInterval, bool ackOnly)
00945         : IAXFullFrame(type,subclass,sCallNo,dCallNo,oSeqNo,iSeqNo,tStamp,buf,len),
00946           m_ack(false), m_ackOnly(ackOnly), m_retransCount(retransCount), m_retransTimeInterval(retransInterval),
00947           m_nextTransTime(Time::msecNow() + m_retransTimeInterval)
00948         {}
00949 
00953     virtual ~IAXFrameOut()
00954         {}
00955 
00960     inline bool timeout() const
00961         { return m_retransCount == 0; }
00962 
00968     inline bool timeForRetrans(u_int64_t time) const
00969         { return time > m_nextTransTime; }
00970 
00974     void setRetrans();
00975 
00979     void transmitted();
00980 
00985     inline bool ack() const
00986         { return m_ack; }
00987 
00991     inline void setAck()
00992         { m_ack = true; }
00993 
00998     inline bool ackOnly() const
00999         { return m_ackOnly; }
01000 
01005     void adjustAuthTimeout(u_int64_t nextTransTime);
01006 
01007 private:
01008     bool m_ack;                         // Acknoledge flag
01009     bool m_ackOnly;                     // Frame need only ACK as a response
01010     u_int16_t m_retransCount;           // Retransmission counter
01011     u_int32_t m_retransTimeInterval;    // Retransmission interval
01012     u_int64_t m_nextTransTime;          // Next transmission time
01013 };
01014 
01019 class YIAX_API IAXMetaTrunkFrame : public RefObject, public Mutex
01020 {
01021 public:
01027     IAXMetaTrunkFrame(IAXEngine* engine, const SocketAddr& addr);
01028 
01032     virtual ~IAXMetaTrunkFrame();
01033 
01038     inline const SocketAddr& addr() const
01039         { return m_addr; }
01040 
01045     inline u_int32_t timestamp()
01046         { return m_timestamp; }
01047 
01052     void setTimestamp(u_int32_t tStamp);
01053 
01061     bool add(u_int16_t sCallNo, const DataBlock& data, u_int32_t tStamp);
01062 
01068     bool send(u_int32_t tStamp);
01069 
01070 private:
01071     u_int8_t* m_data;           // Data buffer
01072     u_int16_t m_dataAddIdx;     // Current add index
01073     u_int32_t m_timestamp;      // Frame timestamp
01074     IAXEngine* m_engine;        // The engine that owns this frame
01075     SocketAddr m_addr;          // Remote peer address
01076 };
01077 
01083 class YIAX_API IAXTransaction : public RefObject, public Mutex
01084 {
01085     friend class IAXEvent;
01086     friend class IAXEngine;
01087 public:
01091     enum Type {
01092         Incorrect,                      // Unsupported/unknown type
01093         New,                            // Media exchange call
01094         RegReq,                         // Registration
01095         RegRel,                         // Registration release
01096         Poke,                           // Ping
01097         //FwDownl,
01098     };
01099 
01103     enum State {
01104         Connected,                      // Call leg established (Accepted) for transactions of type New
01105         NewLocalInvite,                 // New outgoing transaction: Poke/New/RegReq/RegRel
01106         NewLocalInvite_AuthRecv,        // Auth request received for an outgoing transaction
01107         NewLocalInvite_RepSent,         // Auth reply sent for an outgoing transaction
01108         NewRemoteInvite,                // New incoming transaction: Poke/New/RegReq/RegRel
01109         NewRemoteInvite_AuthSent,       // Auth sent for an incoming transaction
01110         NewRemoteInvite_RepRecv,        // Auth reply received for an incoming transaction
01111         Unknown,                        // Initial state
01112         Terminated,                     // Terminated. No more frames accepted
01113         Terminating,                    // Terminating. Wait for ACK or timeout to terminate
01114     };
01115 
01125     static IAXTransaction* factoryIn(IAXEngine* engine, IAXFullFrame* frame, u_int16_t lcallno, const SocketAddr& addr,
01126                 void* data = 0);
01127 
01137     static IAXTransaction* factoryOut(IAXEngine* engine, Type type, u_int16_t lcallno, const SocketAddr& addr,
01138                 IAXIEList& ieList, void* data = 0);
01139 
01143     virtual ~IAXTransaction();
01144 
01149     inline IAXEngine* getEngine() const
01150         { return m_engine; }
01151 
01156     inline Type type() const
01157         { return m_type; }
01158 
01163     inline State state() const
01164         { return m_state; }
01165 
01170     inline u_int64_t timeStamp() const
01171         { return Time::msecNow() - m_timeStamp; }
01172 
01177     inline bool outgoing() const
01178         { return m_localInitTrans; }
01179 
01184     inline void setUserData(void* data)
01185         { m_userdata = data; }
01186 
01191     inline void* getUserData() const
01192         { return m_userdata; }
01193 
01198     inline u_int16_t localCallNo() const
01199         { return m_lCallNo; }
01200 
01205     inline u_int16_t remoteCallNo() const
01206         { return m_rCallNo; }
01207 
01212     inline const SocketAddr& remoteAddr() const
01213         { return m_addr; }
01214 
01219     inline const String& username()
01220         { return m_username; }
01221 
01226     inline const String& callingNo()
01227         { return m_callingNo; }
01228 
01233     inline const String& callingName()
01234         { return m_callingName; }
01235 
01240     inline const String& calledNo()
01241         { return m_calledNo; }
01242 
01247     inline const String& calledContext()
01248         { return m_calledContext; }
01249 
01254     inline const String& challenge()
01255         { return m_challenge; }
01256 
01261     inline u_int32_t format()
01262         { return m_format; }
01263 
01268     inline u_int32_t formatIn()
01269         { return m_formatIn; }
01270 
01275     inline u_int32_t formatOut() const 
01276         { return m_formatOut; }
01277 
01282     inline u_int32_t capability() const
01283         { return m_capability; }
01284 
01289     inline u_int32_t expire() const
01290         { return m_expire; }
01291 
01296     inline const String& authdata()
01297         { return m_authdata; }
01298 
01305     IAXTransaction* processFrame(IAXFrame* frame);
01306 
01314     IAXTransaction* processMedia(DataBlock& data, u_int32_t tStamp, bool voice = false);
01315 
01322     IAXTransaction* sendMedia(const DataBlock& data, u_int32_t format);
01323 
01330     IAXEvent* getEvent(u_int64_t time);
01331 
01336     static unsigned char getMaxFrameList();
01337 
01343     static bool setMaxFrameList(unsigned char value);
01344 
01350     inline bool sendAnswer()
01351         { return sendConnected(IAXFullFrame::Answer); }
01352 
01358     inline bool sendRinging()
01359         { return sendConnected(IAXFullFrame::Ringing); }
01360 
01366     inline bool sendProgress()
01367         { return sendConnected(IAXFullFrame::Proceeding); }
01368 
01376     bool sendAccept();
01377 
01385     bool sendHangup(const char* cause = 0, u_int8_t code = 0);
01386 
01394     bool sendReject(const char* cause = 0, u_int8_t code = 0);
01395 
01401     bool sendAuth();
01402 
01409     bool sendAuthReply(const String& response);
01410 
01417     inline bool sendDtmf(u_int8_t dtmf)
01418         { return dtmf <= 127 ? sendConnected((IAXFullFrame::ControlType)dtmf,IAXFrame::DTMF) : false; }
01419 
01426     bool sendText(const char* text);
01427 
01434     inline bool sendNoise(u_int8_t noise)
01435         { return noise <= 127 ? sendConnected((IAXFullFrame::ControlType)noise,IAXFrame::Noise) : false; }
01436 
01442     bool abortReg();
01443 
01449     bool enableTrunking(IAXMetaTrunkFrame* trunkFrame);
01450 
01454     void print();
01455 
01459     static String s_iax_modNoAuthMethod;
01460 
01464     static String s_iax_modNoMediaFormat;
01465 
01469     static String s_iax_modInvalidAuth;
01470 
01474     static String s_iax_modNoUsername;
01475 
01476 protected:
01486     IAXTransaction(IAXEngine* engine, IAXFullFrame* frame, u_int16_t lcallno, const SocketAddr& addr,
01487         void* data = 0);
01488 
01498     IAXTransaction(IAXEngine* engine, Type type, u_int16_t lcallno, const SocketAddr& addr, IAXIEList& ieList,
01499         void* data = 0);
01500 
01505     void init(IAXIEList& ieList);
01506 
01513     bool incrementSeqNo(const IAXFullFrame* frame, bool inbound);
01514 
01520     bool isFrameAcceptable(const IAXFullFrame* frame);
01521 
01527     bool changeState(State newState);
01528 
01537     IAXEvent* terminate(u_int8_t evType, bool local, const IAXFullFrame* frame = 0, bool createIEList = true);
01538 
01546     IAXEvent* waitForTerminate(u_int8_t evType, bool local, const IAXFullFrame* frame);
01547 
01558     void postFrame(IAXFrame::Type type, u_int32_t subclass, void* data = 0, u_int16_t len = 0, u_int32_t tStamp = 0,
01559                 bool ackOnly = false);
01560 
01567     bool sendFrame(IAXFrameOut* frame, bool vnak = false);
01568 
01577     IAXEvent* createEvent(u_int8_t evType, bool local, const IAXFullFrame* frame, State newState);
01578 
01590     IAXEvent* createResponse(IAXFrameOut* frame, u_int8_t findType, u_int8_t findSubclass, u_int8_t evType, bool local, State newState);
01591 
01598     IAXEvent* getEventResponse(IAXFrameOut* frame, bool& delFrame);
01599 
01606     IAXEvent* getEventResponse_New(IAXFrameOut* frame, bool& delFrame);
01607 
01613     IAXEvent* processAuthReq(IAXEvent* event);
01614 
01621     IAXEvent* processAccept(IAXEvent* event);
01622 
01628     IAXEvent* processAuthRep(IAXEvent* event);
01629 
01636     IAXEvent* getEventResponse_Reg(IAXFrameOut* frame, bool& delFrame);
01637 
01643     IAXEvent* processRegAck(IAXEvent* event);
01644 
01651     IAXEvent* getEventStartTrans(IAXFullFrame* frame, bool& delFrame);
01652 
01659     IAXEvent* getEventRequest(IAXFullFrame* frame, bool& delFrame);
01660 
01667     IAXEvent* getEventRequest_New(IAXFullFrame* frame, bool& delFrame);
01668 
01675     IAXFullFrame* findInFrame(IAXFrame::Type type, u_int32_t subclass);
01676 
01684     bool findInFrameTimestamp(const IAXFullFrame* frameOut, IAXFrame::Type type, u_int32_t subclass);
01685 
01691     bool findInFrameAck(const IAXFullFrame* frameOut);
01692 
01696     void ackInFrames();
01697 
01705     bool sendConnected(IAXFullFrame::ControlType subclass, IAXFrame::Type frametype = IAXFrame::Control);
01706 
01711     void sendAck(const IAXFullFrame* frame);
01712 
01716     void sendInval();
01717 
01721     void sendVNAK();
01722 
01727     void sendUnsupport(u_int32_t subclass);
01728 
01735     IAXEvent* processInternalOutgoingRequest(IAXFrameOut* frame, bool& delFrame);
01736 
01743     IAXEvent* processInternalIncomingRequest(const IAXFullFrame* frame, bool& delFrame);
01744 
01751     IAXEvent* processMidCallControl(const IAXFullFrame* frame, bool& delFrame);
01752 
01759     IAXEvent* processMidCallIAXControl(const IAXFullFrame* frame, bool& delFrame);
01760 
01767     IAXEvent* remoteRejectCall(const IAXFullFrame* frame, bool& delFrame);
01768 
01774     IAXEvent* getEventTerminating(u_int64_t time);
01775 
01781     IAXTransaction* processVoiceFrame(const IAXFullFrame* frame);
01782 
01788     IAXTransaction* retransmitOnVNAK(u_int16_t seqNo);
01789 
01794     IAXEvent* internalAccept();
01795 
01801     IAXEvent* internalReject(String& reason);
01802 
01808     void eventTerminated(IAXEvent* event);
01809 
01815     inline IAXEvent* keepEvent(IAXEvent* event) {
01816         m_currentEvent = event;
01817         return event;
01818     }
01819 
01820 private:
01821     // Params
01822     bool m_localInitTrans;                      // True: local initiated transaction
01823     bool m_localReqEnd;                         // Local client requested terminate
01824     Type m_type;                                // Transaction type
01825     State m_state;                              // Transaction state
01826     u_int64_t m_timeStamp;                      // Transaction creation timestamp
01827     u_int32_t m_timeout;                        // Transaction timeout (in seconds) on remote termination request
01828     SocketAddr m_addr;                          // Socket
01829     u_int16_t m_lCallNo;                        // Local peer call id
01830     u_int16_t m_rCallNo;                        // Remote peer call id
01831     unsigned char m_oSeqNo;                     // Outgoing frame sequence number
01832     unsigned char m_iSeqNo;                     // Incoming frame sequence number
01833     IAXEngine* m_engine;                        // Engine that owns this transaction
01834     void* m_userdata;                           // Arbitrary user data
01835     u_int32_t m_lastFullFrameOut;               // Last transmitted full frame timestamp
01836     u_int16_t m_lastMiniFrameOut;               // Last transmitted mini frame timestamp
01837     u_int32_t m_lastMiniFrameIn;                // Last received mini frame timestamp
01838     u_int16_t m_lastAck;                        // Last ack'd received frame's oseqno
01839     Mutex m_mutexInMedia;                       // Keep received media thread safe
01840     IAXEvent* m_pendingEvent;                   // Pointer to a pending event or 0
01841     IAXEvent* m_currentEvent;                   // Pointer to last generated event or 0
01842     // Outgoing frames management
01843     ObjList m_outFrames;                        // Transaction & protocol control outgoing frames
01844     u_int16_t m_retransCount;                   // Retransmission counter. 0 --> Timeout
01845     u_int32_t m_retransInterval;                // Frame retransmission interval
01846     // Incoming frames management
01847     ObjList m_inFrames;                         // Transaction & protocol control incoming frames
01848     static unsigned char m_maxInFrames;         // Max frames number allowed in m_inFrames
01849     // Call leg management
01850     u_int32_t m_pingInterval;                   // Ping remote peer interval
01851     u_int64_t m_timeToNextPing;                 // Time of the next Ping
01852     // Statistics
01853     u_int32_t m_inTotalFramesCount;             // Total received frames
01854     u_int32_t m_inOutOfOrderFrames;             // Total out of order frames
01855     u_int32_t m_inDroppedFrames;                // Total dropped frames
01856     // Data
01857     IAXAuthMethod::Type m_authmethod;           // Authentication method to use
01858     String m_username;                          // Username
01859     String m_callingNo;                         // Calling number
01860     String m_callingName;                       // Calling name
01861     String m_calledNo;                          // Called number
01862     String m_calledContext;                     // Called context
01863     String m_challenge;                         // Challenge
01864     String m_authdata;                          // Auth data received with auth reply
01865     u_int32_t m_expire;                         // Registration expiring time
01866     u_int32_t m_format;                         // Media format used for initial negotiation
01867     u_int32_t m_formatIn;                       // Incoming media format
01868     u_int32_t m_formatOut;                      // Outgoing media format
01869     u_int32_t m_capability;                     // Media capability of this transaction
01870     // Meta trunking
01871     IAXMetaTrunkFrame* m_trunkFrame;            // Reference to a trunk frame if trunking is enabled for this transaction
01872 };
01873 
01878 class YIAX_API IAXEvent
01879 {
01880     friend class IAXTransaction;
01881     friend class IAXConnectionlessTransaction;
01882 public:
01886     enum Type {
01887         Invalid = 0,            // Invalid frame received
01888         Terminated,             // Transaction terminated
01889         Timeout,                // Transaction timeout
01890         NotImplemented,         // Feature not implemented
01891         New,                    // New remote transaction
01892         AuthReq,                // Auth request
01893         AuthRep,                // Auth reply
01894         Accept,                 // Request accepted
01895         Hangup,                 // Remote hangup
01896         Reject,                 // Remote reject
01897         Busy,                   // Call busy
01898         Text,                   // Text frame received
01899         Dtmf,                   // DTMF frame received
01900         Noise,                  // Noise frame received
01901         Answer,                 // Call answered
01902         Quelch,                 // Quelch the call
01903         Unquelch,               // Unquelch the call
01904         Progressing,            // Call progressing
01905         Ringing,                // Ringing
01906     };
01907 
01912     ~IAXEvent();
01913 
01918     inline Type type() const
01919         { return m_type; }
01920 
01925     inline bool local() const
01926         { return m_local; }
01927 
01932     inline bool final() const
01933         { return m_final; }
01934 
01938     inline void setFinal()
01939         { m_final = true; }
01940 
01946     inline u_int8_t frameType()
01947         { return m_frameType; }
01948 
01953     inline u_int32_t subclass()
01954         { return m_subClass; }
01955 
01960     inline IAXEngine* getEngine() const
01961         { return m_transaction ? m_transaction->getEngine() : 0; }
01962 
01967     inline IAXTransaction* getTransaction() const
01968         { return m_transaction; }
01969 
01974     inline void* getUserData() const
01975         { return m_transaction ? m_transaction->getUserData() : 0; }
01976 
01981     inline IAXIEList& getList()
01982         { return m_ieList; }
01983 
01984 protected:
01994     IAXEvent(Type type, bool local, bool final, IAXTransaction* transaction, u_int8_t frameType = 0, u_int32_t subclass = 0);
01995 
02004     IAXEvent(Type type, bool local, bool final, IAXTransaction* transaction, const IAXFullFrame* frame = 0);
02005 
02006 private:
02007     inline IAXEvent() {}                // Default constructor
02008 
02009     Type m_type;                        // Event type
02010     u_int8_t m_frameType;               // Frame type
02011     u_int32_t m_subClass;               // Frame subclass
02012     bool m_local;                       // If true the event is generated locally, the receiver MUST not respond
02013     bool m_final;                       // Final event flag
02014     IAXTransaction* m_transaction;      // Transaction that generated this event
02015     IAXIEList m_ieList;                 // IAXInfoElement list
02016 };
02017 
02022 class YIAX_API IAXEngine : public DebugEnabler, public Mutex
02023 {
02024 public:
02040     IAXEngine(const char* iface, int port, u_int16_t transListCount, u_int16_t retransCount, u_int16_t retransInterval,
02041         u_int16_t authTimeout, u_int16_t transTimeout, u_int16_t maxFullFrameDataLen,
02042         u_int32_t format, u_int32_t capab, u_int32_t trunkSendInterval, bool authRequired);
02043 
02048     virtual ~IAXEngine();
02049 
02056     IAXTransaction* addFrame(const SocketAddr& addr, IAXFrame* frame);
02057 
02065     IAXTransaction* addFrame(const SocketAddr& addr, const unsigned char* buf, unsigned int len);
02066 
02073     virtual void processMedia(IAXTransaction* transaction, DataBlock& data, u_int32_t tStamp)
02074         {}
02075 
02081     bool process();
02082 
02087     inline u_int16_t retransCount() const
02088         { return m_retransCount; }
02089 
02094     inline u_int16_t retransInterval() const
02095         { return m_retransInterval; }
02096 
02101     inline bool authRequired() const
02102         { return m_authRequired; }
02103 
02108     inline u_int16_t authTimeout() const
02109         { return m_authTimeout; }
02110 
02115     inline u_int32_t transactionTimeout() const
02116         { return m_transTimeout; }
02117 
02122     inline u_int16_t maxFullFrameDataLen() const
02123         { return m_maxFullFrameDataLen; }
02124 
02129     inline u_int32_t format() const
02130         { return m_format; }
02131 
02136     inline u_int32_t capability() const
02137         { return m_capability; }
02138 
02143     void readSocket(SocketAddr& addr);
02144 
02153     bool writeSocket(const void* buf, int len, const SocketAddr& addr, IAXFullFrame* frame = 0);
02154 
02158     void runGetEvents();
02159 
02165     void removeTransaction(IAXTransaction* transaction);
02166 
02172     u_int32_t transactionCount();
02173 
02178     void keepAlive(SocketAddr& addr);
02179 
02186     virtual bool voiceFormatChanged(IAXTransaction* trans, u_int32_t format)
02187         { return false; }
02188 
02194     bool acceptFormatAndCapability(IAXTransaction* trans);
02195 
02200     virtual void defaultEventHandler(IAXEvent* event);
02201 
02206     void enableTrunking(IAXTransaction* trans);
02207 
02212     void removeTrunkFrame(IAXMetaTrunkFrame* metaFrame);
02213 
02217     void runProcessTrunkFrames();
02218 
02223     inline Socket& socket()
02224         { return m_socket; }
02225 
02232     static void getMD5FromChallenge(String& md5data, const String& challenge, const String& password);
02233 
02240     static bool isMD5ChallengeCorrect(const String& md5data, const String& challenge, const String& password);
02241 
02242 protected:
02248     bool processTrunkFrames(u_int32_t time = Time::msecNow());
02249 
02256     virtual void processEvent(IAXEvent* event);
02257 
02264     IAXEvent* getEvent(u_int64_t time);
02265 
02270     u_int16_t generateCallNo();
02271 
02276     void releaseCallNo(u_int16_t lcallno);
02277 
02286     IAXTransaction* startLocalTransaction(IAXTransaction::Type type, const SocketAddr& addr, IAXIEList& ieList, bool trunking = false);
02287 
02288 private:
02289     Socket m_socket;                            // Socket
02290     ObjList** m_transList;                      // Full transactions
02291     ObjList m_incompleteTransList;              // Incomplete transactions (no remote call number)
02292     bool m_lUsedCallNo[IAX2_MAX_CALLNO + 1];    // Used local call numnmbers flags
02293     int m_lastGetEvIndex;                       // getEvent: keep last array entry
02294     // Parameters
02295     bool m_authRequired;                        // Automatically request authentication
02296     int m_maxFullFrameDataLen;                  // Max full frame data (IE list) length
02297     u_int16_t m_startLocalCallNo;               // Start index of local call number allocation
02298     u_int16_t m_transListCount;                 // m_transList count
02299     u_int16_t m_retransCount;                   // Retransmission counter for each transaction belonging to this engine
02300     u_int16_t m_retransInterval;                // Retransmission interval default value in miliseconds
02301     u_int16_t m_authTimeout;                    // Timeout (in seconds) of acknoledged auth frames sent
02302     u_int32_t m_transTimeout;                   // Timeout (in seconds) on remote request of transactions
02303                                                 //  belonging to this engine
02304     // Media
02305     u_int32_t m_format;                         // The default media format
02306     u_int32_t m_capability;                     // The media capability
02307     // Trunking
02308     Mutex m_mutexTrunk;                         // Mutex for trunk operations
02309     ObjList m_trunkList;                        // Trunk frames list
02310     u_int32_t m_trunkSendInterval;              // Trunk frame send interval
02311 };
02312 
02313 }
02314 
02315 #endif /* __YATEIAX_H */
02316 
02317 /* vi: set ts=8 sw=4 sts=4 noet: */