PCBest Networks SIP SDK

OS Requirement: (If you need SDK version which doesn't depend on DirectX lib for server-side applications, please contact us at http://www.pcbest.net)
WIN 2008/Windows 7/8/9/10/11
WIN Server 2008, 2012, 2016, 2022

For WIN 2003, WINXP, Please use our 32bit SDK only.

For old systems, as we are compiling our samples on .NET 4.6, please contact us if you still need supports for the following:
WIn2000
Win98 and Me

Mem 2G +
CPU: Core2Duo +

If you are using activex control in bin folder, the ocx is required to be registered before you use it. 
Command to register: regsvr32 gtsipctrl.ocx.
Under Windows 7, you need run your command line "As Administrator" to register an ActiveX.

Version History:

version 3.10 2025-01-12
1. Upgraded our compiler to Visual Studio 2022, including all samples provided.
2. Added support for OpenAI Realtime API

version 3.03 2024-11-15
1. Added support for SIPS and SRTP

-- 3.02 2023-10-28
1. Fixed the problem with Windows server licensing

---3.01a 2022-03-10
1. Fixed the issue for g722 codec 64bit
2. Enhanced Opus codec
3. Added RAD Studio C++ Builder XE8 samples for softphone and server

---3.01 2021-11-23
1. Addessed an issue with multiple private IP addresses within same NAT


---3.00b 2021-03-18
1. Fixed a call connection issue with device Patton SN200/2JS2V (VIA branch related)

---3.00a 2021-02-07
1. Many customers reported that they are still running their applications on Win2003 server and XP, 
so we have recompiled our SDK to XP compatible on 32bit SDK only.

2. Added DotNetLibs for different versions of .NET Frameworks
You will just need to copy the GTAPIASM.dll into bin folder, then compile your .NET app referenced to it, with correspending .NET framework setting in 'Application' project properties.


---3.00 2021-01-20
1. Moved compiling tool to VS2015 completely. 
.NET samples are compiling against to .NET Framework 4.6. 
For WinXP and Windows 2003 users, if you need support, please contact us.

---2.10m 2020-12-18
1. Fixed an issue when holding but still transmitting the RTP
2. Fixed an issue with special gateway which SDK doesn't detect DTMF.

---2.10l 2020-04-22
1. Fixed a Via header from AareSwitch/6.10.11775 that can't be recgonized.
2. Fixed a bug with raw file recording.

---2.10k 2020-02-18
1. Fixed a crash issue with Ascom phone


---2.10j 2019-11-23
1. Fixed an issue with 64bit environment

---2.10i 2019-04-02
1. Fixed an issue with reinvite to different audio codec it is supposed to be.


---2.10h 2018-11-05
Some minor bug fixes.

---2.10g 2018-09-24
1. Fixed the problem with set speaker and microphone level
2. Found a stack overflow issue with new logging, fixed.
3. Fixed a problem with speaker and microphone vloume adjuster

---2.10f 2018-04-23
1. Fixed an issue with to-tag in PRACK

---2.10e 2018-01-31
1. Improved logging.
2. Multiple SIP accounts for a NAT issue.

---2.10d 2017-03-18
1. Improved log for setting number of log files
"gtsrv.log.file.number"

Sometimes you may need to set the log files to more than 10, so you can download them from data center easily with smaller size.
You can use this tag to set how many log files you want.


---2.10c 2017-02-23
1. Fixed a possible issue that a null pointer is passed into proxy subscrible module to cause it unstable

---2.10b 2016-08-30
1. Added one tag "gtsrv.sip.min.inband.audio.dtmf.dur" for setting the minimal inband DTMF tone length for DTMF detection.
The default value is 120ms. You can set it to 40ms plus, but remeber, the lower value, the more sensitive it could be, so lower value might cause false detection.

---2.10 2016-06-07
1. 64bit supports for the SDK
2. Some interfaces changed in order to support 64bit

---2.06 2016-01-26
1. Fixed couple of bugs with SIP TCP
2. Added On_RecvOfferedEx event to retrive the whole SIP INVITE message
Description: Event to notify a new incoming call. This event is only triggered for a new inbound call. Note, please override only one of this event and On_RecvOffered.
Format:
C++: void On_RecvOfferedEx(int ch, const char* sCaller, const char* sCallee, const char* sDestAddr, const char* sViaAddr, const char* sFromIP, unsigned short nFromPort , const char* sOrgSIPTxt, const char* Reserved1, const char* Reserved2, const char* Reserved3)
.NET: void On_RecvOfferedEx(int ch, string sCaller, string sCallee, string DestAddr, string sViaAddr, string sFromIP, unsigned short nFromPort, string sOrgSIPTxt, const string Reserved1, string Reserved2, string Reserved3)
OCX: void OnCallOfferedEx(int ch, BSTR sCaller, BSTR sCallee, BSTR sDestAddr, BSTR sViaAddr, BSTR sFromIP, unsigned short nFromPort, BSTR sOrgSIPTxt, BSTR Reserved1, BSTR Reserved2, BSTR Reserved3)
DLL: void GTAPI_SetCB_On_RecvOfferedEx
Parameters:
Ch: Channel Index
sCaller: Caller ID. It equals to SIP From field.
sCallee: Called ID. It equals to SIP To field.
sDestAddr: Call destination address. It equals to SIP Uri field.
sViaAddr: Call via address. It equals to the most top via address in SIP message.
sFromIP: the ip address that SIP message is from.
sFromPort: the ip port that SIP message is from.
sOrgSIPTxt: the original SIP message in pure text
Reserved1, Reserved2, Reserved3: for future usuage
Return:
null
Sample code:
//Softphone code. Play local ring tone in sound card to mention users that there is a new incoming call
Void On_RecvOfferedEx(int ch, ...)
{
PlayLocalRingSound(); 
}


---2.05w5
1. Added GetRemotePartyID and SetRemotePartyID functions
2. Added TCP support.

---2.05w4, 2015-11-08
1. Added function SetChanAudioDir to force incoming or send only audio.

---2.05w3
1. A small patch for cseq method for BYE message.

---2.05w2
1. Added callback function for getting RTP raw packet.
2. A small patch for cancelling call without setting to-tag in ringing
3. A fix for reaching "Too Many Hops" in Proxy model.
4. An enhancement for Reinvite detecting RTP source. 


---2.05w1
1. Added support for PRACK
Enable this feature by setting "gtsrv.sip.use.prack" to 1.

2. Enhanced SIP Presence message event

3. Enhancement for sipgate.de reinivte


---2.05v
1. Added two more parameters for ProxySetUserInfo, so the user can set the proxy extension's original SIP FROM and TO info even extension is not really registered on the system.
const char* from_id : the original SIP FROM in Register message, usually it is something like Mike<sip:101@192.168.1.100>.
const char* to_id : the most of case, it is the same as from_id.

With this two more functions, users can develop a Proxy server and sending MWI messages to specific extensions even they are not registering on local SIP server/proxy.

We can call it MWI server/service.


---2.05u
1. Added support for g722
2. Added a bug with record-route

---2.05t
1. Fixed a race condition for CANCEL and OK
2. Added a tag "gtsrv.sip.rtp.port.space" for setting the RTP space of each channel

---2.05s
1. Introduced a new tag to control max time of a call conversation in stack.
"gtsrv.sip.max.dlg.duration"
Defaultly it is 21600 seconds(6 hours).
You can set it to 0, for unlimited.


---2.05r
1. Added SIPAccount_Register function for manual register and unregister a sip accont
2. Found an issue with memory queue which causes ActiveX application crash on starting. Fixed.
3. Fixed an issue with remote present private contact address.


---2.05q
1. Fixed a private and public IP mix, and using public but no sound issue.
2. Removed extra string in SIP user agent name
3. Added two new functions for setting DTMF type in runtime

void GTAPI_SetChanDTMFType(int ch, unsigned int dtmfType); ////dtmf type: 0 = in audio //1 = sip info //2 = rtp //3 = auto
unsigned int GTAPI_GetChanDTMFType(int ch);


---2.05p
1. Added two more functions

//Proxy connect two channels. When two channels are proxy connected, the actual media(audio) is bypassed between 2 far ends.
static void Send_ProxyConnect(int ch1, int ch2);
static void Send_ProxyDisconnect(int ch1, int ch2);

2. Enhanced answering machine beep detection.

---2.05o3
Optiomized SDK by these ways:
1. Changed way of internal communication from TCP to Memory Queue
2. Reduced memory use of each channel in order to hold more channels in system


---2.05o2
1. Enhanced with DNS SRV.
Just try to enable:
CFG_SetValue("gtsrv.sip.enable.dns.srv", "1");

2. Fixed an issue with Nortel SIP phone device.
It has an extra tag in FROM:
From: <sip:6083@10.50.20.70:5060>;tag=a19c3028-11fa280a-13c4-55013-66aad4-28a124ff-66aad4;user=phone

Fixed similar problem for TO also.


3. Fixed an issue with Send_MakeEx not setting DestIP and DestPort

4. Added two functions for license info operation.
//get the hardware information
string GetLicHWInfo(string sAppName, string sKey, int nChanNum, string sMAC);

//license file name to save the validated info
string GetLicFileName(string sAppName);

---2.05o1
1. Fixed a problem with cancelling call.


---2.05o
1. Fixed a problem with call transferring, for Asterisk 1.8.
2. Fixed a problem with session progress no content in first package
3. Support 302 server side, by using Send_HangupEx
So when a new call arrive, 
On_RecvOffered(int ch, ....)
{
Send_HangupEx(ch, 302, "Moved Moved Temporarily Contact: <sip:newaddr@newdomain.com>");
}

---2.05n

1. Added the following two functions
const char* GT_API GTAPI_GetPChargingVector(int ch);
void GT_API GTAPI_SetPChargingVector(int ch, const char* p);

2. Fixed an issue with sending DTMF inband

3. Added extra contact info in On_RecvIdle for 3xx disconnect.


---2.05m
1. Added SIP BLF support for Proxy API
//direction can be set to  recipient , "initiator", or just "".
//state can be set to:
//"confirmed" ===> connected
//"early" ===> ringing
//"terminated" or "void" ===> idle

//pid: proxy site index, usually it is 0

//username: extension name
void ProxyUpdateUserState(unsigned int pid, const char* username, const char* direction, const char* state);


How to use this function?

For example, your proxy application has defined 101, 102, 103 ... extensions.

When 101 call state changes(when you direct a call to it, or it calls out), you should call this function like:

ProxyUpdateUserState(0, "101", "recipient", "early"); //an incoming call to 101, ringed, but not answered.


If other extensions have requested the state monitoring(BLF) for 101, they will be notified.

2. Fixed a registration issue with AudioCodes MP118 FXS gateway when working as Proxy server model.



---2.05l
1. fixed an issue with multiple public ip address and private ip address issue.
2. Added code for trying and ringing timeout for OnRecvIdle event.

---2.05k
1. Fixed a multiple local IP address and multiple SIP application running on different IP issue.


---2.05j
1. Added one more parameter authid for On_ProxyNewCallSession for marking the real authrization id.
2. Added option for if proxy server send OPTIONS ping to proxy clients to indentify status.
"gtsrv.sip.proxy.site1.check.user.status" default is false(0). Set it to 1 to enable it.


---2.05i
1. Enhancement on Human and Answering machine detection.
2. Sloved a crash problem with g729
3. Fixed a bug for GetRenderDeviceCount and GetCaptureDeviceCount

---2.05h
1. Made SDK compatible with Andriod Linphone client.
2. Fixed an issue of sip account with non-5060 port.
3. Fixed sip cancel to-tag issue. Added tag "gtsrv.sip.get.totag.from.ring.for.cancel" to control the case.

---2.05g
1. Fixed a possible logging crash issue.


---2.05f
1. Added two methods:
a. Send_WaitForCall(ch)
Some people prefer to allow inbound call only after calling a funciton WaitForCall.
In default, SDK send the new incoming call into a channel when it is(turning into) IDLE. But if you prefer waitForCall mode to accept new call, 
you can "gtsrv.wait.for.call.mode" to 1 before startServer, then call this function after channel is IDLE.

b. SetChanDir(ch, dir)
dir: 1 = inbound call only, 2 = outbound call only, 3 = both(default)
You can use this function to set some channels do inbound calls only or outbound calls only or both.

2. Fixed an issue channel could possibly turning to unrecoverable status connecting.


---2.05e
1. Add option(gtsrv.sip.keep.alive.msg) to disable KeepAliveMsg
2. Add option(gtsrv.sip.get.remote.contact.from.ring) to suit some gateways and SIP servers.
Some GWs or SIP servers only recognize the SIP URI in Ring or SessionProgress they give when cancelling a call.
Other only recognize the initial SIP URI in SIP INVITE when cancelling a call even they give a different SIP contact address in ring, or session progress.
In order to be compatible to both behaviors, this option is added.
Default it is FALSE(0). You can set it to TRUE(1) if you are having problem to cancel an outbound call.


---2.05d
1. Solved a re-invite missing OK issue.

---2.05c
1. Fixed a register problem with Cisco SBC
2. Added On_SIPMsg event for .NET interface

---2.05b
Samples enhancement, and document enhancement.

---2.05a
1. Added support for Cisco 7940 phone
2. Fixed a re-invite problem with Alcatel oxo server.
3. Fixed an issue with freephonie.net's Cirpack/v4.42q (gw_sip)

---2.05
1. Added Send_StopAudioEx. Please refer to the SDK API doc 3.8.7.
2. Added Send_ConfStopAudioEx. Please refer to the SDK API doc 3.11.6.
3. Resolved a call cancell issue when 183 has record_route.

---2.04g
1. Fixed an issue when there is only speaker, but no microphone but the client still wants to use softphone feature.
2. Fixed in above situation, the DTMF doesn't work.


---2.04f
1. Fixed an issue when asnwering the call, but it is cancelled at the same time.
2. Fixed an issue for no-audio event in call holding or holded status.


---2.04e
1. Fixed an issue when holding a call on channel 1, call on channel 2, but channel 1 can hear channel 2's voice. This issue were ONLY affecting softphone.
2. Fixed the SDP Session owner version issue for Asterisk servers. Before that, we have to enable  ignoresdpversion  feature on Asterisk PBX.

---2.04d
1. Enhancement on performance.


---2.04c
1. Solved a wav format issue
2. Fixed a reinvite RTP re-open issue


---2.04b
1. Added P_Asserted_Identity header for SIP message.
2. Uses From or RequestURI ID as SIP contact address if possible.
3. Fixed an issue with OnSessionProgress. When receiving multiple 183 messages. It would try to re-open the RTP.


---2.04a
1. Crash bug fixed in a very rare situation.

---2.04
1. Use CSharpSIPPhone instead of CSharpSimplePhone sample.
2. Use VBSIPPhone instead of VBSimplePhone sample.


---2.03h
1. Fixed transfer issue with AudioCode, Matrix, and Sangoma GW
2. Added sending 487 after "OK" when cancelling call as some devices expecting "OK" first then 487.


---2.03g
1. Bug fix.

---2.03f
1. Made sdk work with snom 300, although it is because snom 300 doesn't generate right SIP message.
2. SIP INFO DTMF detection work with northwind gateway.

---2.03e
1. Fixed a problem when calling sip address without specifying caller id.
2. Fixed a problem for incoming calls when there are multiple sip accounts with same sip domain.

---2.03d
1. Fixed MessageTextDelivered issue when remote is not reachable
2. Fixed return code when remote GW is turned off
3. Fixed Win7 and Win2k8 issue with .NET interface SetChanUserStr and GetChanUserStr
4. Fixed the remote contact detection issue when using Send_MakeEx. 
If pass remote URI, or remote ip address in to Send_MakeEX, the SDK will not learn remote contact, and will not send following SIP message to this contact addres.
This fixed issue for proxy server, when sometimes softphone cannot figure out correct public ip and port in contact address.


---2.03c
1. Re-organized samples folder.
2. Added a tag "gtsrv.sip.callcontrol.handle.3xx" to control if the SDK should automatically deal with SIP 3xx message.
3. Fixed an issue about RTP SSRC when setting up RTP Duplex after call is connected.


---v2.03b
1. bug fixes


---v2.03a
1. Added two more parameters for Send_MakeEx.

static void Send_MakeEx(int ch, const char* sCallee, const char* sCaller, const char* sURI, const char* sContact, const char* sAuthName, const char* sAuthPassword, const char* sDestIP = 0, unsigned short nDestPort = 0);
sDestIP: Destionation IP Address
nDestPort: Destionation IP Port

2. Added three more parameters for On_ProxyUserRegistered
void On_ProxyUserRegistered(unsigned int pid, const char* username, time_t tnow, unsigned int exp_sec, const char* org_contact, const char* mapped_contact, const char* szUAName, int UANatType, const char* szFromID, const char* szToID, const char* saddr, unsigned short nport)
org_contact: contact address showing in REGISTER message
mapped_contact: mapped contact address that SDK figured out by using REGISTER source IP and port. If it is "", then org_contact is alright, and matching.
saddr: REGISTER Message source IP address
nport: REGISTER Message source IP port

3. Added three more parameters for ProxySetUserInfo
void ProxySetUserInfo(unsigned int pid, const char* username, const char* passwd, time_t regt, unsigned int regex, const char* org_contact, const char* mapped_contact, const char* uaname, int nattype, const char* src_ip, unsigned short src_port);
org_contact: contact address showing in REGISTER message
mapped_contact: mapped contact address that SDK figured out by using REGISTER source IP and port. If it is "", then org_contact is alright, and matching.
src_ip: REGISTER Message source IP address
src_port: REGISTER Message source IP port


---v2.03
1. Added function SetChanCallExtraSIPHeader.
Some customers need to add customized special header in SIP INVITE message
This function is added to make this possible.
void SetChanCallExtraSIPHeader(int ch, const char* s);
ch: Channel ID
s: header string

NOTE: You need to use this function before Send_Make or Send_MakeEx is called every time.

2. Fixed SIP account proxy settings.
Here is something may cause confused.
As Send_Make and Send_MakeEX doesn't have a parameter saying if it should use SIP account to dialout, so SDK has to determine it by FROM and To header.
If From or To header matches one of the SIP accounts, SDK will use it as. So if this SIP account's proxy server address is different than domain, then the call may be directed to somewhere else.

3. Fixed a CSeq issue with Cisco.
SDK syncronized the CSeq with remote, but the fact is that it is local value.
This issue has been fixed.

4. Fixed some issues with DirectX FullDuplex buffer, also license key validation part is enhanced.

---v2.02c
Fixed license issue

---v2.02b
1. Fixed a re-open RTP port issue in Windows7 OS

---V2.02a
1. Fixed memory leak for GTSIPCtrl.ocx(SDK's ActiveX interface).


2. Added one function for setting audio format of conference room
Send_ConfSetAudioFormat
Please see API document for the format of this function

---v2.02
1. Added one interface to control channel's volume of sound
SetChanAudioLevel(int ch, float inLevel, float outLevel);
ch: channel index
inLevel: inbound sound level. defaultly it is 1.00, so there is no any change.
outlevel: outbound sound level. defaultly it is 1.00, so there is no any change.

2. Fix the compability issue with Asterisk 1.6 on hold/unhold.
Issue was:
All SIP messages are sent with SDP Owner Username: -, Session ID: 0, Session Version: 0.
There is many changes from Asterisk 1.4 to Asterisk 1.6, one of them is about SDP package versions; 
Asterisk 1.6 is more bit strict and require version data on SDP, but expose a configuration parameter for disable this behavior by enabling  ignoresdpversion  feature on Asterisk PBX.



---v2.01

1. Sloved attendent transfering issue with Aastra MX-ONE server.


---v2.00

1. Added video features for SDK, including the following functions:


SQCIF 128   96
QCIF 176   144
CIF = 352x288
4CIF 704   576 
16CIF 1408   1152 

QVGA = 320x240 
VGA = 640x480 


"gtsrv.sip.prefered.video.codec"



2. Can set the sound device by index (Softphone SDK)
The index is from 0. The following code set the second device as speaker, and microphone.
CFG_SetValue("gtsrv.sip.dxsound.device.playback", "1");
CFG_SerValue("gtsrv.sip.dxsound.device.capture", "1");

3. Added SIPAccount_Enable function to enable/disable a SIP account

4. Added an event for SIP messages
void On_SIPMsg(int dir, const char* src_ip, unsigned short src_port, \
		const char* dest_ip, unsigned short dest_port, char* buf, int len)
dir: 0 = incoming, 1 = outgoing
src_ip: message from ip address
src_port: message from ip port
dest_ip: message to ip address
dest_port: message to ip port
buf: sip message buffer
len: message length in bytes

NOTE: IN ORDER TO TRIGGER THIS EVENT, YOU NEED TO SET "gtsrv.sip.on.msg" TO "1".

5. Added an event for proxy user subscribed on the system
void On_ProxyUserSubscribed(unsigned int pid, const char* fromid, const char* toid, const char* suri, const char* via, const char* callid, \
		const char* saddr, unsigned short nport)
pid: proxy id
fromid, toid, suri, via, callid: SIP message info element
saddr: message source ip
nport: message source port

6. Added a new function to set channel's output when in conference room
void SetChanConfMask(int ch, unsigned int bitMask);
This function is used to disable the chan's output voice to other channels in the same conference.
Default channel mask is always 0xFFFFFFFF, which means output to all other channels in the conference room.
Every bit marks a channel. If the bit is 1, its voice can output to the channel. 
The First channel in the conference room is 0x01.
The second channel in the conference room is 0x02.
The third channel in the conference room is 0x04.
So if you want the channel's output goes to the first channel, and the third channel, you can set this for this channel:
SetChanConfMaskch, 0x05); //which 0x05 = 0x01 + 0x04

Another example, 
1st channel is connected with Agent.   (Channel Index is 0, and it is the first channel set to the conference room)
2nd channel is connected with Customer. (Channel Index is 1, and it is the second channel set to the conference room)
3rd channel is suppervisor. (Channel Index is 2, and it is the third channel set to the conference room)
they are all in the same conference room. Regularly if don't set anything, they can hear eachother.
if supervisor only wants the agent hear his voice, not the customer, you can do so:
SetChanConfMask(2, 0x01);
it means that only the first channel get his voice.

7. Solved issue with Windows 7 reopen RTP socket on re-invite
8. Solved issue with Windows 7 when somethimes re-open the internal TCP listening port

9. Added a tag to disable dynamically checking remote RTP sender address.
gtsrv.sip.dyn.check.remote.rtp
Defaultly it is 1 = enabled. 
Set it to 0 means disable checking

10. Added a tag to set public ip address instead of using STUN
sometimes if your machine is on DMZ, then you can set this tag.
gtsrv.sip.public.ip.in.rtp
Set it to "" = not enabled
Set it to "0" will always let SDK to use public ip address in SIP SDP.
See it to "209.223.21.33" as using this public ip address

11. Fix a bug for "gtsrv.sip.dtmf.key.duration" settting for inband audio when playing DTMF string
Bug orginal case: When using inband audio DTMF mode with the code below, the actual length of the tones is 160 ms:

var t = (DtmfTone) tone;
this.environment.CFG_SetValue("gtsrv.sip.dtmf.key.duration", "100");
this.environment.Send_PlayDTMFStr(connection.Channel, t.Tone);
this.environment.ProcessGTApiEvents();



---v1.73c
1. changed Send_HungUp to Send_HangUp
old:
static void Send_HungUp(int ch);

new:
static void Send_HangUp(int ch, int code, const char* desc);

2. On_RecvIdle format changed
Old:
void On_RecvIdle(int ch);

new:
Void On_RecvIdle(int ch, int code, const char* desc);


---v1.73
1. #define GTSIP_RTP_PORT_SPACE 2
2. changed event format for On_ProxyUserRegistered
virtual void On_ProxyUserRegistered(unsigned int pid, const char* username, time_t tnow, unsigned int exp_sec, const char* contact, const char* szUAName, 
int UANatType, const char* szFromID, const char* szToID){}
3. Change the way to set Proxy users.
a. delete the functions
GetProxyUserValid
GetProxyUserPassword
GetProxyUserRegTime
GetProxyUserRegExpire
GetProxyUserContact
GetProxyUserUAName
GetProxyUserNATType
b. Added three functions:
void ProxySetUserInfo(unsigned int pid, const char* username, const char* passwd, time_t regt, unsigned int regex, const char* contactaddr, const char* uaname, int nattype);
void ProxySetUserMsg(unsigned int pid, const char* username, bool bMsgWait, const char* sMsgAcct, int cnt1, int cnt2, int cnt3, int cnt4);
void ProxyDisableAllUsers(unsigned int pid);

4.added "gtsrv.lic.file.dir" tag for setting license file directory

5. added virtual function for SIP message
	virtual void			On_SIPMsg(int dir, const char* src_ip, unsigned short src_port, \
		const char* dest_ip, unsigned short dest_port, char* buf, int len){}

6. Fixed license problem for multiple NIC.

7. GetChanLastMsgText will return whole message data

8. Fixed a bug in composing Via header in SIP message

9. Added last_msg_time flag for under-layer sip_dialog
The SDK driver will check if the dialog is more than 6 hours
if it does, then remove it from dialog list


---v1.72g
1. Add a tag to control max proxy client can register on
"gtsrv.sip.proxy.max.user.reg.expire"

2. added two functions to associate user string data with channel.
	bool SetChanUserStr(int chan_id, int data_idx, const char* s)
	const char* GetChanUserData(int chan_id, int data_idx)

---v1.72f 
1. fixed a DTMF detection problem with PlayAudio

---v1.72e
1. First version move all code to VC8
2. Add two functions to associate user data with channel.
	bool SetChanUserData(int chan_id, int data_idx, unsigned long d)
	bool GetChanUserData(int chan_id, int data_idx, unsigned long* d)



---v1.72d

1. Fixed a bug with Replaces header in INVITE message
2. Automatically answered the call with INVITE replaces

---v1.72c
1. Added an event to indicate if Send_MessageText was successful
void On_RecvMessageTextDelivered(int ch, int msg_code, const char* msg_txt)
ch: chan id. (also can be message id. It is the same id you passed into Send_MessageText)
msg_code: 200 is OK(Successful). others are not successful.
msg_txt: massage decription.

2. Added sound device(speakers and microphones) Enumerate functions

	static unsigned int GetRenderDeviceCount();
	static const char* GetRenderDeviceName(int idx);
	static GT_BOOL	IsRenderDevicePrimary(int idx);

	static unsigned int GetCaptureDeviceCount();
	static const char* GetCaptureDeviceName(int idx);
	static GT_BOOL	IsCaptureDevicePrimary(int idx);

3. Added Send_TransferEx for attended transfer



---v1.72b
1. Enhancement on DTMF sending(RFC2833)
2. Enhancement on channel efficiency
3. Enhancement on ACK message for 3CX PBX
4. Enhancement for WAVE devices
5. Always send Keep-alive message no matter if it is in NAT or not, or if it is set to use NAT address in SIP
6. fixed a problem to choose a IP address from multiple local ip address.
7. Fixed the wrong contact info in OK message for Register.
8. Added OnRecvNotifyPresence and OnRecvMessageText for OCX

---v1.72a

1. Add attended trasnfer feature.
2. Fixed the problem with SIP Message Challenge.
3. Fixed the problem when remote ptime > 20ms in SDP
4. On_RecvTransfering changed interface from:
void On_RecvTransfering(int ch, const char* sAddr)
to:
void On_RecvTransfering(int ch, const char* sAddr, const char* sReplaceCallID, const char* sReplaceFromTag, const char* sReplaceToTag)
5. Added three new functions for getting SIP call id, from-tag, and to-tag.
const char* GetChanCallID(int ch);
const char* GetChanCallFromTag(int ch);
const char* GetChanCallToTag(int ch);
6. Added a tag to disable process priority settings
Tag name: gtsrv.set.process.priority
Default value: 1 (Enable)
Other value: 0 (Disable)
If this tag is 1(default), then SDK will try set your application process priority level to REALTIME_PRIORITY_CLASS. 
7. Four more functions added to operate the mute status of speaker and microphone
void SetSpeakerMuteStatus(GT_BOOL bMute);
GT_BOOL GetSpeakerMuteStatus();
void SetMicMuteStatus(GT_BOOL bMute);
GT_BOOL GetMicMuteStatus();
8. Solved the problem with SendGetStatus in OCX
9. Solved the problem when calling out, the channel's status is RESERVED.
10. fixed a bug when using SIPAccount_Remove, it doesn't unregister the account.
11. Fixed a problem with SIP Account Subscribe
12. fixed a problem with register multiple bindlings

---v1.72
1. Add a tag to set if polling rtp
"gtsrv.sip.rtp.poll"
1 = use a seperate thread to poll RTP data
0 = no polling

2. Add a tag "gtsrv.sip.dx.session.progress" to control the directx sound when received OnSessionProgress event.
1 = open 0 = no
so "gtsrv.sip.server.model" can be three values:
0 = softphone model
1 = server model
2 = mixed application model
when you set the application model to 1(server model), but you open directX sound in your application to work with sound card, your application model will be set to 2 now. 
(before it will set back to 0 softphone model).
If you want to open directx sound in model 1 and 2, you have to set "gtsrv.sip.dx.session.progress" to 1.

3. Fixed a bug for unregistering when sdk stop

4. Fixed a bug with DTMF key buffer resetting

5. Fixed the license issue with the new one

6. Fixed the ring timeout when session-progress

7. Fixed the problem with blind-transfer

---v1.71f
1. Add the process for multiple SIP message in one UDP or TCP package
2. Add the UDP Relay general logic in the core
3. Add RTPDuplexConnect and RTPDuplexDisconnect commands for RTP relay
4. Add a tag "gtsrv.sip.reg1.retry.interval" to control re-register SIP account interval.
5. Add a tag "gtsrv.sip.dtmf.key.duration" to control DTMF tone duration.
6. Add checking for internal communication tcp port before opens it in StartServer function.
7. Add checking SIP UDP port in StartServer function.
8. Add an event to indicate the recording file name of DX channels.
On_RecvDXAudioStatus(int ch, int status, const char* fn)
ch: channel id
status: 1 == recording just started
fn: file full path name
After call is disconnected(you received IDLE event on this channel), you can use the file name to do some post process for recording file.
9. Add a new recording function for 2 way recording on channel
Send_RecordAudio2
10. Add audio functions for conference room
void Send_ConfPlayAudio(int conf, const char* audioFileName, int iMaxDigit, const char* termStr, int iMaxTimer, unsigned int uStartByte);
void Send_ConfRecordAudio(int conf, const char* audioFileName, int iMaxDigit, const char* termStr, int iMaxTimer, unsigned int uStartByte);
void Send_ConfRecordAudio2(int conf, const char* audioFileName, int iMaxDigit, const char* termStr, int iMaxTimer, unsigned int uStartByte);
void Send_ConfAddAudio(int conf, const char* pAudioName, unsigned int uBeginByte);
void Send_ConfClearAudio(int conf);
void Send_ConfStopAudio(int conf);
void Send_GetConfAudioStatus(int conf);
11. Also add three events for conference audio status
void On_RecvConfAudioStatus(int conf, int resType, int statusCode, unsigned long bytesDone);
void On_RecvConfAudioPlayDone(int conf, int doneReason, const char* dtmfBuffer);
void On_RecvConfAudioRecordDone(int conf, int doneReason, const char* dtmfBuffer);
12. Add On_RecvSessionProgress for 183 session progress SIP response.
Also, RTP media can be accessed by On_RecvRTPPackage event when On_RecvSessionProgress event is triggered.
14. Four new dynamical conference functions are added
GT_HANDLE CreateConf();
void	DestroyConf(GT_HANDLE h);
GT_BOOL SetChanInConf(GT_HANDLE h, int ch, int bAdd);
int		GetConfIndex(GT_HANDLE h);
15. Support conference monitoring
GT_BOOL SetChanInConf(GT_HANDLE h, int ch, int bAdd);
void Send_SetChanInConference(int conf, int ch, int bAdd);
when bAdd = 2, the chan can monitor the conference, but cannot speak in conference
16. added a tag for default dtmf payload setting
"gtsrv.sip.default.dtmf.payload"
If you don't set it, the sdk use 106 as default DTMF payload type for dialing out.
17. Change above "gtsrv.sip.default.dtmf.payload" to 101, and also move iLBC 30ms and 20ms code 104, and 103.
18. Improved the performance by doing so:
a. Make dynamic memory allocation to static at a lot of places
b. Improve the perfermance of some low level threads
c. Change the timer structure from Centerized Timer to channel-based Timer
d. Rewrite RTP stack to a fast and efficient one
e. Make threading model on span (Not opening a thread for each channel)
19. Add tone detection Interfaces:
//Tone Handle
	static void Send_ClearToneList(int ch);
	static void Send_AddTone(int ch, int freq, int duration);
	static void Send_StartToneDetection(int ch);
	static void Send_StopToneDetection(int ch);
	virtual void On_RecvToneDetected(int ch, int freq){}

20. Also control the VAD for each channel
//VAD
	static void Send_EnableVAD(int ch);
	static void Send_DisableVAD(int ch);

21. Add a tag to control if mapping SIP address for proxy site
"gtsrv.sip.proxy.site1.map.reg.source"

22. Fixed sending inband 'A', 'B', 'C' and 'D' DTMF tones.

23. Add six functions for dynamically manage SIP accounts
GT_HANDLE SIPAccount_Add(const char* dp_name, const char* username, const char *domain, const char* proxy,
		const char* authorization, const char *password, int expire, GT_BOOL bReg, int maxSimultaneousCalls, int retryInterval);
void SIPAccount_Remove(GT_HANDLE h);
int SIPAccount_Count();
int SIPAccount_Index(GT_HANDLE h);
GT_HANDLE SIPAccount_Handle(int idx);
const char* SIPAccount_Get(int idx, int type); //type = 0 display name 1 = username 2 = domain  3 = proxy  4 = authorization 5 = password

24. Add outbound call GUI for SIPServerApp(in three different source code C++, vb.net and vb source)

---v1.71e
1. Fixed a deal-lock bug.

---v1.71d
1. Fixed a bug with playing .wav and .au files.


---v1.71c
1. Fixed a bug with sending DTMF on RFC2833

2. audio driver settings, default 1
tag: "gtsrv.sip.audio.driver"
0 = WMME
1 = DirectSound
2 = ASIO
3 = WASAPI
4 = WDMKS
**** this feature is not enabled in 1.71c

3. audio channel settings for input(capture) and output(playback).
tag: "gtsrv.sip.audio.capture.channels"
can be 1, or 2

tag: "gtsrv.sip.audio.playback.channels"
can be 1, or 2
**** this feature is not enabled in 1.71c

---v1.71b
1. Rewrote the AGC functions.
These two tags can be set to 8000 - 32767
"gtsrv.dx.play.agc.level"
"gtsrv.dx.capture.agc.level"

2. Fixed a problem when server not responds to INVITE

3. Fixed a bug in recording feature.

4. Fixed a DTMF detection bug
The bug was:
When DTMF method is set to auto, and if not using ALAW or MULAW to communication, random DTMF may be presents by SDK.

5. Added On_RecvNoAudio event for stop receiving RTP incoming package.
void On_RecvNoAudio(int ch, int)
{
	//channel ch is not having rtp incoming audio	
}

"gtsrv.sip.no.audio.duration" is used to control the no audio duration event.

---v1.71a
1. Add "Human or answer machine detection" feature.
tags:
set "gtsrv.human.detect.enabled" to 1
also set "gtsrv.sip.on.in.vad" to 1

There are two thresholds,
"gtsrv.human.detect.duration" means how many milliseconds totally to detect the human or machine after call is connected. Defaultly it is 4000 (4 seconds)
"gtsrv.human.detect.voiceon" means milliseconds threshold for first sentence length. If the first setence is less than this threshold, it is considered as a human voice, otherwise it is machine. defaultly it is 2000 (2 seconds)

An event On_DetectHumanVoiceDone will be triggered.
void On_DetectHumanVoiceDone(int ch, int result)
ch: Channel Index, from 0
result: 
0 = Answering Machine
1 =  Human voice
-1 = silence (no voice at all in the "gtsrv.human.detect.duration" milliseconds.)
-2 = detected voice, but unknown because "gtsrv.human.detect.duration" is reached.

2. Add a function to get the channel recording file name when using clientphone recording feature. (set tag "gtphone.audio.record.enabled" to 1)
const char* GetChanAudioRecordFileName(int ch);
ch: Channel Index
Note: please using this function after the call is connected, or call is just idle. You only can operate(move, rename, or mp3 process) the file after the call is idle.
Sample code:
void On_RecvConnected(int ch)
{
	Send_StartDXAudio(ch);
        GetChanAudioRecordFileName(ch);
}

or 
void On_RecvIdle(int ch)
{
	const char* srcFileName = GetChanAudioRecordFileName(ch);
	MoveFile(srcFileName, destFileName);
}



---v1.71
1. *** Audio interfaces changed. 
Add one more parameter for the following four functions for C++ and .NET interfaces. The parametre is the byte offset where you want to play or record audio.

PlayAudio
RecordAudio
AddAudio
On_RecvAudioStatus

2. Added call signal proxy to under layer.

3. GetSoundDeviceCount and GetSoundDeviceName are added to popular sound device list

4. ProxySetNewCallSessionAddr is added to return transfered call address later in a proxy call mode.

5. Improvement on conference audio quality

6. 3xx redirect are enabled to client phone application

7. Fix a RTP problem when two ends are in same symmetric router.

8. A bug fixed in VAD interfaces.

9. Memory leak fixed.

10. Add two functions for channel status
static void Send_SetChanStatus(int ch, int status);
//use this function to mannually set channel status. Be caution to use this function.
//Channel status could be:
// 0 = GT_CALL_IDLE,
// 1 = GT_CALL_DIALING,
// 2 = GT_CALL_RINGING,
// 3 = GT_CALL_OFFERED,
// 4 = GT_CALL_CONNECTING,
// 5 = GT_CALL_CONNECTED,
// 6 = GT_CALL_DISCONNECTING,
// 7 = GT_CALL_RELEASING,
// 8 = GT_CALL_NOT_AVAILABLE,  //When span is not up
// 9 = GT_CALL_OFF_LINE,   // when resource is limited
// 10 = GT_CALL_MARKED_BUSY, //when mannually marked busy or maint
// 11 = GT_CALL_RESERVED, //reserved 

static void Send_GetChanStatus(int ch);
// to get the status of a channel
// this function will triger a On_RecvStatus event.

11. Fix a problem with SIP From and TO header for server: sip.xs4all.nl

12. Fixed Call-ID problem in Register message for some servers.

13. Fixed resend subscribe problem when previous expiered.

14. Fixed compatibility to simplecall.net

15. Set default "gtsrv.dx.record.buf.len" from 640(ms) to 80(ms)

16. Fixed a problem with hungup when holding call is not completed

17. Add two tags for DirectX AGC(Automatic Gain Control) process

"gtsrv.dx.play.agc.level"
"gtsrv.dx.capture.agc.level"

the agc level is the percent of max volume for the sound buffer. 
The valid range is 0.5f to 1.0f, but the recomended range is 0.8f to 0.95f. At 1.0f, some clipping might be experienced.

18. Add support for RTP address "0.0.0.0"

19. Reduce the volume of ring, call and busy tone for softphone interfaces.


---V1.70d
1. Improvement on JitterBuffer for server application
2. Add realtime memory management and timer function in the GTAPI_FACE2.h for C++ programmer
3. On_SendRTPPacket is moved to the right place which can be trigered even there is not outgoing traffic(audio).


---V1.70c
1. Improvement on audio delay and quality


---V1.70b
1. Added two new functions to GTSIPCtrl.ocx control. These two functions are for web developers who want to use encrypted settings in their JavaScript or VBScript.
BSTR EncryptStr(LPCTSTR SourceStr, LPCTSTR KeyStr1, LPCTSTR KeyStr2)
SourceStr: source string to be encrypted.
KeyStr1: First Key to encrypt
KeyStr2: Second Key to encrypt

CFGSetValueEx(LPCTSTR sKey, LPCTSTR sValue)
sKey: configuration key
sValue: encrypted string

Please see the word document "How to encrypt your JavaScript code when using ocx in web page.doc" in doc folder for details.

2. Improved audio quality on delay.

3. Fixed crash on unlicensed software after running one hour.

4. Added demo in SIPServerApp for Conference and Voice Activity Detection


---V1.70a

1. Added server function to redirect calls
First Set "gtsrv.sip.callcontrol.auto.ringcall" = 0
Then use Send_Redirect in On_RecvOffered function.

Send_Redirect(int ch, const char* redirectTo, const char* respCode, const char* respText);
ch: channel number
redirectTo: redirect SIP address. must be format like: "<sip:123@abc.com>"
respCode and respText cab be the following value:

"300" "Multiple Choices"
"301" "Moved Permanently"
"302" "Moved Temporarily"
"305" "Use Proxy"
"380" "Alternative Service"

Sample to redirect a call to "123@abc.com"
Send_Redirect(ch, "<sip:123@abc.com>", "302", "Moved Temporarily");


2. Conference support
In order to use conference feature. You must set "gtsrv.sip.conference.room" to the number of conference room.
Then use the following functions to start and stop conference rooms.

void Send_StartConference(int conf)
conf: conference room index, from 0.

void Send_StopConference(int conf)
conf: conference room index, from 0.

void Send_SetChanInConference(int conf, int ch, int bAdd);
conf: conference room index, from 0.
ch: channel number from 0. If it is -1, then add or remove DXSound from conference room.
bAdd: 1 = Add this channel to conference room. 0 = Remove this channel from conference room.


---V1.70 beta
1. Add an event function(callback) to detect voice activity on channels.
Set "gtsrv.sip.on.in.vad" to 1 if you want to detect incoming voice
Set "gtsrv.sip.on.out.vad" to 1 if you want to detect outgoing voice

virtual void On_VoiceActivityDetected(int ch, int voice_dir, int voice_on, int level, unsigned int reserved)
ch: Channel id
voice_dir: 1 = incoming, 0 = outgoing
voice_on: 1 = voice, 0 = silence
level: voice energy level. Always 0 now.
reserved: not used.


---V1.66
1. Added two more functions for call control on answering call side
Send_Accept	==  Send SIP trying to remote side
Send_Answer     ==  Send SIP ringing to remote side

Usually these two functions will be invoked by SDK automatically.
If you are developing a SIP server, you may need to use these two functions in On_CallOffered event to manually send message.
You need to set 
"gtsrv.sip.callcontrol.auto.acceptcall" = 0
"gtsrv.sip.callcontrol.auto.ringcall" = 0
to disable SDK to automatically accept and answer calls.


2. Added support for SIP/Presence

Use CFG_SetValue to turn on SIP "SUBSCRIBE" message for presence:
"gtsrv.sip.reg1.subscribe" = "1" 				//default it is 0(off)
"gtsrv.sip.reg1.subscribe.addr" = "123@sipproxy.com" 		//You can specify multiple address. 
								//like "123@sipproxy.com;456@sipproxy.com;789@sipproxy.com"

"gtsrv.sip.reg1.subscribe.expire" = 600 			//default it is 600, 10 minutes.
"gtsrv.sip.reg1.subscribe.accept" = 0				//0 = pidf(default),  1 = dialog-info

Two more events for subscribe and notify presence.
void On_RecvSubscribeStatus(int id, int status, int regtime);
id : sip account profile id, from 0
status: 1 = successfully subscribe, 0 = failed
regtime: seconds to subscribe

void On_RecvNotifyPresence(int id, const char* subscription_state, const char* content_type, const char* content_info)
id : sip account profile id, from 0
subscription_state: from SIP Notify message, it is "active" usually.
content_type: from SIP Notify message, can be "application/dialog-info+xml", or "application/pidf+xml"
content_info: real xml content

3. Added support for SIP/Message for instant message

Add the following event for incoming instant message
void On_RecvMessageText(int ch, const char* sFrom, const char* sTo, const char* sDestAddr, const char* sViaAddr, const char* sContent)
ch: channel index, from 0. if it is -1. the message is not attached to any exist call sessions.
sFrom: message from
sTo: message to
sDestAddr: message is for
sViaAddr: message via
sContent: message content

Method Send_MessageText is for sending out simple message
void Send_MessageText(int ch, const char* msgfrom, const char* msgto, const char* content)
ch: set -1 for reserved info
msgfrom: message from sip address. format is : <sip:abc@def.com>
msgto: message to sip address. format is : <sip:abc@def.com>
content: instant message. for example: "Watson, come here."

4. Fix a problem with NAT ip address

5. Fix a bug with RFC 2833(DTMF). Bug was SDK generates duplicated DTMF events.

6. Send_EnableDTMF(int ch) changed to Send_EnableDTMF(int ch, int iMaxDigit, const char* termStr, int iMaxTimer)
iMaxDigit: max digits to detect. set it to 0 with no limitation.
termStr: if the detected dtmf is in termStr, it will stop DTMF detection. null("") string means no any term digits. sample: "#", "#12", "#*"
iMaxTimer: maxium timeout in milliseconds. 0 =  no timeout.

7. Nine new functions are added into Env Class, also to .NET and OCX interfaces.

int GetLocalIPCount(); //Get All local IP counts

const char* GetLocalIP(int idx); //Get local IP address

const char* GetSIPAddressInfo(int flag, const char* sipAddr); 
//strip username, domain, and port from SIP address.
flag: 0 = display name, 1 = username, 2 = domain, 3 = port

bool GT_API StopSound(); //It is used to stop local ring, remote ring, and busy sound

//peer node infomation
const char* GetPeerSIPIPAddress(int ch);  //get peer sip ip address
unsigned short GetPeerSIPIPPort(int ch);  //get peer sip ip port
const char* GetPeerRTPIPAddress(int ch);  //get peer rtp ip address
unsigned short GetPeerRTPIPPort(int ch);  //get peer rtp ip port
const char* GetPeerSIPContactAddress(int ch); //get peer sip contact address

8. If rtp range doesn't start from even number. SDK will make it even.

---V1.65d
1. Changed default VAD mode from ON to OFF.
Old: Default "gtsrv.sip.vad.enabled" is 1
New: Default "gtsrv.sip.vad.enabled" is 0 

2. Added GetLicTo function to GTAPIASM::GTAPIEnv (.NET) class.

3. Added keep-alive package for non-proxy(no sip account) IP Internet calls.


---V1.65c

1. Fixed compatibility problems with CallCentric and Vonage.
2. Fixed a registration timeout issue.


---V1.65

1. Added support for RFC 2883. (DTMF in RTP)

2. Resolved problem with SIP CANCEL and ACK after call is ringing.
	This problem is introduced from 6.4 (Maybe. I think.)



---V1.64
1. Fixed a bug for Audio Recording feature of SIP client phone.
When set "gtphone.audio.record.enabled" to 1 to enable automatical audio recording, the WAV file couldn't be played by Windows Media Player. 
Now this bug is fixed. The wav files can be played by WMP.

2. SDK can play 8K Mono 16Bit PCM, 8Bit Mulaw, 8Bit Alaw wav files now. 
SDK was only able to play 8K 8Bit Mulaw wav files.

3. Added "Music On Hold" feature to all interfaces, also in sample code "SIPServerApp".

4. a Delph6 sample is added into SDK.
It is in folder sdk/samples/ocx/delphi6.

5. On_SentRTPPacket, On_RenderDXAudio, On_CaptureDXAudio now accept the buffer from application.
Those functions were used to send audio buffer to application, but they now also accept the change of buffer.
If you changed the buffer of On_SentRTPPacket and On_CaptureDXAudio, the audio will be taken effect to remote side.
If you changed the buffer of On_RenderDXAudio, the audio will has effect on local sound card.


---V1.63
1. Added a sample for Borland C++ Build 6.

2. Removed Allow SIP Header from SIP Request.

3. Fixed a bug with 183 - Session Progress.
Old code doesn't release RTP port and DX audio in some cases when 183 message occures.

4. Added four virtual functions for .NET class GTAPIASM.GTAPIEnv to access low level layer audio data.(See V1.53 comments for how to use these functions.)
virtual void On_RecvRTPPacket(int ch, int fmt, IntPtr buf, int buflen, unsigned short seq, unsigned int timestamp, IntPtr  pSysTime)
virtual void On_SentRTPPacket(int ch, int fmt, IntPtr  buf, int buflen, unsigned short seq, unsigned int timestamp, IntPtr  pSysTime)
virtual void On_CaptureDXAudio(int ch, int fmt, IntPtr buf, int buflen, unsigned short seq, unsigned int timestamp, IntPtr  pSysTime)
virtual void On_RenderDXAudio(int ch, int fmt, IntPtr buf, int buflen, unsigned short seq, unsigned int timestamp, IntPtr pSysTime)

****Import Notice**** for using above four functions in .NET program.
If you enable those functions, you will get these functions triggered every 20 milliseconds. 
Because the thread to trigger those functions is low level thread of Span, you can NOT access any Windows GUI functions to update your Windows status. (for example, update text value of edit or static.)
You have to do a very fast job to copy buffer to your local, then start your process.

How to copy buffer from native code to .NET managed code?
Please see the link http://www.wit-igraph.com/doc/prog/apps/engine/vbc/mem.htm
or sample source code in GTAPIASM project.


5. Added two methods and one event for chan's timer. (C++, OCX, .NET)
void					StartTimer(int ch, unsigned long milli_secs);
void					StopTimer(int ch);
virtual void			OnTimer(int ch);

How to use it?
Start a timer by using StartTimer function, then handle it on OnTimer function.

6. Added two methods for retrieving code and text of lastest SIP message.
C++ CGTAPIEnv class:
	int GetChanLastMsgCode(int ch);
	const char* GetChanLastMsgText(int ch);
.NET GTAPIASM::GTAPIENV
	int GetChanLastMsgCode(int ch);
	string GetChanLastMsgText(int ch);
OCX ActiveX Control:
	int GetChanLastMsgCode(int ch);
	BSTR GetChanLastMsgText(int ch);

These methods are good for getting the reason of unsuccessful outbound calls.
Sample: 
	On_RecvIdle(int ch)  //OnCallIdle(int ch) in OCX
{
	if(outbound call)
	{
		//if the call didn't even get connected and it isn't cancelled by user
		int msgCode = GetChanLastMsgCode(ch);
		if(msgCode == 486) //busy
	}
	else(inbound call)
	{
		//if the call didn't even get connected and it isn't cancelled by user
		//then it is a missed call
	}
}

The value list of GetChanLastMsgCode is defined in RFC 3261.
for example:

Informational  =  "100"  ;  Trying
              /   "180"  ;  Ringing
              /   "181"  ;  Call Is Being Forwarded
              /   "182"  ;  Queued
              /   "183"  ;  Session Progress

Success  =  "200"  ;  OK

Redirection  =  "300"  ;  Multiple Choices
            /   "301"  ;  Moved Permanently
            /   "302"  ;  Moved Temporarily
            /   "305"  ;  Use Proxy
            /   "380"  ;  Alternative Service

Client-Error  =  "400"  ;  Bad Request
             /   "401"  ;  Unauthorized
             /   "402"  ;  Payment Required
             /   "403"  ;  Forbidden
             /   "404"  ;  Not Found
             /   "405"  ;  Method Not Allowed
             /   "406"  ;  Not Acceptable
             /   "407"  ;  Proxy Authentication Required
             /   "408"  ;  Request Timeout
             /   "410"  ;  Gone
             /   "413"  ;  Request Entity Too Large
             /   "414"  ;  Request-URI Too Large
             /   "415"  ;  Unsupported Media Type
             /   "416"  ;  Unsupported URI Scheme
             /   "420"  ;  Bad Extension
             /   "421"  ;  Extension Required
             /   "423"  ;  Interval Too Brief
             /   "480"  ;  Temporarily not available
             /   "481"  ;  Call Leg/Transaction Does Not Exist
             /   "482"  ;  Loop Detected
             /   "483"  ;  Too Many Hops
             /   "484"  ;  Address Incomplete
             /   "485"  ;  Ambiguous
             /   "486"  ;  Busy Here
             /   "487"  ;  Request Terminated
             /   "488"  ;  Not Acceptable Here
             /   "491"  ;  Request Pending
             /   "493"  ;  Undecipherable

Server-Error  =  "500"  ;  Internal Server Error
             /   "501"  ;  Not Implemented
             /   "502"  ;  Bad Gateway
             /   "503"  ;  Service Unavailable
             /   "504"  ;  Server Time-out
             /   "505"  ;  SIP Version not supported
             /   "513"  ;  Message Too Large

Global-Failure  =  "600"  ;  Busy Everywhere
               /   "603"  ;  Decline
               /   "604"  ;  Does not exist anywhere
               /   "606"  ;  Not Acceptable


---V1.62
1. Added support for abbreviation of SIP Header. (Both in dlls and ocx)
2. Two new buttons added into VB.NET SIP phone sample to show how to dynamically changed sound device in a live call, 
and how to dynamically do audio recording.

---V1.61
Changed the sample code of "SIPServerApp". 
It can accept DTMF digits when playing or recording audio file.


---V1.60
An activeX is added into SDK family. VB6, Dephi and Borland C++ Builder programers can use this OCX to develop SIP applications.
OCX name: GTSIPCtrl.ocx
How to register this activeX in Windows: c:\sdkfolder\bin\>regsvr32 gtsipctrl.ocx
How to insert this activeX into your projects: See picture http://www.pcbest.net/images/insert-ocx.jpg
Guide to this ActiveX: http://www.pcbest.net/sipsdkref-ocx.htm
sdkfolder\samples\OCX\VB6 is the sample code of this ActiveX.


---V1.59
1. Dynamically change "gtphone.audio.record.enabled" without restarting sip server. (For phone client)
This makes dynamically recording audio channel available.

2. Play a list of audio. (For Server Application)
It is possible to play a list of audio file.
For example, if we want to play 3 files: 1.wav, 2.wav and 3.wav.
Steps:
Send_AddAudio(0, "1.wav");
Send_AddAudio(0, "2.wav");
Send_AddAudio(0, "3.wav");
Send_PlayAudio(0, "", 0, "", 0);

3. DTMF detection is available for PlayAudio and RecordAudio (For sever application only)
void Send_PlayAudio(int ch, const char* audioFileName, int iMaxDigit, const char* termStr, int iMaxTimer);
int iMaxDigit : Maxium number of digits arrived. (0 = unlimited)
const char* termStr: If any of character in the termStr pressed, the audio will stop. ("" = no term string)
int iMaxTimer: timeout value. (0 = no limitation)

void Send_RecordAudio(int ch, const char* audioFileName, int iMaxDigit, const char* termStr, int iMaxTimer);
same as above.

sample: 
a. If we want to play a audio, but when "#" is pressed or max 4 digits arrived, audio will be stopped.
Send_PlayAudio(0, "audio.wav", 4, "#", 0);

b. If we want to record a audio which is max of 60 seconds length, but when "#" is pressed, recording audio will stop.
Send_RecordAudio(0, "audio.wav", 0, "#", 60000);

4. Ability to use one sound card to play, another one to record. (For client phone application using DirectX for audio.)
Add two tags for specifying direcx playback and recording devices separately:
"gtsrv.sip.dxsound.device.playback"
"gtsrv.sip.dxsound.device.capture"
Please use keyword of devices. For example, we have two sound cards.
One is Intel 2345M, antoher is SoundBlaster SB879B.
We want Intel to play voice, and SB to recording.
Then:
CFG_SetValue("gtsrv.sip.dxsound.device.playback", "2345M");
CFG_SetValue("gtsrv.sip.dxsound.device.capture", "SB879B");

5. Ability to change sound card dynamically in a live call.
Add one function to CGTAPIEnv class to reset dx device.
Call sample:
CFG_SetValue("gtsrv.sip.dxsound.device.playback", "2345M"); //set key word of playback device
CFG_SetValue("gtsrv.sip.dxsound.device.capture", "SB879B"); //set key word of recording device
Send_ResetDxAudio(ch);

6. Add one tag to control the way of DTMF
"gtsrv.sip.dtmf.method"
0 = default, Using DTMF inband audio
1 = SIP Info
2 = RTP RFC2833.
3 = Auto

7. Add a callback function to CGTAPIEnv class for message indication of vocie mail box
virtual void On_RecvNotifySimpleMsgSummary(const char* sMsgWaiting, const char* sMsgAccount, const char* sVoiceMsg){}
const char* sMsgWaiting : Yes or No
const char* sMsgAccount : The sip account to retrieve voice message
const char* sVoiceMsg : Voice message count

8. On_RecvDTMFDone of CGTAPIEnv has new format.
Old : void On_RecvDTMFDone(int ch)
New : void On_RecvDTMFDone(int ch, int reason, const char* dtmfBuf)


---V1.58

1. Add a tag for identify if application is a SIP server or SIP client phone.

CFG_SettValue("gtsrv.sip.server.model", "1") //Server model, default.
or CFG_SettValue("gtsrv.sip.server.model", "0") //SIP Client Phone model, using DX audio

2. Four more functions added to env class play tones.
//num = 0-9, '*' or '#'
bool PlayNumTone(char num);
bool PlayLocalRingSound();
bool PlayRemoteRingSound();
bool PlayBusySound();

---V1.57
Enhanced error handling.
Env class member function On_RecvError(int ch) is changed to On_RecvError(int ch, int errCode).
Please use gterr.h as error code list reference.

---V1.56

Resolved the following several issues:

1. unable to access what kind of audio codec is being used.
Fixed. Use the following functions to access audio codec that being used.
C++ : 	int	CGTAPIEnv ::GetChanAudioCodec(int ch);
.NET :  int 	GTAPIASM.GTAPIEnv.GetChanAudioCodec(int ch);

102 = Speex
101 = iLBC 30ms
100 = iLBC 20ms
3 = GSM
98 = G726-32
0 = G711-Mulaw
8 = G711-Alaw

2. When using second sound card as DXSound audio, the following functions only operator the first primary sound card.
void		SetMicVolume(float v);
float		GetMicVolume();
void		SetSpeakerVolume(float v);
float		GetSpeakerVolume();

Fixed: Above functions will handle second audio card's volume if it is using sencond as DXSound audio.

3. When multipul channels are connected, audio quality is bad.
Fixed.


---V1.55
In order to assist programmers who are using SDK to develop IVR applications, "SIP Server App" is added into sample code.
The soure code of this application has two version: C++ and VB.NET. 
The application will help programmers with Playing audio, recording audio, echo test, call bridge, and DTMF Detection.

Play Sound: Answer the call, and play the specified sound file.
Record Sound: Answer the call, and record sound into a WAV file.
Echo Test: A sample to return voice back to sender.
Call Bridge: Full Duplex Connect two channels, so two clients can talk with each other.
DTMF Detector: Answer calls, and wait for DTMF digits. Digits will be displayed on the channels' status line.

Please copy GTSIPServerApp.ini in INI folder to c:\, and edit it with your condiguration.

---V1.54
Reslove the crash when using "gtsrv.sip.dxsound.device" to specify dxsound device


---V1.53
Add four virtual functions to class GTNetCmdClientI for raw audio access. 
Note: only C++ programers can use these interface now, because those functions are very realtime, and must return ASAP.

Set "gtsrv.sip.on.rtp.packet" to 1, or 2, or 3 to access rtp data.
1 = MULAW
2 = ALAW
3 = PCM

Overwrite the following two functions to get raw audio data.
virtual void On_RecvRTPPacket(int ch, int fmt, char* buf, int buflen, unsigned short seq, unsigned int timestamp, SYSTEMTIME* pSysTime)
virtual void On_SentRTPPacket(int ch, int fmt, char* buf, int buflen, unsigned short seq, unsigned int timestamp, SYSTEMTIME* pSysTime)


Set "gtsrv.sip.on.dx.audio" to 1, or 2, or 3 to access directx audio data
1 = MULAW
2 = ALAW
3 = PCM

Overwrite the following two functions to get raw directx audio data.
virtual void On_CaptureDXAudio(int ch, int fmt, char* buf, int buflen, unsigned short seq, unsigned int timestamp, SYSTEMTIME* pSysTime)
virtual void On_RenderDXAudio(int ch, int fmt, char* buf, int buflen, unsigned short seq, unsigned int timestamp, SYSTEMTIME* pSysTime)


////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//Open Source License
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

OpenSSL: https://www.openssl.org/source/license.html

libSRTP:
 
libSRTP is distributed under the following license, which is included in the source code distribution. It is reproduced in the manual in case you got the library from another source.

Copyright (c) 2001-2017 Cisco Systems, Inc. All rights reserved.

Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:

Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
Neither the name of the Cisco Systems, Inc. nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
