ast_h323.cxx 80 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679
  1. #ifndef _GNU_SOURCE
  2. #define _GNU_SOURCE
  3. #endif
  4. /*
  5. * ast_h323.cpp
  6. *
  7. * OpenH323 Channel Driver for ASTERISK PBX.
  8. * By Jeremy McNamara
  9. * For The NuFone Network
  10. *
  11. * chan_h323 has been derived from code created by
  12. * Michael Manousos and Mark Spencer
  13. *
  14. * This file is part of the chan_h323 driver for Asterisk
  15. *
  16. * chan_h323 is free software; you can redistribute it and/or modify
  17. * it under the terms of the GNU General Public License as published by
  18. * the Free Software Foundation; either version 2 of the License, or
  19. * (at your option) any later version.
  20. *
  21. * chan_h323 is distributed WITHOUT ANY WARRANTY; without even
  22. * the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
  23. * PURPOSE. See the GNU General Public License for more details.
  24. *
  25. * You should have received a copy of the GNU General Public License
  26. * along with this program; if not, write to the Free Software
  27. * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  28. *
  29. * Version Info: $Id$
  30. */
  31. #define VERSION(a,b,c) ((a)*10000+(b)*100+(c))
  32. #include <arpa/inet.h>
  33. #include <list>
  34. #include <string>
  35. #include <algorithm>
  36. #include <ptlib.h>
  37. #include <h323.h>
  38. #include <h323pdu.h>
  39. #include <h323neg.h>
  40. #include <mediafmt.h>
  41. /* H323 Plus */
  42. #if VERSION(OPENH323_MAJOR, OPENH323_MINOR, OPENH323_BUILD) > VERSION(1,19,4)
  43. #ifdef H323_H450
  44. #include "h450/h4501.h"
  45. #include "h450/h4504.h"
  46. #include "h450/h45011.h"
  47. #include "h450/h450pdu.h"
  48. #endif
  49. #ifdef H323_H460
  50. #include <h460/h4601.h>
  51. #endif
  52. #else /* !H323 Plus */
  53. #include <lid.h>
  54. #ifdef H323_H450
  55. #include "h4501.h"
  56. #include "h4504.h"
  57. #include "h45011.h"
  58. #include "h450pdu.h"
  59. #endif
  60. #endif /* H323 Plus */
  61. #include "compat_h323.h"
  62. #include "asterisk.h"
  63. #ifdef __cplusplus
  64. extern "C" {
  65. #endif
  66. #include "asterisk/compat.h"
  67. #include "asterisk/logger.h"
  68. #include "asterisk/channel.h"
  69. #include "asterisk/astobj.h"
  70. #ifdef __cplusplus
  71. }
  72. #endif
  73. #undef open
  74. #undef close
  75. #include "chan_h323.h"
  76. #include "ast_h323.h"
  77. #include "cisco-h225.h"
  78. #include "caps_h323.h"
  79. /* PWLIB_MAJOR renamed to PTLIB_MAJOR in 2.x.x */
  80. #if (defined(PTLIB_MAJOR) || VERSION(PWLIB_MAJOR, PWLIB_MINOR, PWLIB_BUILD) >= VERSION(1,12,0))
  81. #define SKIP_PWLIB_PIPE_BUG_WORKAROUND 1
  82. #endif
  83. ///////////////////////////////////////////////
  84. /* We have to have a PProcess running for the life of the instance to give
  85. * h323plus a static instance of PProcess to get system information.
  86. * This class is defined with PDECLARE_PROCESS(). See pprocess.h from pwlib.
  87. */
  88. /* PWlib Required Components */
  89. #if VERSION(OPENH323_MAJOR, OPENH323_MINOR, OPENH323_BUILD) > VERSION(1,19,4)
  90. #define MAJOR_VERSION 1
  91. #define MINOR_VERSION 19
  92. #define BUILD_TYPE ReleaseCode
  93. #define BUILD_NUMBER 6
  94. #else
  95. #define MAJOR_VERSION 1
  96. #define MINOR_VERSION 0
  97. #define BUILD_TYPE ReleaseCode
  98. #define BUILD_NUMBER 0
  99. #endif
  100. const char *h323manufact = "The NuFone Networks";
  101. const char *h323product = "H.323 Channel Driver for Asterisk";
  102. PDECLARE_PROCESS(MyProcess,PProcess,h323manufact,h323product,MAJOR_VERSION,MINOR_VERSION,BUILD_TYPE,BUILD_NUMBER)
  103. static MyProcess localProcess; // active for the life of the DLL
  104. /* void MyProcess::Main()
  105. {
  106. }
  107. */
  108. ////////////////////////////////////////////////
  109. /** Counter for the number of connections */
  110. static int channelsOpen;
  111. /**
  112. * We assume that only one endPoint should exist.
  113. * The application cannot run the h323_end_point_create() more than once
  114. * FIXME: Singleton this, for safety
  115. */
  116. static MyH323EndPoint *endPoint = NULL;
  117. #ifndef SKIP_PWLIB_PIPE_BUG_WORKAROUND
  118. static int _timerChangePipe[2];
  119. #endif
  120. static unsigned traceOptions = PTrace::Timestamp | PTrace::Thread | PTrace::FileAndLine;
  121. class PAsteriskLog : public PObject, public iostream {
  122. PCLASSINFO(PAsteriskLog, PObject);
  123. public:
  124. PAsteriskLog() : iostream(cout.rdbuf()) { init(&buffer); }
  125. ~PAsteriskLog() { flush(); }
  126. private:
  127. PAsteriskLog(const PAsteriskLog &) : iostream(cout.rdbuf()) { }
  128. PAsteriskLog & operator=(const PAsteriskLog &) { return *this; }
  129. class Buffer : public streambuf {
  130. public:
  131. virtual int overflow(int=EOF);
  132. virtual int underflow();
  133. virtual int sync();
  134. PString string;
  135. } buffer;
  136. friend class Buffer;
  137. };
  138. static PAsteriskLog *logstream = NULL;
  139. int PAsteriskLog::Buffer::overflow(int c)
  140. {
  141. if (pptr() >= epptr()) {
  142. int ppos = pptr() - pbase();
  143. char *newptr = string.GetPointer(string.GetSize() + 2000);
  144. setp(newptr, newptr + string.GetSize() - 1);
  145. pbump(ppos);
  146. }
  147. if (c != EOF) {
  148. *pptr() = (char)c;
  149. pbump(1);
  150. }
  151. return 0;
  152. }
  153. int PAsteriskLog::Buffer::underflow()
  154. {
  155. return EOF;
  156. }
  157. int PAsteriskLog::Buffer::sync()
  158. {
  159. char *str = ast_strdup(string);
  160. char *s, *s1;
  161. char c;
  162. /* Pass each line with different ast_verbose() call */
  163. for (s = str; s && *s; s = s1) {
  164. s1 = strchr(s, '\n');
  165. if (!s1)
  166. s1 = s + strlen(s);
  167. else
  168. s1++;
  169. c = *s1;
  170. *s1 = '\0';
  171. ast_verbose("%s", s);
  172. *s1 = c;
  173. }
  174. ast_free(str);
  175. string = PString();
  176. char *base = string.GetPointer(2000);
  177. setp(base, base + string.GetSize() - 1);
  178. return 0;
  179. }
  180. static ostream &my_endl(ostream &os)
  181. {
  182. if (logstream) {
  183. PTrace::SetOptions(traceOptions);
  184. return PTrace::End(os);
  185. }
  186. return endl(os);
  187. }
  188. #define cout \
  189. (logstream ? (PTrace::ClearOptions((unsigned)-1), PTrace::Begin(0, __FILE__, __LINE__)) : std::cout)
  190. #define endl my_endl
  191. void MyProcess::Main()
  192. {
  193. PTrace::Initialise(PTrace::GetLevel(), NULL, traceOptions);
  194. PTrace::SetStream(logstream);
  195. cout << " == Creating H.323 Endpoint" << endl;
  196. if (endPoint) {
  197. cout << " == ENDPOINT ALREADY CREATED" << endl;
  198. return;
  199. }
  200. endPoint = new MyH323EndPoint();
  201. /* Due to a bug in the H.323 recomendation/stack we should request a sane
  202. amount of bandwidth from the GK - this function is ignored if not using a GK
  203. We are requesting 128 (64k in each direction), which is the worst case codec. */
  204. endPoint->SetInitialBandwidth(1280);
  205. }
  206. void PAssertFunc(const char *msg)
  207. {
  208. ast_log(LOG_ERROR, "%s\n", msg);
  209. /* XXX: Probably we need to crash here */
  210. }
  211. /** MyH323EndPoint
  212. */
  213. MyH323EndPoint::MyH323EndPoint()
  214. : H323EndPoint()
  215. {
  216. /* Capabilities will be negotiated on per-connection basis */
  217. capabilities.RemoveAll();
  218. /* Reset call setup timeout to some more reasonable value than 1 minute */
  219. signallingChannelCallTimeout = PTimeInterval(0, 0, 10); /* 10 minutes */
  220. }
  221. /** The fullAddress parameter is used directly in the MakeCall method so
  222. * the General form for the fullAddress argument is :
  223. * [alias@][transport$]host[:port]
  224. * default values: alias = the same value as host.
  225. * transport = ip.
  226. * port = 1720.
  227. */
  228. int MyH323EndPoint::MyMakeCall(const PString & dest, PString & token, void *_callReference, void *_opts)
  229. {
  230. PString fullAddress;
  231. MyH323Connection * connection;
  232. H323Transport *transport = NULL;
  233. unsigned int *callReference = (unsigned int *)_callReference;
  234. call_options_t *opts = (call_options_t *)_opts;
  235. /* Determine whether we are using a gatekeeper or not. */
  236. if (GetGatekeeper()) {
  237. fullAddress = dest;
  238. if (h323debug) {
  239. cout << " -- Making call to " << fullAddress << " using gatekeeper." << endl;
  240. }
  241. } else {
  242. fullAddress = dest;
  243. if (h323debug) {
  244. cout << " -- Making call to " << fullAddress << " without gatekeeper." << endl;
  245. }
  246. /* Use bindaddr for outgoing calls too if we don't use gatekeeper */
  247. if (listeners.GetSize() > 0) {
  248. H323TransportAddress taddr = listeners[0].GetTransportAddress();
  249. PIPSocket::Address addr;
  250. WORD port;
  251. if (taddr.GetIpAndPort(addr, port)) {
  252. /* Create own transport for specific addresses only */
  253. if (addr) {
  254. if (h323debug)
  255. cout << "Using " << addr << " for outbound call" << endl;
  256. transport = new MyH323TransportTCP(*this, addr);
  257. if (!transport)
  258. cout << "Unable to create transport for outgoing call" << endl;
  259. }
  260. } else
  261. cout << "Unable to get address and port" << endl;
  262. }
  263. }
  264. if (!(connection = (MyH323Connection *)H323EndPoint::MakeCallLocked(fullAddress, token, opts, transport))) {
  265. if (h323debug) {
  266. cout << "Error making call to \"" << fullAddress << '"' << endl;
  267. }
  268. return 1;
  269. }
  270. *callReference = connection->GetCallReference();
  271. if (h323debug) {
  272. cout << "\t-- " << GetLocalUserName() << " is calling host " << fullAddress << endl;
  273. cout << "\t-- Call token is " << (const char *)token << endl;
  274. cout << "\t-- Call reference is " << *callReference << endl;
  275. #ifdef PTRACING
  276. cout << "\t-- DTMF Payload is " << connection->dtmfCodec << endl;
  277. #endif
  278. }
  279. connection->Unlock();
  280. return 0;
  281. }
  282. void MyH323EndPoint::SetEndpointTypeInfo( H225_EndpointType & info ) const
  283. {
  284. H323EndPoint::SetEndpointTypeInfo(info);
  285. if (terminalType == e_GatewayOnly){
  286. info.RemoveOptionalField(H225_EndpointType::e_terminal);
  287. info.IncludeOptionalField(H225_EndpointType::e_gateway);
  288. }
  289. info.m_gateway.IncludeOptionalField(H225_GatewayInfo::e_protocol);
  290. info.m_gateway.m_protocol.SetSize(1);
  291. H225_SupportedProtocols &protocol=info.m_gateway.m_protocol[0];
  292. protocol.SetTag(H225_SupportedProtocols::e_voice);
  293. PINDEX as=SupportedPrefixes.GetSize();
  294. ((H225_VoiceCaps &)protocol).m_supportedPrefixes.SetSize(as);
  295. for (PINDEX p=0; p<as; p++) {
  296. H323SetAliasAddress(SupportedPrefixes[p], ((H225_VoiceCaps &)protocol).m_supportedPrefixes[p].m_prefix, H225_AliasAddress::e_dialedDigits);
  297. }
  298. }
  299. void MyH323EndPoint::SetGateway(void)
  300. {
  301. terminalType = e_GatewayOnly;
  302. }
  303. PBoolean MyH323EndPoint::ClearCall(const PString & token, H323Connection::CallEndReason reason)
  304. {
  305. if (h323debug) {
  306. #ifdef PTRACING
  307. cout << "\t-- ClearCall: Request to clear call with token " << token << ", cause " << reason << endl;
  308. #else
  309. cout << "\t-- ClearCall: Request to clear call with token " << token << ", cause [" << (int)reason << "]" << endl;
  310. #endif
  311. }
  312. return H323EndPoint::ClearCall(token, reason);
  313. }
  314. PBoolean MyH323EndPoint::ClearCall(const PString & token)
  315. {
  316. if (h323debug) {
  317. cout << "\t-- ClearCall: Request to clear call with token " << token << endl;
  318. }
  319. return H323EndPoint::ClearCall(token, H323Connection::EndedByLocalUser);
  320. }
  321. void MyH323EndPoint::SendUserTone(const PString &token, char tone)
  322. {
  323. H323Connection *connection = NULL;
  324. connection = FindConnectionWithLock(token);
  325. if (connection != NULL) {
  326. connection->SendUserInputTone(tone, 500);
  327. connection->Unlock();
  328. }
  329. }
  330. void MyH323EndPoint::OnClosedLogicalChannel(H323Connection & connection, const H323Channel & channel)
  331. {
  332. channelsOpen--;
  333. if (h323debug) {
  334. cout << "\t\tchannelsOpen = " << channelsOpen << endl;
  335. }
  336. H323EndPoint::OnClosedLogicalChannel(connection, channel);
  337. }
  338. PBoolean MyH323EndPoint::OnConnectionForwarded(H323Connection & connection,
  339. const PString & forwardParty,
  340. const H323SignalPDU & pdu)
  341. {
  342. if (h323debug) {
  343. cout << "\t-- Call Forwarded to " << forwardParty << endl;
  344. }
  345. return FALSE;
  346. }
  347. PBoolean MyH323EndPoint::ForwardConnection(H323Connection & connection,
  348. const PString & forwardParty,
  349. const H323SignalPDU & pdu)
  350. {
  351. if (h323debug) {
  352. cout << "\t-- Forwarding call to " << forwardParty << endl;
  353. }
  354. return H323EndPoint::ForwardConnection(connection, forwardParty, pdu);
  355. }
  356. void MyH323EndPoint::OnConnectionEstablished(H323Connection & connection, const PString & estCallToken)
  357. {
  358. if (h323debug) {
  359. cout << "\t=-= In OnConnectionEstablished for call " << connection.GetCallReference() << endl;
  360. cout << "\t\t-- Connection Established with \"" << connection.GetRemotePartyName() << "\"" << endl;
  361. }
  362. on_connection_established(connection.GetCallReference(), (const char *)connection.GetCallToken());
  363. }
  364. /** OnConnectionCleared callback function is called upon the dropping of an established
  365. * H323 connection.
  366. */
  367. void MyH323EndPoint::OnConnectionCleared(H323Connection & connection, const PString & clearedCallToken)
  368. {
  369. PString remoteName = connection.GetRemotePartyName();
  370. switch (connection.GetCallEndReason()) {
  371. case H323Connection::EndedByCallForwarded:
  372. if (h323debug) {
  373. cout << "-- " << remoteName << " has forwarded the call" << endl;
  374. }
  375. break;
  376. case H323Connection::EndedByRemoteUser:
  377. if (h323debug) {
  378. cout << "-- " << remoteName << " has cleared the call" << endl;
  379. }
  380. break;
  381. case H323Connection::EndedByCallerAbort:
  382. if (h323debug) {
  383. cout << "-- " << remoteName << " has stopped calling" << endl;
  384. }
  385. break;
  386. case H323Connection::EndedByRefusal:
  387. if (h323debug) {
  388. cout << "-- " << remoteName << " did not accept your call" << endl;
  389. }
  390. break;
  391. case H323Connection::EndedByRemoteBusy:
  392. if (h323debug) {
  393. cout << "-- " << remoteName << " was busy" << endl;
  394. }
  395. break;
  396. case H323Connection::EndedByRemoteCongestion:
  397. if (h323debug) {
  398. cout << "-- Congested link to " << remoteName << endl;
  399. }
  400. break;
  401. case H323Connection::EndedByNoAnswer:
  402. if (h323debug) {
  403. cout << "-- " << remoteName << " did not answer your call" << endl;
  404. }
  405. break;
  406. case H323Connection::EndedByTransportFail:
  407. if (h323debug) {
  408. cout << "-- Call with " << remoteName << " ended abnormally" << endl;
  409. }
  410. break;
  411. case H323Connection::EndedByCapabilityExchange:
  412. if (h323debug) {
  413. cout << "-- Could not find common codec with " << remoteName << endl;
  414. }
  415. break;
  416. case H323Connection::EndedByNoAccept:
  417. if (h323debug) {
  418. cout << "-- Did not accept incoming call from " << remoteName << endl;
  419. }
  420. break;
  421. case H323Connection::EndedByAnswerDenied:
  422. if (h323debug) {
  423. cout << "-- Refused incoming call from " << remoteName << endl;
  424. }
  425. break;
  426. case H323Connection::EndedByNoUser:
  427. if (h323debug) {
  428. cout << "-- Remote endpoint could not find user: " << remoteName << endl;
  429. }
  430. break;
  431. case H323Connection::EndedByNoBandwidth:
  432. if (h323debug) {
  433. cout << "-- Call to " << remoteName << " aborted, insufficient bandwidth." << endl;
  434. }
  435. break;
  436. case H323Connection::EndedByUnreachable:
  437. if (h323debug) {
  438. cout << "-- " << remoteName << " could not be reached." << endl;
  439. }
  440. break;
  441. case H323Connection::EndedByHostOffline:
  442. if (h323debug) {
  443. cout << "-- " << remoteName << " is not online." << endl;
  444. }
  445. break;
  446. case H323Connection::EndedByNoEndPoint:
  447. if (h323debug) {
  448. cout << "-- No phone running for " << remoteName << endl;
  449. }
  450. break;
  451. case H323Connection::EndedByConnectFail:
  452. if (h323debug) {
  453. cout << "-- Transport error calling " << remoteName << endl;
  454. }
  455. break;
  456. default:
  457. if (h323debug) {
  458. #ifdef PTRACING
  459. cout << " -- Call with " << remoteName << " completed (" << connection.GetCallEndReason() << ")" << endl;
  460. #else
  461. cout << " -- Call with " << remoteName << " completed ([" << (int)connection.GetCallEndReason() << "])" << endl;
  462. #endif
  463. }
  464. }
  465. if (connection.IsEstablished()) {
  466. if (h323debug) {
  467. cout << "\t-- Call duration " << setprecision(0) << setw(5) << (PTime() - connection.GetConnectionStartTime()) << endl;
  468. }
  469. }
  470. /* Invoke the PBX application registered callback */
  471. on_connection_cleared(connection.GetCallReference(), clearedCallToken);
  472. return;
  473. }
  474. H323Connection * MyH323EndPoint::CreateConnection(unsigned callReference, void *userData, H323Transport *transport, H323SignalPDU *setupPDU)
  475. {
  476. unsigned options = 0;
  477. call_options_t *opts = (call_options_t *)userData;
  478. MyH323Connection *conn;
  479. if (opts && opts->fastStart) {
  480. options |= H323Connection::FastStartOptionEnable;
  481. } else {
  482. options |= H323Connection::FastStartOptionDisable;
  483. }
  484. if (opts && opts->h245Tunneling) {
  485. options |= H323Connection::H245TunnelingOptionEnable;
  486. } else {
  487. options |= H323Connection::H245TunnelingOptionDisable;
  488. }
  489. /* Disable until I can figure out the proper way to deal with this */
  490. #if 0
  491. if (opts->silenceSuppression) {
  492. options |= H323Connection::SilenceSuppresionOptionEnable;
  493. } else {
  494. options |= H323Connection::SilenceSUppressionOptionDisable;
  495. }
  496. #endif
  497. conn = new MyH323Connection(*this, callReference, options);
  498. if (conn) {
  499. if (opts)
  500. conn->SetCallOptions(opts, (setupPDU ? TRUE : FALSE));
  501. }
  502. return conn;
  503. }
  504. /* MyH323Connection Implementation */
  505. MyH323Connection::MyH323Connection(MyH323EndPoint & ep, unsigned callReference,
  506. unsigned options)
  507. : H323Connection(ep, callReference, options)
  508. {
  509. #ifdef H323_H450
  510. /* Dispatcher will free out all registered handlers */
  511. delete h450dispatcher;
  512. h450dispatcher = new H450xDispatcher(*this);
  513. h4502handler = new H4502Handler(*this, *h450dispatcher);
  514. h4504handler = new MyH4504Handler(*this, *h450dispatcher);
  515. h4506handler = new H4506Handler(*this, *h450dispatcher);
  516. h45011handler = new H45011Handler(*this, *h450dispatcher);
  517. #endif
  518. cause = -1;
  519. sessionId = 0;
  520. bridging = FALSE;
  521. holdHandling = progressSetup = progressAlert = 0;
  522. dtmfMode = 0;
  523. dtmfCodec[0] = dtmfCodec[1] = (RTP_DataFrame::PayloadTypes)0;
  524. redirect_reason = -1;
  525. transfer_capability = -1;
  526. #ifdef TUNNELLING
  527. tunnelOptions = remoteTunnelOptions = 0;
  528. #endif
  529. if (h323debug) {
  530. cout << " == New H.323 Connection created." << endl;
  531. }
  532. return;
  533. }
  534. MyH323Connection::~MyH323Connection()
  535. {
  536. if (h323debug) {
  537. cout << " == H.323 Connection deleted." << endl;
  538. }
  539. return;
  540. }
  541. PBoolean MyH323Connection::OnReceivedProgress(const H323SignalPDU &pdu)
  542. {
  543. PBoolean isInband;
  544. unsigned pi;
  545. if (!H323Connection::OnReceivedProgress(pdu)) {
  546. return FALSE;
  547. }
  548. if (!pdu.GetQ931().GetProgressIndicator(pi))
  549. pi = 0;
  550. if (h323debug) {
  551. cout << "\t- Progress Indicator: " << pi << endl;
  552. }
  553. switch(pi) {
  554. case Q931::ProgressNotEndToEndISDN:
  555. case Q931::ProgressInbandInformationAvailable:
  556. isInband = TRUE;
  557. break;
  558. default:
  559. isInband = FALSE;
  560. }
  561. on_progress(GetCallReference(), (const char *)GetCallToken(), isInband);
  562. return connectionState != ShuttingDownConnection;
  563. }
  564. PBoolean MyH323Connection::MySendProgress()
  565. {
  566. /* The code taken from H323Connection::AnsweringCall() but ALWAYS send
  567. PROGRESS message, including slow start operations */
  568. H323SignalPDU progressPDU;
  569. H225_Progress_UUIE &prog = progressPDU.BuildProgress(*this);
  570. if (!mediaWaitForConnect) {
  571. if (SendFastStartAcknowledge(prog.m_fastStart))
  572. prog.IncludeOptionalField(H225_Progress_UUIE::e_fastStart);
  573. else {
  574. if (connectionState == ShuttingDownConnection)
  575. return FALSE;
  576. /* Do early H.245 start */
  577. earlyStart = TRUE;
  578. if (!h245Tunneling) {
  579. if (!H323Connection::StartControlChannel())
  580. return FALSE;
  581. prog.IncludeOptionalField(H225_Progress_UUIE::e_h245Address);
  582. controlChannel->SetUpTransportPDU(prog.m_h245Address, TRUE);
  583. }
  584. }
  585. }
  586. progressPDU.GetQ931().SetProgressIndicator(Q931::ProgressInbandInformationAvailable);
  587. #ifdef TUNNELLING
  588. EmbedTunneledInfo(progressPDU);
  589. #endif
  590. HandleTunnelPDU(&progressPDU);
  591. WriteSignalPDU(progressPDU);
  592. return TRUE;
  593. }
  594. H323Connection::AnswerCallResponse MyH323Connection::OnAnswerCall(const PString & caller,
  595. const H323SignalPDU & setupPDU,
  596. H323SignalPDU & connectPDU)
  597. {
  598. unsigned pi;
  599. if (h323debug) {
  600. cout << "\t=-= In OnAnswerCall for call " << GetCallReference() << endl;
  601. }
  602. if (connectionState == ShuttingDownConnection)
  603. return H323Connection::AnswerCallDenied;
  604. if (!setupPDU.GetQ931().GetProgressIndicator(pi)) {
  605. pi = 0;
  606. }
  607. if (h323debug) {
  608. cout << "\t\t- Progress Indicator: " << pi << endl;
  609. }
  610. if (progressAlert) {
  611. pi = progressAlert;
  612. } else if (pi == Q931::ProgressOriginNotISDN) {
  613. pi = Q931::ProgressInbandInformationAvailable;
  614. }
  615. if (pi && alertingPDU) {
  616. alertingPDU->GetQ931().SetProgressIndicator(pi);
  617. }
  618. if (h323debug) {
  619. cout << "\t\t- Inserting PI of " << pi << " into ALERTING message" << endl;
  620. }
  621. #ifdef TUNNELLING
  622. if (alertingPDU)
  623. EmbedTunneledInfo(*alertingPDU);
  624. EmbedTunneledInfo(connectPDU);
  625. #endif
  626. if (!on_answer_call(GetCallReference(), (const char *)GetCallToken())) {
  627. return H323Connection::AnswerCallDenied;
  628. }
  629. /* The call will be answered later with "AnsweringCall()" function.
  630. */
  631. return ((pi || (fastStartState != FastStartDisabled)) ? AnswerCallDeferredWithMedia : AnswerCallDeferred);
  632. }
  633. PBoolean MyH323Connection::OnAlerting(const H323SignalPDU & alertingPDU, const PString & username)
  634. {
  635. if (h323debug) {
  636. cout << "\t=-= In OnAlerting for call " << GetCallReference()
  637. << ": sessionId=" << sessionId << endl;
  638. cout << "\t-- Ringing phone for \"" << username << "\"" << endl;
  639. }
  640. if (on_progress) {
  641. PBoolean isInband;
  642. unsigned alertingPI;
  643. if (!alertingPDU.GetQ931().GetProgressIndicator(alertingPI)) {
  644. alertingPI = 0;
  645. }
  646. if (h323debug) {
  647. cout << "\t\t- Progress Indicator: " << alertingPI << endl;
  648. }
  649. switch(alertingPI) {
  650. case Q931::ProgressNotEndToEndISDN:
  651. case Q931::ProgressInbandInformationAvailable:
  652. isInband = TRUE;
  653. break;
  654. default:
  655. isInband = FALSE;
  656. }
  657. on_progress(GetCallReference(), (const char *)GetCallToken(), isInband);
  658. }
  659. on_chan_ringing(GetCallReference(), (const char *)GetCallToken() );
  660. return connectionState != ShuttingDownConnection;
  661. }
  662. void MyH323Connection::SetCallOptions(void *o, PBoolean isIncoming)
  663. {
  664. call_options_t *opts = (call_options_t *)o;
  665. progressSetup = opts->progress_setup;
  666. progressAlert = opts->progress_alert;
  667. holdHandling = opts->holdHandling;
  668. dtmfCodec[0] = (RTP_DataFrame::PayloadTypes)opts->dtmfcodec[0];
  669. dtmfCodec[1] = (RTP_DataFrame::PayloadTypes)opts->dtmfcodec[1];
  670. dtmfMode = opts->dtmfmode;
  671. if (isIncoming) {
  672. fastStartState = (opts->fastStart ? FastStartInitiate : FastStartDisabled);
  673. h245Tunneling = (opts->h245Tunneling ? TRUE : FALSE);
  674. } else {
  675. sourceE164 = PString(opts->cid_num);
  676. SetLocalPartyName(PString(opts->cid_name));
  677. SetDisplayName(PString(opts->cid_name));
  678. if (opts->redirect_reason >= 0) {
  679. rdnis = PString(opts->cid_rdnis);
  680. redirect_reason = opts->redirect_reason;
  681. }
  682. cid_presentation = opts->presentation;
  683. cid_ton = opts->type_of_number;
  684. if (opts->transfer_capability >= 0) {
  685. transfer_capability = opts->transfer_capability;
  686. }
  687. }
  688. tunnelOptions = opts->tunnelOptions;
  689. }
  690. void MyH323Connection::SetCallDetails(void *callDetails, const H323SignalPDU &setupPDU, PBoolean isIncoming)
  691. {
  692. PString sourceE164;
  693. PString destE164;
  694. PString sourceAliases;
  695. PString destAliases;
  696. char *s, *s1;
  697. call_details_t *cd = (call_details_t *)callDetails;
  698. memset(cd, 0, sizeof(*cd));
  699. cd->call_reference = GetCallReference();
  700. cd->call_token = strdup((const char *)GetCallToken());
  701. sourceE164 = "";
  702. setupPDU.GetSourceE164(sourceE164);
  703. cd->call_source_e164 = strdup((const char *)sourceE164);
  704. destE164 = "";
  705. setupPDU.GetDestinationE164(destE164);
  706. cd->call_dest_e164 = strdup((const char *)destE164);
  707. /* XXX Is it possible to have this information for outgoing calls too? XXX */
  708. if (isIncoming) {
  709. PString sourceName;
  710. PIPSocket::Address Ip;
  711. WORD sourcePort;
  712. PString redirect_number;
  713. unsigned redirect_reason;
  714. unsigned plan, type, screening, presentation;
  715. Q931::InformationTransferCapability capability;
  716. unsigned transferRate, codingStandard, userInfoLayer1;
  717. /* Fetch presentation and type information about calling party's number */
  718. if (setupPDU.GetQ931().GetCallingPartyNumber(sourceName, &plan, &type, &presentation, &screening, 0, 0)) {
  719. /* Construct fields back */
  720. cd->type_of_number = (type << 4) | plan;
  721. cd->presentation = (presentation << 5) | screening;
  722. } else if (cd->call_source_e164[0]) {
  723. cd->type_of_number = 0; /* UNKNOWN */
  724. cd->presentation = 0x03; /* ALLOWED NETWORK NUMBER - Default */
  725. if (setupPDU.GetQ931().HasIE(Q931::UserUserIE)) {
  726. const H225_Setup_UUIE &setup_uuie = setupPDU.m_h323_uu_pdu.m_h323_message_body;
  727. if (setup_uuie.HasOptionalField(H225_Setup_UUIE::e_presentationIndicator))
  728. cd->presentation = (cd->presentation & 0x9f) | (((unsigned int)setup_uuie.m_presentationIndicator.GetTag()) << 5);
  729. if (setup_uuie.HasOptionalField(H225_Setup_UUIE::e_screeningIndicator))
  730. cd->presentation = (cd->presentation & 0xe0) | (((unsigned int)setup_uuie.m_screeningIndicator.GetValue()) & 0x1f);
  731. }
  732. } else {
  733. cd->type_of_number = 0; /* UNKNOWN */
  734. cd->presentation = 0x43; /* NUMBER NOT AVAILABLE */
  735. }
  736. sourceName = setupPDU.GetQ931().GetDisplayName();
  737. cd->call_source_name = strdup((const char *)sourceName);
  738. GetSignallingChannel()->GetRemoteAddress().GetIpAndPort(Ip, sourcePort);
  739. cd->sourceIp = strdup((const char *)Ip.AsString());
  740. if (setupPDU.GetQ931().GetRedirectingNumber(redirect_number, NULL, NULL, NULL, NULL, &redirect_reason, 0, 0, 0)) {
  741. cd->redirect_number = strdup((const char *)redirect_number);
  742. cd->redirect_reason = redirect_reason;
  743. }
  744. else
  745. cd->redirect_reason = -1;
  746. /* Fetch Q.931's transfer capability */
  747. if (((Q931 &)setupPDU.GetQ931()).GetBearerCapabilities(capability, transferRate, &codingStandard, &userInfoLayer1))
  748. cd->transfer_capability = ((unsigned int)capability & 0x1f) | (codingStandard << 5);
  749. else
  750. cd->transfer_capability = 0x00; /* ITU coding of Speech */
  751. /* Don't show local username as called party name */
  752. SetDisplayName(cd->call_dest_e164);
  753. }
  754. /* Convert complex strings */
  755. // FIXME: deal more than one source alias
  756. sourceAliases = setupPDU.GetSourceAliases();
  757. s1 = strdup((const char *)sourceAliases);
  758. if ((s = strchr(s1, ' ')) != NULL)
  759. *s = '\0';
  760. if ((s = strchr(s1, '\t')) != NULL)
  761. *s = '\0';
  762. cd->call_source_aliases = s1;
  763. destAliases = setupPDU.GetDestinationAlias();
  764. s1 = strdup((const char *)destAliases);
  765. if ((s = strchr(s1, ' ')) != NULL)
  766. *s = '\0';
  767. if ((s = strchr(s1, '\t')) != NULL)
  768. *s = '\0';
  769. cd->call_dest_alias = s1;
  770. }
  771. #ifdef TUNNELLING
  772. static PBoolean FetchInformationElements(Q931 &q931, const PBYTEArray &data)
  773. {
  774. PINDEX offset = 0;
  775. while (offset < data.GetSize()) {
  776. // Get field discriminator
  777. int discriminator = data[offset++];
  778. #if 0
  779. /* Do not overwrite existing IEs */
  780. if (q931.HasIE((Q931::InformationElementCodes)discriminator)) {
  781. if ((discriminatir & 0x80) == 0)
  782. offset += data[offset++];
  783. if (offset > data.GetSize())
  784. return FALSE;
  785. continue;
  786. }
  787. #endif
  788. PBYTEArray * item = new PBYTEArray;
  789. // For discriminator with high bit set there is no data
  790. if ((discriminator & 0x80) == 0) {
  791. int len = data[offset++];
  792. #if 0 // That is not H.225 but regular Q.931 (ISDN) IEs
  793. if (discriminator == UserUserIE) {
  794. // Special case of User-user field. See 7.2.2.31/H.225.0v4.
  795. len <<= 8;
  796. len |= data[offset++];
  797. // we also have a protocol discriminator, which we ignore
  798. offset++;
  799. // before decrementing the length, make sure it is not zero
  800. if (len == 0)
  801. return FALSE;
  802. // adjust for protocol discriminator
  803. len--;
  804. }
  805. #endif
  806. if (offset + len > data.GetSize()) {
  807. delete item;
  808. return FALSE;
  809. }
  810. memcpy(item->GetPointer(len), (const BYTE *)data+offset, len);
  811. offset += len;
  812. }
  813. q931.SetIE((Q931::InformationElementCodes)discriminator, *item);
  814. delete item;
  815. }
  816. return TRUE;
  817. }
  818. static PBoolean FetchCiscoTunneledInfo(Q931 &q931, const H323SignalPDU &pdu)
  819. {
  820. PBoolean res = FALSE;
  821. const H225_H323_UU_PDU &uuPDU = pdu.m_h323_uu_pdu;
  822. if(uuPDU.HasOptionalField(H225_H323_UU_PDU::e_nonStandardControl)) {
  823. for(int i = 0; i < uuPDU.m_nonStandardControl.GetSize(); ++i) {
  824. const H225_NonStandardParameter &np = uuPDU.m_nonStandardControl[i];
  825. const H225_NonStandardIdentifier &id = np.m_nonStandardIdentifier;
  826. if (id.GetTag() == H225_NonStandardIdentifier::e_h221NonStandard) {
  827. const H225_H221NonStandard &ni = id;
  828. /* Check for Cisco */
  829. if ((ni.m_t35CountryCode == 181) && (ni.m_t35Extension == 0) && (ni.m_manufacturerCode == 18)) {
  830. const PBYTEArray &data = np.m_data;
  831. if (h323debug)
  832. cout << setprecision(0) << "Received non-standard Cisco extension data " << np.m_data << endl;
  833. CISCO_H225_H323_UU_NonStdInfo c;
  834. PPER_Stream strm(data);
  835. if (c.Decode(strm)) {
  836. PBoolean haveIEs = FALSE;
  837. if (h323debug)
  838. cout << setprecision(0) << "H323_UU_NonStdInfo = " << c << endl;
  839. if (c.HasOptionalField(CISCO_H225_H323_UU_NonStdInfo::e_protoParam)) {
  840. FetchInformationElements(q931, c.m_protoParam.m_qsigNonStdInfo.m_rawMesg);
  841. haveIEs = TRUE;
  842. }
  843. if (c.HasOptionalField(CISCO_H225_H323_UU_NonStdInfo::e_commonParam)) {
  844. FetchInformationElements(q931, c.m_commonParam.m_redirectIEinfo.m_redirectIE);
  845. haveIEs = TRUE;
  846. }
  847. if (haveIEs && h323debug)
  848. cout << setprecision(0) << "Information elements collected:" << q931 << endl;
  849. res = TRUE;
  850. } else {
  851. cout << "ERROR while decoding non-standard Cisco extension" << endl;
  852. return FALSE;
  853. }
  854. }
  855. }
  856. }
  857. }
  858. return res;
  859. }
  860. static PBoolean EmbedCiscoTunneledInfo(H323SignalPDU &pdu)
  861. {
  862. static const struct {
  863. Q931::InformationElementCodes ie;
  864. PBoolean dontDelete;
  865. } codes[] = {
  866. { Q931::RedirectingNumberIE, },
  867. { Q931::FacilityIE, },
  868. // { Q931::CallingPartyNumberIE, TRUE },
  869. };
  870. PBoolean res = FALSE;
  871. PBoolean notRedirOnly = FALSE;
  872. Q931 tmpQ931;
  873. Q931 &q931 = pdu.GetQ931();
  874. for(unsigned i = 0; i < ARRAY_LEN(codes); ++i) {
  875. if (q931.HasIE(codes[i].ie)) {
  876. tmpQ931.SetIE(codes[i].ie, q931.GetIE(codes[i].ie));
  877. if (!codes[i].dontDelete)
  878. q931.RemoveIE(codes[i].ie);
  879. if (codes[i].ie != Q931::RedirectingNumberIE)
  880. notRedirOnly = TRUE;
  881. res = TRUE;
  882. }
  883. }
  884. /* Have something to embed */
  885. if (res) {
  886. PBYTEArray msg;
  887. if (!tmpQ931.Encode(msg))
  888. return FALSE;
  889. PBYTEArray ies(msg.GetPointer() + 5, msg.GetSize() - 5);
  890. H225_H323_UU_PDU &uuPDU = pdu.m_h323_uu_pdu;
  891. if(!uuPDU.HasOptionalField(H225_H323_UU_PDU::e_nonStandardControl)) {
  892. uuPDU.IncludeOptionalField(H225_H323_UU_PDU::e_nonStandardControl);
  893. uuPDU.m_nonStandardControl.SetSize(0);
  894. }
  895. H225_NonStandardParameter *np = new H225_NonStandardParameter;
  896. uuPDU.m_nonStandardControl.Append(np);
  897. H225_NonStandardIdentifier &nsi = (*np).m_nonStandardIdentifier;
  898. nsi.SetTag(H225_NonStandardIdentifier::e_h221NonStandard);
  899. H225_H221NonStandard &ns = nsi;
  900. ns.m_t35CountryCode = 181;
  901. ns.m_t35Extension = 0;
  902. ns.m_manufacturerCode = 18;
  903. CISCO_H225_H323_UU_NonStdInfo c;
  904. c.IncludeOptionalField(CISCO_H225_H323_UU_NonStdInfo::e_version);
  905. c.m_version = 0;
  906. if (notRedirOnly) {
  907. c.IncludeOptionalField(CISCO_H225_H323_UU_NonStdInfo::e_protoParam);
  908. CISCO_H225_QsigNonStdInfo &qsigInfo = c.m_protoParam.m_qsigNonStdInfo;
  909. qsigInfo.m_iei = ies[0];
  910. qsigInfo.m_rawMesg = ies;
  911. } else {
  912. c.IncludeOptionalField(CISCO_H225_H323_UU_NonStdInfo::e_commonParam);
  913. c.m_commonParam.m_redirectIEinfo.m_redirectIE = ies;
  914. }
  915. PPER_Stream stream;
  916. c.Encode(stream);
  917. stream.CompleteEncoding();
  918. (*np).m_data = stream;
  919. }
  920. return res;
  921. }
  922. static const char OID_QSIG[] = "1.3.12.9";
  923. static PBoolean FetchQSIGTunneledInfo(Q931 &q931, const H323SignalPDU &pdu)
  924. {
  925. PBoolean res = FALSE;
  926. const H225_H323_UU_PDU &uuPDU = pdu.m_h323_uu_pdu;
  927. if (uuPDU.HasOptionalField(H225_H323_UU_PDU::e_tunnelledSignallingMessage)) {
  928. const H225_H323_UU_PDU_tunnelledSignallingMessage &sig = uuPDU.m_tunnelledSignallingMessage;
  929. const H225_TunnelledProtocol_id &proto = sig.m_tunnelledProtocolID.m_id;
  930. if ((proto.GetTag() == H225_TunnelledProtocol_id::e_tunnelledProtocolObjectID) &&
  931. (((const PASN_ObjectId &)proto).AsString() == OID_QSIG)) {
  932. const H225_ArrayOf_PASN_OctetString &sigs = sig.m_messageContent;
  933. for(int i = 0; i < sigs.GetSize(); ++i) {
  934. const PASN_OctetString &msg = sigs[i];
  935. if (h323debug)
  936. cout << setprecision(0) << "Q.931 message data is " << msg << endl;
  937. if(!q931.Decode((const PBYTEArray &)msg)) {
  938. cout << "Error while decoding Q.931 message" << endl;
  939. return FALSE;
  940. }
  941. res = TRUE;
  942. if (h323debug)
  943. cout << setprecision(0) << "Received QSIG message " << q931 << endl;
  944. }
  945. }
  946. }
  947. return res;
  948. }
  949. static H225_EndpointType *GetEndpointType(H323SignalPDU &pdu)
  950. {
  951. if (!pdu.GetQ931().HasIE(Q931::UserUserIE))
  952. return NULL;
  953. H225_H323_UU_PDU_h323_message_body &body = pdu.m_h323_uu_pdu.m_h323_message_body;
  954. switch (body.GetTag()) {
  955. case H225_H323_UU_PDU_h323_message_body::e_setup:
  956. return &((H225_Setup_UUIE &)body).m_sourceInfo;
  957. case H225_H323_UU_PDU_h323_message_body::e_callProceeding:
  958. return &((H225_CallProceeding_UUIE &)body).m_destinationInfo;
  959. case H225_H323_UU_PDU_h323_message_body::e_connect:
  960. return &((H225_Connect_UUIE &)body).m_destinationInfo;
  961. case H225_H323_UU_PDU_h323_message_body::e_alerting:
  962. return &((H225_Alerting_UUIE &)body).m_destinationInfo;
  963. case H225_H323_UU_PDU_h323_message_body::e_facility:
  964. return &((H225_Facility_UUIE &)body).m_destinationInfo;
  965. case H225_H323_UU_PDU_h323_message_body::e_progress:
  966. return &((H225_Progress_UUIE &)body).m_destinationInfo;
  967. }
  968. return NULL;
  969. }
  970. static PBoolean QSIGTunnelRequested(H323SignalPDU &pdu)
  971. {
  972. H225_EndpointType *epType = GetEndpointType(pdu);
  973. if (epType) {
  974. if (!(*epType).HasOptionalField(H225_EndpointType::e_supportedTunnelledProtocols)) {
  975. return FALSE;
  976. }
  977. H225_ArrayOf_TunnelledProtocol &protos = (*epType).m_supportedTunnelledProtocols;
  978. for (int i = 0; i < protos.GetSize(); ++i)
  979. {
  980. if ((protos[i].GetTag() == H225_TunnelledProtocol_id::e_tunnelledProtocolObjectID) &&
  981. (((const PASN_ObjectId &)protos[i]).AsString() == OID_QSIG)) {
  982. return TRUE;
  983. }
  984. }
  985. }
  986. return FALSE;
  987. }
  988. static PBoolean EmbedQSIGTunneledInfo(H323SignalPDU &pdu)
  989. {
  990. static const Q931::InformationElementCodes codes[] =
  991. { Q931::RedirectingNumberIE, Q931::FacilityIE };
  992. Q931 &q931 = pdu.GetQ931();
  993. PBYTEArray message;
  994. q931.Encode(message);
  995. /* Remove non-standard IEs */
  996. for(unsigned i = 0; i < ARRAY_LEN(codes); ++i) {
  997. if (q931.HasIE(codes[i])) {
  998. q931.RemoveIE(codes[i]);
  999. }
  1000. }
  1001. H225_H323_UU_PDU &uuPDU = pdu.m_h323_uu_pdu;
  1002. H225_EndpointType *epType = GetEndpointType(pdu);
  1003. if (epType) {
  1004. if (!(*epType).HasOptionalField(H225_EndpointType::e_supportedTunnelledProtocols)) {
  1005. (*epType).IncludeOptionalField(H225_EndpointType::e_supportedTunnelledProtocols);
  1006. (*epType).m_supportedTunnelledProtocols.SetSize(0);
  1007. }
  1008. H225_ArrayOf_TunnelledProtocol &protos = (*epType).m_supportedTunnelledProtocols;
  1009. PBoolean addQSIG = TRUE;
  1010. for (int i = 0; i < protos.GetSize(); ++i)
  1011. {
  1012. if ((protos[i].GetTag() == H225_TunnelledProtocol_id::e_tunnelledProtocolObjectID) &&
  1013. (((PASN_ObjectId &)protos[i]).AsString() == OID_QSIG)) {
  1014. addQSIG = FALSE;
  1015. break;
  1016. }
  1017. }
  1018. if (addQSIG) {
  1019. H225_TunnelledProtocol *proto = new H225_TunnelledProtocol;
  1020. (*proto).m_id.SetTag(H225_TunnelledProtocol_id::e_tunnelledProtocolObjectID);
  1021. (PASN_ObjectId &)(proto->m_id) = OID_QSIG;
  1022. protos.Append(proto);
  1023. }
  1024. }
  1025. if (!uuPDU.HasOptionalField(H225_H323_UU_PDU::e_tunnelledSignallingMessage))
  1026. uuPDU.IncludeOptionalField(H225_H323_UU_PDU::e_tunnelledSignallingMessage);
  1027. H225_H323_UU_PDU_tunnelledSignallingMessage &sig = uuPDU.m_tunnelledSignallingMessage;
  1028. H225_TunnelledProtocol_id &proto = sig.m_tunnelledProtocolID.m_id;
  1029. if ((proto.GetTag() != H225_TunnelledProtocol_id::e_tunnelledProtocolObjectID) ||
  1030. (((const PASN_ObjectId &)proto).AsString() != OID_QSIG)) {
  1031. proto.SetTag(H225_TunnelledProtocol_id::e_tunnelledProtocolObjectID);
  1032. (PASN_ObjectId &)proto = OID_QSIG;
  1033. sig.m_messageContent.SetSize(0);
  1034. }
  1035. PASN_OctetString *msg = new PASN_OctetString;
  1036. sig.m_messageContent.Append(msg);
  1037. *msg = message;
  1038. return TRUE;
  1039. }
  1040. PBoolean MyH323Connection::EmbedTunneledInfo(H323SignalPDU &pdu)
  1041. {
  1042. if ((tunnelOptions & H323_TUNNEL_QSIG) || (remoteTunnelOptions & H323_TUNNEL_QSIG))
  1043. EmbedQSIGTunneledInfo(pdu);
  1044. if ((tunnelOptions & H323_TUNNEL_CISCO) || (remoteTunnelOptions & H323_TUNNEL_CISCO))
  1045. EmbedCiscoTunneledInfo(pdu);
  1046. return TRUE;
  1047. }
  1048. /* Handle tunneled messages */
  1049. PBoolean MyH323Connection::HandleSignalPDU(H323SignalPDU &pdu)
  1050. {
  1051. if (pdu.GetQ931().HasIE(Q931::UserUserIE)) {
  1052. Q931 tunneledInfo;
  1053. const Q931 *q931Info;
  1054. q931Info = NULL;
  1055. if (FetchCiscoTunneledInfo(tunneledInfo, pdu)) {
  1056. q931Info = &tunneledInfo;
  1057. remoteTunnelOptions |= H323_TUNNEL_CISCO;
  1058. }
  1059. if (FetchQSIGTunneledInfo(tunneledInfo, pdu)) {
  1060. q931Info = &tunneledInfo;
  1061. remoteTunnelOptions |= H323_TUNNEL_QSIG;
  1062. }
  1063. if (!(remoteTunnelOptions & H323_TUNNEL_QSIG) && QSIGTunnelRequested(pdu)) {
  1064. remoteTunnelOptions |= H323_TUNNEL_QSIG;
  1065. }
  1066. if (q931Info) {
  1067. if (q931Info->HasIE(Q931::RedirectingNumberIE)) {
  1068. pdu.GetQ931().SetIE(Q931::RedirectingNumberIE, q931Info->GetIE(Q931::RedirectingNumberIE));
  1069. if (h323debug) {
  1070. PString number;
  1071. unsigned reason;
  1072. if(q931Info->GetRedirectingNumber(number, NULL, NULL, NULL, NULL, &reason, 0, 0, 0))
  1073. cout << "Got redirection from " << number << ", reason " << reason << endl;
  1074. }
  1075. }
  1076. }
  1077. }
  1078. return H323Connection::HandleSignalPDU(pdu);
  1079. }
  1080. #endif
  1081. PBoolean MyH323Connection::OnReceivedSignalSetup(const H323SignalPDU & setupPDU)
  1082. {
  1083. call_details_t cd;
  1084. if (h323debug) {
  1085. cout << "\t--Received SETUP message" << endl;
  1086. }
  1087. if (connectionState == ShuttingDownConnection)
  1088. return FALSE;
  1089. SetCallDetails(&cd, setupPDU, TRUE);
  1090. /* Notify Asterisk of the request */
  1091. call_options_t *res = on_incoming_call(&cd);
  1092. if (!res) {
  1093. if (h323debug) {
  1094. cout << "\t-- Call Failed" << endl;
  1095. }
  1096. return FALSE;
  1097. }
  1098. SetCallOptions(res, TRUE);
  1099. /* Disable fastStart if requested by remote side */
  1100. if (h245Tunneling && !setupPDU.m_h323_uu_pdu.m_h245Tunneling) {
  1101. masterSlaveDeterminationProcedure->Stop();
  1102. capabilityExchangeProcedure->Stop();
  1103. PTRACE(3, "H225\tFast Start DISABLED!");
  1104. h245Tunneling = FALSE;
  1105. }
  1106. return H323Connection::OnReceivedSignalSetup(setupPDU);
  1107. }
  1108. PBoolean MyH323Connection::OnSendSignalSetup(H323SignalPDU & setupPDU)
  1109. {
  1110. call_details_t cd;
  1111. if (h323debug) {
  1112. cout << "\t-- Sending SETUP message" << endl;
  1113. }
  1114. if (connectionState == ShuttingDownConnection)
  1115. return FALSE;
  1116. if (progressSetup)
  1117. setupPDU.GetQ931().SetProgressIndicator(progressSetup);
  1118. if (redirect_reason >= 0) {
  1119. setupPDU.GetQ931().SetRedirectingNumber(rdnis, 0, 0, 0, 0, redirect_reason);
  1120. /* OpenH323 incorrectly fills number IE when redirecting reason is specified - fix it */
  1121. PBYTEArray IE(setupPDU.GetQ931().GetIE(Q931::RedirectingNumberIE));
  1122. IE[0] = IE[0] & 0x7f;
  1123. IE[1] = IE[1] & 0x7f;
  1124. setupPDU.GetQ931().SetIE(Q931::RedirectingNumberIE, IE);
  1125. }
  1126. if (transfer_capability)
  1127. setupPDU.GetQ931().SetBearerCapabilities((Q931::InformationTransferCapability)(transfer_capability & 0x1f), 1, ((transfer_capability >> 5) & 3));
  1128. SetCallDetails(&cd, setupPDU, FALSE);
  1129. int res = on_outgoing_call(&cd);
  1130. if (!res) {
  1131. if (h323debug) {
  1132. cout << "\t-- Call Failed" << endl;
  1133. }
  1134. return FALSE;
  1135. }
  1136. /* OpenH323 will build calling party information with default
  1137. type and presentation information, so build it to be recorded
  1138. by embedding routines */
  1139. setupPDU.GetQ931().SetCallingPartyNumber(sourceE164, (cid_ton >> 4) & 0x07,
  1140. cid_ton & 0x0f, (cid_presentation >> 5) & 0x03, cid_presentation & 0x1f);
  1141. setupPDU.GetQ931().SetDisplayName(GetDisplayName());
  1142. #ifdef TUNNELLING
  1143. EmbedTunneledInfo(setupPDU);
  1144. #endif
  1145. return H323Connection::OnSendSignalSetup(setupPDU);
  1146. }
  1147. static PBoolean BuildFastStartList(const H323Channel & channel,
  1148. H225_ArrayOf_PASN_OctetString & array,
  1149. H323Channel::Directions reverseDirection)
  1150. {
  1151. H245_OpenLogicalChannel open;
  1152. const H323Capability & capability = channel.GetCapability();
  1153. if (channel.GetDirection() != reverseDirection) {
  1154. if (!capability.OnSendingPDU(open.m_forwardLogicalChannelParameters.m_dataType))
  1155. return FALSE;
  1156. }
  1157. else {
  1158. if (!capability.OnSendingPDU(open.m_reverseLogicalChannelParameters.m_dataType))
  1159. return FALSE;
  1160. open.m_forwardLogicalChannelParameters.m_multiplexParameters.SetTag(
  1161. H245_OpenLogicalChannel_forwardLogicalChannelParameters_multiplexParameters::e_none);
  1162. open.m_forwardLogicalChannelParameters.m_dataType.SetTag(H245_DataType::e_nullData);
  1163. open.IncludeOptionalField(H245_OpenLogicalChannel::e_reverseLogicalChannelParameters);
  1164. }
  1165. if (!channel.OnSendingPDU(open))
  1166. return FALSE;
  1167. PTRACE(4, "H225\tBuild fastStart:\n " << setprecision(2) << open);
  1168. PINDEX last = array.GetSize();
  1169. array.SetSize(last+1);
  1170. array[last].EncodeSubType(open);
  1171. PTRACE(3, "H225\tBuilt fastStart for " << capability);
  1172. return TRUE;
  1173. }
  1174. H323Connection::CallEndReason MyH323Connection::SendSignalSetup(const PString & alias,
  1175. const H323TransportAddress & address)
  1176. {
  1177. // Start the call, first state is asking gatekeeper
  1178. connectionState = AwaitingGatekeeperAdmission;
  1179. // Indicate the direction of call.
  1180. if (alias.IsEmpty())
  1181. remotePartyName = remotePartyAddress = address;
  1182. else {
  1183. remotePartyName = alias;
  1184. remotePartyAddress = alias + '@' + address;
  1185. }
  1186. // Start building the setup PDU to get various ID's
  1187. H323SignalPDU setupPDU;
  1188. H225_Setup_UUIE & setup = setupPDU.BuildSetup(*this, address);
  1189. #ifdef H323_H450
  1190. h450dispatcher->AttachToSetup(setupPDU);
  1191. #endif
  1192. // Save the identifiers generated by BuildSetup
  1193. setupPDU.GetQ931().GetCalledPartyNumber(remotePartyNumber);
  1194. H323TransportAddress gatekeeperRoute = address;
  1195. // Check for gatekeeper and do admission check if have one
  1196. H323Gatekeeper * gatekeeper = endpoint.GetGatekeeper();
  1197. H225_ArrayOf_AliasAddress newAliasAddresses;
  1198. if (gatekeeper != NULL) {
  1199. H323Gatekeeper::AdmissionResponse response;
  1200. response.transportAddress = &gatekeeperRoute;
  1201. response.aliasAddresses = &newAliasAddresses;
  1202. if (!gkAccessTokenOID)
  1203. response.accessTokenData = &gkAccessTokenData;
  1204. while (!gatekeeper->AdmissionRequest(*this, response, alias.IsEmpty())) {
  1205. PTRACE(1, "H225\tGatekeeper refused admission: "
  1206. << (response.rejectReason == UINT_MAX
  1207. ? PString("Transport error")
  1208. : H225_AdmissionRejectReason(response.rejectReason).GetTagName()));
  1209. #ifdef H323_H450
  1210. h4502handler->onReceivedAdmissionReject(H4501_GeneralErrorList::e_notAvailable);
  1211. #endif
  1212. switch (response.rejectReason) {
  1213. case H225_AdmissionRejectReason::e_calledPartyNotRegistered:
  1214. return EndedByNoUser;
  1215. case H225_AdmissionRejectReason::e_requestDenied:
  1216. return EndedByNoBandwidth;
  1217. case H225_AdmissionRejectReason::e_invalidPermission:
  1218. case H225_AdmissionRejectReason::e_securityDenial:
  1219. return EndedBySecurityDenial;
  1220. case H225_AdmissionRejectReason::e_resourceUnavailable:
  1221. return EndedByRemoteBusy;
  1222. case H225_AdmissionRejectReason::e_incompleteAddress:
  1223. if (OnInsufficientDigits())
  1224. break;
  1225. // Then default case
  1226. default:
  1227. return EndedByGatekeeper;
  1228. }
  1229. PString lastRemotePartyName = remotePartyName;
  1230. while (lastRemotePartyName == remotePartyName) {
  1231. Unlock(); // Release the mutex as can deadlock trying to clear call during connect.
  1232. digitsWaitFlag.Wait();
  1233. if (!Lock()) // Lock while checking for shutting down.
  1234. return EndedByCallerAbort;
  1235. }
  1236. }
  1237. mustSendDRQ = TRUE;
  1238. if (response.gatekeeperRouted) {
  1239. setup.IncludeOptionalField(H225_Setup_UUIE::e_endpointIdentifier);
  1240. setup.m_endpointIdentifier = gatekeeper->GetEndpointIdentifier();
  1241. gatekeeperRouted = TRUE;
  1242. }
  1243. }
  1244. #ifdef H323_TRANSNEXUS_OSP
  1245. // check for OSP server (if not using GK)
  1246. if (gatekeeper == NULL) {
  1247. OpalOSP::Provider * ospProvider = endpoint.GetOSPProvider();
  1248. if (ospProvider != NULL) {
  1249. OpalOSP::Transaction * transaction = new OpalOSP::Transaction();
  1250. if (transaction->Open(*ospProvider) != 0) {
  1251. PTRACE(1, "H225\tCannot create OSP transaction");
  1252. return EndedByOSPRefusal;
  1253. }
  1254. OpalOSP::Transaction::DestinationInfo destInfo;
  1255. if (!AuthoriseOSPTransaction(*transaction, destInfo)) {
  1256. delete transaction;
  1257. return EndedByOSPRefusal;
  1258. }
  1259. // save the transaction for use by the call
  1260. ospTransaction = transaction;
  1261. // retrieve the call information
  1262. gatekeeperRoute = destInfo.destinationAddress;
  1263. newAliasAddresses.Append(new H225_AliasAddress(destInfo.calledNumber));
  1264. // insert the token
  1265. setup.IncludeOptionalField(H225_Setup_UUIE::e_tokens);
  1266. destInfo.InsertToken(setup.m_tokens);
  1267. }
  1268. }
  1269. #endif
  1270. // Update the field e_destinationAddress in the SETUP PDU to reflect the new
  1271. // alias received in the ACF (m_destinationInfo).
  1272. if (newAliasAddresses.GetSize() > 0) {
  1273. setup.IncludeOptionalField(H225_Setup_UUIE::e_destinationAddress);
  1274. setup.m_destinationAddress = newAliasAddresses;
  1275. // Update the Q.931 Information Element (if is an E.164 address)
  1276. PString e164 = H323GetAliasAddressE164(newAliasAddresses);
  1277. if (!e164)
  1278. remotePartyNumber = e164;
  1279. }
  1280. if (addAccessTokenToSetup && !gkAccessTokenOID && !gkAccessTokenData.IsEmpty()) {
  1281. PString oid1, oid2;
  1282. PINDEX comma = gkAccessTokenOID.Find(',');
  1283. if (comma == P_MAX_INDEX)
  1284. oid1 = oid2 = gkAccessTokenOID;
  1285. else {
  1286. oid1 = gkAccessTokenOID.Left(comma);
  1287. oid2 = gkAccessTokenOID.Mid(comma+1);
  1288. }
  1289. setup.IncludeOptionalField(H225_Setup_UUIE::e_tokens);
  1290. PINDEX last = setup.m_tokens.GetSize();
  1291. setup.m_tokens.SetSize(last+1);
  1292. setup.m_tokens[last].m_tokenOID = oid1;
  1293. setup.m_tokens[last].IncludeOptionalField(H235_ClearToken::e_nonStandard);
  1294. setup.m_tokens[last].m_nonStandard.m_nonStandardIdentifier = oid2;
  1295. setup.m_tokens[last].m_nonStandard.m_data = gkAccessTokenData;
  1296. }
  1297. if (!signallingChannel->SetRemoteAddress(gatekeeperRoute)) {
  1298. PTRACE(1, "H225\tInvalid "
  1299. << (gatekeeperRoute != address ? "gatekeeper" : "user")
  1300. << " supplied address: \"" << gatekeeperRoute << '"');
  1301. connectionState = AwaitingTransportConnect;
  1302. return EndedByConnectFail;
  1303. }
  1304. // Do the transport connect
  1305. connectionState = AwaitingTransportConnect;
  1306. // Release the mutex as can deadlock trying to clear call during connect.
  1307. Unlock();
  1308. signallingChannel->SetWriteTimeout(100);
  1309. PBoolean connectFailed = !signallingChannel->Connect();
  1310. // Lock while checking for shutting down.
  1311. if (!Lock())
  1312. return EndedByCallerAbort;
  1313. // See if transport connect failed, abort if so.
  1314. if (connectFailed) {
  1315. connectionState = NoConnectionActive;
  1316. switch (signallingChannel->GetErrorNumber()) {
  1317. case ENETUNREACH :
  1318. return EndedByUnreachable;
  1319. case ECONNREFUSED :
  1320. return EndedByNoEndPoint;
  1321. case ETIMEDOUT :
  1322. return EndedByHostOffline;
  1323. }
  1324. return EndedByConnectFail;
  1325. }
  1326. PTRACE(3, "H225\tSending Setup PDU");
  1327. connectionState = AwaitingSignalConnect;
  1328. // Put in all the signalling addresses for link
  1329. setup.IncludeOptionalField(H225_Setup_UUIE::e_sourceCallSignalAddress);
  1330. signallingChannel->SetUpTransportPDU(setup.m_sourceCallSignalAddress, TRUE);
  1331. if (!setup.HasOptionalField(H225_Setup_UUIE::e_destCallSignalAddress)) {
  1332. setup.IncludeOptionalField(H225_Setup_UUIE::e_destCallSignalAddress);
  1333. signallingChannel->SetUpTransportPDU(setup.m_destCallSignalAddress, FALSE);
  1334. }
  1335. // If a standard call do Fast Start (if required)
  1336. if (setup.m_conferenceGoal.GetTag() == H225_Setup_UUIE_conferenceGoal::e_create) {
  1337. // Get the local capabilities before fast start is handled
  1338. OnSetLocalCapabilities();
  1339. // Ask the application what channels to open
  1340. PTRACE(3, "H225\tCheck for Fast start by local endpoint");
  1341. fastStartChannels.RemoveAll();
  1342. OnSelectLogicalChannels();
  1343. // If application called OpenLogicalChannel, put in the fastStart field
  1344. if (!fastStartChannels.IsEmpty()) {
  1345. PTRACE(3, "H225\tFast start begun by local endpoint");
  1346. for (PINDEX i = 0; i < fastStartChannels.GetSize(); i++)
  1347. BuildFastStartList(fastStartChannels[i], setup.m_fastStart, H323Channel::IsReceiver);
  1348. if (setup.m_fastStart.GetSize() > 0)
  1349. setup.IncludeOptionalField(H225_Setup_UUIE::e_fastStart);
  1350. }
  1351. // Search the capability set and see if we have video capability
  1352. for (PINDEX i = 0; i < localCapabilities.GetSize(); i++) {
  1353. switch (localCapabilities[i].GetMainType()) {
  1354. case H323Capability::e_Audio:
  1355. case H323Capability::e_UserInput:
  1356. break;
  1357. default: // Is video or other data (eg T.120)
  1358. setupPDU.GetQ931().SetBearerCapabilities(Q931::TransferUnrestrictedDigital, 6);
  1359. i = localCapabilities.GetSize(); // Break out of the for loop
  1360. break;
  1361. }
  1362. }
  1363. }
  1364. if (!OnSendSignalSetup(setupPDU))
  1365. return EndedByNoAccept;
  1366. // Do this again (was done when PDU was constructed) in case
  1367. // OnSendSignalSetup() changed something.
  1368. // setupPDU.SetQ931Fields(*this, TRUE);
  1369. setupPDU.GetQ931().GetCalledPartyNumber(remotePartyNumber);
  1370. fastStartState = FastStartDisabled;
  1371. PBoolean set_lastPDUWasH245inSETUP = FALSE;
  1372. if (h245Tunneling && doH245inSETUP) {
  1373. h245TunnelTxPDU = &setupPDU;
  1374. // Try and start the master/slave and capability exchange through the tunnel
  1375. // Note: this used to be disallowed but is now allowed as of H323v4
  1376. PBoolean ok = StartControlNegotiations();
  1377. h245TunnelTxPDU = NULL;
  1378. if (!ok)
  1379. return EndedByTransportFail;
  1380. if (setup.m_fastStart.GetSize() > 0) {
  1381. // Now if fast start as well need to put this in setup specific field
  1382. // and not the generic H.245 tunneling field
  1383. setup.IncludeOptionalField(H225_Setup_UUIE::e_parallelH245Control);
  1384. setup.m_parallelH245Control = setupPDU.m_h323_uu_pdu.m_h245Control;
  1385. setupPDU.m_h323_uu_pdu.RemoveOptionalField(H225_H323_UU_PDU::e_h245Control);
  1386. set_lastPDUWasH245inSETUP = TRUE;
  1387. }
  1388. }
  1389. // Send the initial PDU
  1390. setupTime = PTime();
  1391. if (!WriteSignalPDU(setupPDU))
  1392. return EndedByTransportFail;
  1393. // WriteSignalPDU always resets lastPDUWasH245inSETUP.
  1394. // So set it here if required
  1395. if (set_lastPDUWasH245inSETUP)
  1396. lastPDUWasH245inSETUP = TRUE;
  1397. // Set timeout for remote party to answer the call
  1398. signallingChannel->SetReadTimeout(endpoint.GetSignallingChannelCallTimeout());
  1399. return NumCallEndReasons;
  1400. }
  1401. PBoolean MyH323Connection::OnSendReleaseComplete(H323SignalPDU & releaseCompletePDU)
  1402. {
  1403. if (h323debug) {
  1404. cout << "\t-- Sending RELEASE COMPLETE" << endl;
  1405. }
  1406. if (cause > 0)
  1407. releaseCompletePDU.GetQ931().SetCause((Q931::CauseValues)cause);
  1408. #ifdef TUNNELLING
  1409. EmbedTunneledInfo(releaseCompletePDU);
  1410. #endif
  1411. return H323Connection::OnSendReleaseComplete(releaseCompletePDU);
  1412. }
  1413. PBoolean MyH323Connection::OnReceivedFacility(const H323SignalPDU & pdu)
  1414. {
  1415. if (h323debug) {
  1416. cout << "\t-- Received Facility message... " << endl;
  1417. }
  1418. return H323Connection::OnReceivedFacility(pdu);
  1419. }
  1420. void MyH323Connection::OnReceivedReleaseComplete(const H323SignalPDU & pdu)
  1421. {
  1422. if (h323debug) {
  1423. cout << "\t-- Received RELEASE COMPLETE message..." << endl;
  1424. }
  1425. if (on_hangup)
  1426. on_hangup(GetCallReference(), (const char *)GetCallToken(), pdu.GetQ931().GetCause());
  1427. return H323Connection::OnReceivedReleaseComplete(pdu);
  1428. }
  1429. PBoolean MyH323Connection::OnClosingLogicalChannel(H323Channel & channel)
  1430. {
  1431. if (h323debug) {
  1432. cout << "\t-- Closing logical channel..." << endl;
  1433. }
  1434. return H323Connection::OnClosingLogicalChannel(channel);
  1435. }
  1436. void MyH323Connection::SendUserInputTone(char tone, unsigned duration, unsigned logicalChannel, unsigned rtpTimestamp)
  1437. {
  1438. SendUserInputModes mode = GetRealSendUserInputMode();
  1439. // That is recursive call... Why?
  1440. // on_receive_digit(GetCallReference(), tone, (const char *)GetCallToken());
  1441. if ((tone != ' ') || (mode == SendUserInputAsTone) || (mode == SendUserInputAsInlineRFC2833)) {
  1442. if (h323debug) {
  1443. cout << "\t-- Sending user input tone (" << tone << ") to remote" << endl;
  1444. }
  1445. H323Connection::SendUserInputTone(tone, duration);
  1446. }
  1447. }
  1448. void MyH323Connection::OnUserInputTone(char tone, unsigned duration, unsigned logicalChannel, unsigned rtpTimestamp)
  1449. {
  1450. /* Why we should check this? */
  1451. if ((dtmfMode & (H323_DTMF_CISCO | H323_DTMF_RFC2833 | H323_DTMF_SIGNAL)) != 0) {
  1452. if (h323debug) {
  1453. cout << "\t-- Received user input tone (" << tone << ") from remote" << endl;
  1454. }
  1455. on_receive_digit(GetCallReference(), tone, (const char *)GetCallToken(), duration);
  1456. }
  1457. }
  1458. void MyH323Connection::OnUserInputString(const PString &value)
  1459. {
  1460. if (h323debug) {
  1461. cout << "\t-- Received user input string (" << value << ") from remote." << endl;
  1462. }
  1463. on_receive_digit(GetCallReference(), value[0], (const char *)GetCallToken(), 0);
  1464. }
  1465. void MyH323Connection::OnSendCapabilitySet(H245_TerminalCapabilitySet & pdu)
  1466. {
  1467. PINDEX i;
  1468. H323Connection::OnSendCapabilitySet(pdu);
  1469. H245_ArrayOf_CapabilityTableEntry & tables = pdu.m_capabilityTable;
  1470. for(i = 0; i < tables.GetSize(); i++)
  1471. {
  1472. H245_CapabilityTableEntry & entry = tables[i];
  1473. if (entry.HasOptionalField(H245_CapabilityTableEntry::e_capability)) {
  1474. H245_Capability & cap = entry.m_capability;
  1475. if (cap.GetTag() == H245_Capability::e_receiveRTPAudioTelephonyEventCapability) {
  1476. H245_AudioTelephonyEventCapability & atec = cap;
  1477. atec.m_dynamicRTPPayloadType = dtmfCodec[0];
  1478. // on_set_rfc2833_payload(GetCallReference(), (const char *)GetCallToken(), (int)dtmfCodec[0]);
  1479. #ifdef PTRACING
  1480. if (h323debug) {
  1481. cout << "\t-- Receiving RFC2833 on payload " <<
  1482. atec.m_dynamicRTPPayloadType << endl;
  1483. }
  1484. #endif
  1485. }
  1486. }
  1487. }
  1488. }
  1489. void MyH323Connection::OnSetLocalCapabilities()
  1490. {
  1491. if (on_setcapabilities)
  1492. on_setcapabilities(GetCallReference(), (const char *)callToken);
  1493. }
  1494. PBoolean MyH323Connection::OnReceivedCapabilitySet(const H323Capabilities & remoteCaps,
  1495. const H245_MultiplexCapability * muxCap,
  1496. H245_TerminalCapabilitySetReject & reject)
  1497. {
  1498. struct __codec__ {
  1499. unsigned int asterisk_codec;
  1500. unsigned int h245_cap;
  1501. const char *oid;
  1502. const char *formatName;
  1503. };
  1504. static const struct __codec__ codecs[] = {
  1505. { AST_FORMAT_G723_1, H245_AudioCapability::e_g7231 },
  1506. { AST_FORMAT_GSM, H245_AudioCapability::e_gsmFullRate },
  1507. { AST_FORMAT_ULAW, H245_AudioCapability::e_g711Ulaw64k },
  1508. { AST_FORMAT_ALAW, H245_AudioCapability::e_g711Alaw64k },
  1509. { AST_FORMAT_G729A, H245_AudioCapability::e_g729AnnexA },
  1510. { AST_FORMAT_G729A, H245_AudioCapability::e_g729 },
  1511. { AST_FORMAT_G726_AAL2, H245_AudioCapability::e_nonStandard, NULL, CISCO_G726r32 },
  1512. #ifdef AST_FORMAT_MODEM
  1513. { AST_FORMAT_MODEM, H245_DataApplicationCapability_application::e_t38fax },
  1514. #endif
  1515. { 0 }
  1516. };
  1517. #if 0
  1518. static const struct __codec__ vcodecs[] = {
  1519. #ifdef HAVE_H261
  1520. { AST_FORMAT_H261, H245_VideoCapability::e_h261VideoCapability },
  1521. #endif
  1522. #ifdef HAVE_H263
  1523. { AST_FORMAT_H263, H245_VideoCapability::e_h263VideoCapability },
  1524. #endif
  1525. #ifdef HAVE_H264
  1526. { AST_FORMAT_H264, H245_VideoCapability::e_genericVideoCapability, "0.0.8.241.0.0.1" },
  1527. #endif
  1528. { 0 }
  1529. };
  1530. #endif
  1531. struct ast_codec_pref prefs;
  1532. RTP_DataFrame::PayloadTypes pt;
  1533. if (!H323Connection::OnReceivedCapabilitySet(remoteCaps, muxCap, reject)) {
  1534. return FALSE;
  1535. }
  1536. memset(&prefs, 0, sizeof(prefs));
  1537. int peer_capabilities = 0;
  1538. for (int i = 0; i < remoteCapabilities.GetSize(); ++i) {
  1539. unsigned int subType = remoteCapabilities[i].GetSubType();
  1540. if (h323debug) {
  1541. cout << "Peer capability is " << remoteCapabilities[i] << endl;
  1542. }
  1543. switch(remoteCapabilities[i].GetMainType()) {
  1544. case H323Capability::e_Audio:
  1545. for (int x = 0; codecs[x].asterisk_codec > 0; ++x) {
  1546. if ((subType == codecs[x].h245_cap) && (!codecs[x].formatName || (!strcmp(codecs[x].formatName, (const char *)remoteCapabilities[i].GetFormatName())))) {
  1547. int ast_codec = codecs[x].asterisk_codec;
  1548. int ms = 0;
  1549. struct ast_format tmpfmt;
  1550. if (!(peer_capabilities & ast_format_id_to_old_bitfield((enum ast_format_id) ast_codec))) {
  1551. struct ast_format_list format;
  1552. ast_codec_pref_append(&prefs, ast_format_set(&tmpfmt, (enum ast_format_id) ast_codec, 0));
  1553. format = ast_codec_pref_getsize(&prefs, &tmpfmt);
  1554. if ((ast_codec == AST_FORMAT_ALAW) || (ast_codec == AST_FORMAT_ULAW)) {
  1555. ms = remoteCapabilities[i].GetTxFramesInPacket();
  1556. } else
  1557. ms = remoteCapabilities[i].GetTxFramesInPacket() * format.inc_ms;
  1558. ast_codec_pref_setsize(&prefs, &tmpfmt, ms);
  1559. }
  1560. if (h323debug) {
  1561. cout << "Found peer capability " << remoteCapabilities[i] << ", Asterisk code is " << ast_codec << ", frame size (in ms) is " << ms << endl;
  1562. }
  1563. peer_capabilities |= ast_format_id_to_old_bitfield((enum ast_format_id) ast_codec);
  1564. }
  1565. }
  1566. break;
  1567. case H323Capability::e_Data:
  1568. if (!strcmp((const char *)remoteCapabilities[i].GetFormatName(), CISCO_DTMF_RELAY)) {
  1569. pt = remoteCapabilities[i].GetPayloadType();
  1570. if ((dtmfMode & H323_DTMF_CISCO) != 0) {
  1571. on_set_rfc2833_payload(GetCallReference(), (const char *)GetCallToken(), (int)pt, 1);
  1572. // if (sendUserInputMode == SendUserInputAsTone)
  1573. // sendUserInputMode = SendUserInputAsInlineRFC2833;
  1574. }
  1575. #ifdef PTRACING
  1576. if (h323debug) {
  1577. cout << "\t-- Outbound Cisco RTP DTMF on payload " << pt << endl;
  1578. }
  1579. #endif
  1580. }
  1581. break;
  1582. case H323Capability::e_UserInput:
  1583. if (!strcmp((const char *)remoteCapabilities[i].GetFormatName(), H323_UserInputCapability::SubTypeNames[H323_UserInputCapability::SignalToneRFC2833])) {
  1584. pt = remoteCapabilities[i].GetPayloadType();
  1585. if ((dtmfMode & H323_DTMF_RFC2833) != 0) {
  1586. on_set_rfc2833_payload(GetCallReference(), (const char *)GetCallToken(), (int)pt, 0);
  1587. // if (sendUserInputMode == SendUserInputAsTone)
  1588. // sendUserInputMode = SendUserInputAsInlineRFC2833;
  1589. }
  1590. #ifdef PTRACING
  1591. if (h323debug) {
  1592. cout << "\t-- Outbound RFC2833 on payload " << pt << endl;
  1593. }
  1594. #endif
  1595. }
  1596. break;
  1597. #if 0
  1598. case H323Capability::e_Video:
  1599. for (int x = 0; vcodecs[x].asterisk_codec > 0; ++x) {
  1600. if (subType == vcodecs[x].h245_cap) {
  1601. H245_CapabilityIdentifier *cap = NULL;
  1602. H245_GenericCapability y;
  1603. if (vcodecs[x].oid) {
  1604. cap = new H245_CapabilityIdentifier(H245_CapabilityIdentifier::e_standard);
  1605. PASN_ObjectId &object_id = *cap;
  1606. object_id = vcodecs[x].oid;
  1607. y.m_capabilityIdentifier = *cap;
  1608. }
  1609. if ((subType != H245_VideoCapability::e_genericVideoCapability) ||
  1610. (vcodecs[x].oid && ((const H323GenericVideoCapability &)remoteCapabilities[i]).IsGenericMatch((const H245_GenericCapability)y))) {
  1611. if (h323debug) {
  1612. cout << "Found peer video capability " << remoteCapabilities[i] << ", Asterisk code is " << vcodecs[x].asterisk_codec << endl;
  1613. }
  1614. peer_capabilities |= vcodecs[x].asterisk_codec;
  1615. }
  1616. if (cap)
  1617. delete(cap);
  1618. }
  1619. }
  1620. break;
  1621. #endif
  1622. default:
  1623. break;
  1624. }
  1625. }
  1626. #if 0
  1627. redir_capabilities &= peer_capabilities;
  1628. #endif
  1629. if (on_setpeercapabilities)
  1630. on_setpeercapabilities(GetCallReference(), (const char *)callToken, peer_capabilities, &prefs);
  1631. return TRUE;
  1632. }
  1633. H323Channel * MyH323Connection::CreateRealTimeLogicalChannel(const H323Capability & capability,
  1634. H323Channel::Directions dir,
  1635. unsigned sessionID,
  1636. const H245_H2250LogicalChannelParameters * /*param*/,
  1637. RTP_QOS * /*param*/ )
  1638. {
  1639. /* Do not open tx channel when transmitter has been paused by empty TCS */
  1640. if ((dir == H323Channel::IsTransmitter) && transmitterSidePaused)
  1641. return NULL;
  1642. return new MyH323_ExternalRTPChannel(*this, capability, dir, sessionID);
  1643. }
  1644. /** This callback function is invoked once upon creation of each
  1645. * channel for an H323 session
  1646. */
  1647. PBoolean MyH323Connection::OnStartLogicalChannel(H323Channel & channel)
  1648. {
  1649. /* Increase the count of channels we have open */
  1650. channelsOpen++;
  1651. if (h323debug) {
  1652. cout << "\t-- Started logical channel: "
  1653. << ((channel.GetDirection() == H323Channel::IsTransmitter) ? "sending " : ((channel.GetDirection() == H323Channel::IsReceiver) ? "receiving " : " "))
  1654. << (const char *)(channel.GetCapability()).GetFormatName() << endl;
  1655. cout << "\t\t-- channelsOpen = " << channelsOpen << endl;
  1656. }
  1657. return connectionState != ShuttingDownConnection;
  1658. }
  1659. void MyH323Connection::SetCapabilities(int caps, int dtmf_mode, void *_prefs, int pref_codec)
  1660. {
  1661. PINDEX lastcap = -1; /* last common capability index */
  1662. int alreadysent = 0;
  1663. int codec;
  1664. int x, y;
  1665. struct ast_codec_pref *prefs = (struct ast_codec_pref *)_prefs;
  1666. struct ast_format_list format;
  1667. int frames_per_packet;
  1668. struct ast_format tmpfmt;
  1669. H323Capability *cap;
  1670. localCapabilities.RemoveAll();
  1671. /* Add audio codecs in preference order first, then
  1672. audio codecs without preference as allowed by mask */
  1673. for (y = 0, x = -1; x < 32 + 32; ++x) {
  1674. ast_format_clear(&tmpfmt);
  1675. if (x < 0)
  1676. codec = pref_codec;
  1677. else if (y || (!(ast_codec_pref_index(prefs, x, &tmpfmt)))) {
  1678. if (!y)
  1679. y = 1;
  1680. else
  1681. y <<= 1;
  1682. codec = y;
  1683. }
  1684. if (tmpfmt.id) {
  1685. codec = ast_format_to_old_bitfield(&tmpfmt);
  1686. }
  1687. if (!(caps & codec) || (alreadysent & codec) || (AST_FORMAT_GET_TYPE(ast_format_id_from_old_bitfield(codec)) != AST_FORMAT_TYPE_AUDIO))
  1688. continue;
  1689. alreadysent |= codec;
  1690. /* format.cur_ms will be set to default if packetization is not explicitly set */
  1691. format = ast_codec_pref_getsize(prefs, ast_format_from_old_bitfield(&tmpfmt, codec));
  1692. frames_per_packet = (format.inc_ms ? format.cur_ms / format.inc_ms : format.cur_ms);
  1693. switch(ast_format_id_from_old_bitfield(codec)) {
  1694. #if 0
  1695. case AST_FORMAT_SPEEX:
  1696. /* Not real sure if Asterisk acutally supports all
  1697. of the various different bit rates so add them
  1698. all and figure it out later*/
  1699. lastcap = localCapabilities.SetCapability(0, 0, new SpeexNarrow2AudioCapability());
  1700. lastcap = localCapabilities.SetCapability(0, 0, new SpeexNarrow3AudioCapability());
  1701. lastcap = localCapabilities.SetCapability(0, 0, new SpeexNarrow4AudioCapability());
  1702. lastcap = localCapabilities.SetCapability(0, 0, new SpeexNarrow5AudioCapability());
  1703. lastcap = localCapabilities.SetCapability(0, 0, new SpeexNarrow6AudioCapability());
  1704. break;
  1705. #endif
  1706. case AST_FORMAT_G729A:
  1707. AST_G729ACapability *g729aCap;
  1708. AST_G729Capability *g729Cap;
  1709. lastcap = localCapabilities.SetCapability(0, 0, g729aCap = new AST_G729ACapability(frames_per_packet));
  1710. lastcap = localCapabilities.SetCapability(0, 0, g729Cap = new AST_G729Capability(frames_per_packet));
  1711. g729aCap->SetTxFramesInPacket(format.cur_ms);
  1712. g729Cap->SetTxFramesInPacket(format.cur_ms);
  1713. break;
  1714. case AST_FORMAT_G723_1:
  1715. AST_G7231Capability *g7231Cap;
  1716. lastcap = localCapabilities.SetCapability(0, 0, g7231Cap = new AST_G7231Capability(frames_per_packet, TRUE));
  1717. g7231Cap->SetTxFramesInPacket(format.cur_ms);
  1718. lastcap = localCapabilities.SetCapability(0, 0, g7231Cap = new AST_G7231Capability(frames_per_packet, FALSE));
  1719. g7231Cap->SetTxFramesInPacket(format.cur_ms);
  1720. break;
  1721. case AST_FORMAT_GSM:
  1722. AST_GSM0610Capability *gsmCap;
  1723. lastcap = localCapabilities.SetCapability(0, 0, gsmCap = new AST_GSM0610Capability(frames_per_packet));
  1724. gsmCap->SetTxFramesInPacket(format.cur_ms);
  1725. break;
  1726. case AST_FORMAT_ULAW:
  1727. AST_G711Capability *g711uCap;
  1728. lastcap = localCapabilities.SetCapability(0, 0, g711uCap = new AST_G711Capability(format.cur_ms, H323_G711Capability::muLaw));
  1729. g711uCap->SetTxFramesInPacket(format.cur_ms);
  1730. break;
  1731. case AST_FORMAT_ALAW:
  1732. AST_G711Capability *g711aCap;
  1733. lastcap = localCapabilities.SetCapability(0, 0, g711aCap = new AST_G711Capability(format.cur_ms, H323_G711Capability::ALaw));
  1734. g711aCap->SetTxFramesInPacket(format.cur_ms);
  1735. break;
  1736. case AST_FORMAT_G726_AAL2:
  1737. AST_CiscoG726Capability *g726Cap;
  1738. lastcap = localCapabilities.SetCapability(0, 0, g726Cap = new AST_CiscoG726Capability(frames_per_packet));
  1739. g726Cap->SetTxFramesInPacket(format.cur_ms);
  1740. break;
  1741. default:
  1742. alreadysent &= ~codec;
  1743. break;
  1744. }
  1745. }
  1746. cap = new H323_UserInputCapability(H323_UserInputCapability::HookFlashH245);
  1747. if (cap && cap->IsUsable(*this)) {
  1748. lastcap++;
  1749. lastcap = localCapabilities.SetCapability(0, lastcap, cap);
  1750. } else {
  1751. delete cap; /* Capability is not usable */
  1752. }
  1753. dtmfMode = dtmf_mode;
  1754. if (h323debug) {
  1755. cout << "DTMF mode is " << (int)dtmfMode << endl;
  1756. }
  1757. if (dtmfMode) {
  1758. lastcap++;
  1759. if (dtmfMode == H323_DTMF_INBAND) {
  1760. cap = new H323_UserInputCapability(H323_UserInputCapability::BasicString);
  1761. if (cap && cap->IsUsable(*this)) {
  1762. lastcap = localCapabilities.SetCapability(0, lastcap, cap);
  1763. } else {
  1764. delete cap; /* Capability is not usable */
  1765. }
  1766. sendUserInputMode = SendUserInputAsString;
  1767. } else {
  1768. if ((dtmfMode & H323_DTMF_RFC2833) != 0) {
  1769. cap = new H323_UserInputCapability(H323_UserInputCapability::SignalToneRFC2833);
  1770. if (cap && cap->IsUsable(*this))
  1771. lastcap = localCapabilities.SetCapability(0, lastcap, cap);
  1772. else {
  1773. dtmfMode |= H323_DTMF_SIGNAL;
  1774. delete cap; /* Capability is not usable */
  1775. }
  1776. }
  1777. if ((dtmfMode & H323_DTMF_CISCO) != 0) {
  1778. /* Try Cisco's RTP DTMF relay too, but prefer RFC2833 or h245-signal */
  1779. cap = new AST_CiscoDtmfCapability();
  1780. if (cap && cap->IsUsable(*this)) {
  1781. lastcap = localCapabilities.SetCapability(0, lastcap, cap);
  1782. /* We cannot send Cisco RTP DTMFs, use h245-signal instead */
  1783. dtmfMode |= H323_DTMF_SIGNAL;
  1784. } else {
  1785. dtmfMode |= H323_DTMF_SIGNAL;
  1786. delete cap; /* Capability is not usable */
  1787. }
  1788. }
  1789. if ((dtmfMode & H323_DTMF_SIGNAL) != 0) {
  1790. /* Cisco usually sends DTMF correctly only through h245-alphanumeric or h245-signal */
  1791. cap = new H323_UserInputCapability(H323_UserInputCapability::SignalToneH245);
  1792. if (cap && cap->IsUsable(*this))
  1793. lastcap = localCapabilities.SetCapability(0, lastcap, cap);
  1794. else
  1795. delete cap; /* Capability is not usable */
  1796. }
  1797. sendUserInputMode = SendUserInputAsTone; /* RFC2833 transmission handled at Asterisk level */
  1798. }
  1799. }
  1800. if (h323debug) {
  1801. cout << "Allowed Codecs for " << GetCallToken() << " (" << GetSignallingChannel()->GetLocalAddress() << "):\n\t" << setprecision(2) << localCapabilities << endl;
  1802. }
  1803. }
  1804. PBoolean MyH323Connection::StartControlChannel(const H225_TransportAddress & h245Address)
  1805. {
  1806. // Check that it is an IP address, all we support at the moment
  1807. if (h245Address.GetTag() != H225_TransportAddress::e_ipAddress
  1808. #if P_HAS_IPV6
  1809. && h245Address.GetTag() != H225_TransportAddress::e_ip6Address
  1810. #endif
  1811. ) {
  1812. PTRACE(1, "H225\tConnect of H245 failed: Unsupported transport");
  1813. return FALSE;
  1814. }
  1815. // Already have the H245 channel up.
  1816. if (controlChannel != NULL)
  1817. return TRUE;
  1818. PIPSocket::Address addr;
  1819. WORD port;
  1820. GetSignallingChannel()->GetLocalAddress().GetIpAndPort(addr, port);
  1821. if (addr) {
  1822. if (h323debug)
  1823. cout << "Using " << addr << " for outbound H.245 transport" << endl;
  1824. controlChannel = new MyH323TransportTCP(endpoint, addr);
  1825. } else
  1826. controlChannel = new MyH323TransportTCP(endpoint);
  1827. if (!controlChannel->SetRemoteAddress(h245Address)) {
  1828. PTRACE(1, "H225\tCould not extract H245 address");
  1829. delete controlChannel;
  1830. controlChannel = NULL;
  1831. return FALSE;
  1832. }
  1833. if (!controlChannel->Connect()) {
  1834. PTRACE(1, "H225\tConnect of H245 failed: " << controlChannel->GetErrorText());
  1835. delete controlChannel;
  1836. controlChannel = NULL;
  1837. return FALSE;
  1838. }
  1839. controlChannel->StartControlChannel(*this);
  1840. return TRUE;
  1841. }
  1842. #ifdef H323_H450
  1843. void MyH323Connection::OnReceivedLocalCallHold(int linkedId)
  1844. {
  1845. if (on_hold)
  1846. on_hold(GetCallReference(), (const char *)GetCallToken(), 1);
  1847. }
  1848. void MyH323Connection::OnReceivedLocalCallRetrieve(int linkedId)
  1849. {
  1850. if (on_hold)
  1851. on_hold(GetCallReference(), (const char *)GetCallToken(), 0);
  1852. }
  1853. #endif
  1854. void MyH323Connection::MyHoldCall(PBoolean isHold)
  1855. {
  1856. if (((holdHandling & H323_HOLD_NOTIFY) != 0) || ((holdHandling & H323_HOLD_Q931ONLY) != 0)) {
  1857. PBYTEArray x ((const BYTE *)(isHold ? "\xF9" : "\xFA"), 1);
  1858. H323SignalPDU signal;
  1859. signal.BuildNotify(*this);
  1860. signal.GetQ931().SetIE((Q931::InformationElementCodes)39 /* Q931::NotifyIE */, x);
  1861. if (h323debug)
  1862. cout << "Sending " << (isHold ? "HOLD" : "RETRIEVE") << " notification: " << signal << endl;
  1863. if ((holdHandling & H323_HOLD_Q931ONLY) != 0) {
  1864. PBYTEArray rawData;
  1865. signal.GetQ931().RemoveIE(Q931::UserUserIE);
  1866. signal.GetQ931().Encode(rawData);
  1867. signallingChannel->WritePDU(rawData);
  1868. } else
  1869. WriteSignalPDU(signal);
  1870. }
  1871. #ifdef H323_H450
  1872. if ((holdHandling & H323_HOLD_H450) != 0) {
  1873. if (isHold)
  1874. h4504handler->HoldCall(TRUE);
  1875. else if (IsLocalHold())
  1876. h4504handler->RetrieveCall();
  1877. }
  1878. #endif
  1879. }
  1880. /* MyH323_ExternalRTPChannel */
  1881. MyH323_ExternalRTPChannel::MyH323_ExternalRTPChannel(MyH323Connection & connection,
  1882. const H323Capability & capability,
  1883. Directions direction,
  1884. unsigned id)
  1885. : H323_ExternalRTPChannel::H323_ExternalRTPChannel(connection, capability, direction, id)
  1886. {
  1887. struct rtp_info *info;
  1888. /* Determine the Local (A side) IP Address and port */
  1889. info = on_external_rtp_create(connection.GetCallReference(), (const char *)connection.GetCallToken());
  1890. if (!info) {
  1891. cout << "\tERROR: on_external_rtp_create failure" << endl;
  1892. return;
  1893. } else {
  1894. localIpAddr = info->addr;
  1895. localPort = info->port;
  1896. /* tell the H.323 stack */
  1897. SetExternalAddress(H323TransportAddress(localIpAddr, localPort), H323TransportAddress(localIpAddr, localPort + 1));
  1898. /* clean up allocated memory */
  1899. ast_free(info);
  1900. }
  1901. /* Get the payload code */
  1902. OpalMediaFormat format(capability.GetFormatName(), FALSE);
  1903. payloadCode = format.GetPayloadType();
  1904. }
  1905. MyH323_ExternalRTPChannel::~MyH323_ExternalRTPChannel()
  1906. {
  1907. if (h323debug) {
  1908. cout << "\tExternalRTPChannel Destroyed" << endl;
  1909. }
  1910. }
  1911. PBoolean MyH323_ExternalRTPChannel::Start(void)
  1912. {
  1913. /* Call ancestor first */
  1914. if (!H323_ExternalRTPChannel::Start()) {
  1915. return FALSE;
  1916. }
  1917. if (h323debug) {
  1918. cout << "\t\tExternal RTP Session Starting" << endl;
  1919. cout << "\t\tRTP channel id " << sessionID << " parameters:" << endl;
  1920. }
  1921. /* Collect the remote information */
  1922. H323_ExternalRTPChannel::GetRemoteAddress(remoteIpAddr, remotePort);
  1923. if (h323debug) {
  1924. cout << "\t\t-- remoteIpAddress: " << remoteIpAddr << endl;
  1925. cout << "\t\t-- remotePort: " << remotePort << endl;
  1926. cout << "\t\t-- ExternalIpAddress: " << localIpAddr << endl;
  1927. cout << "\t\t-- ExternalPort: " << localPort << endl;
  1928. }
  1929. /* Notify Asterisk of remote RTP information */
  1930. on_start_rtp_channel(connection.GetCallReference(), (const char *)remoteIpAddr.AsString(), remotePort,
  1931. (const char *)connection.GetCallToken(), (int)payloadCode);
  1932. return TRUE;
  1933. }
  1934. PBoolean MyH323_ExternalRTPChannel::OnReceivedAckPDU(const H245_H2250LogicalChannelAckParameters & param)
  1935. {
  1936. if (h323debug) {
  1937. cout << " MyH323_ExternalRTPChannel::OnReceivedAckPDU" << endl;
  1938. }
  1939. if (H323_ExternalRTPChannel::OnReceivedAckPDU(param)) {
  1940. GetRemoteAddress(remoteIpAddr, remotePort);
  1941. if (h323debug) {
  1942. cout << " -- remoteIpAddress: " << remoteIpAddr << endl;
  1943. cout << " -- remotePort: " << remotePort << endl;
  1944. }
  1945. on_start_rtp_channel(connection.GetCallReference(), (const char *)remoteIpAddr.AsString(),
  1946. remotePort, (const char *)connection.GetCallToken(), (int)payloadCode);
  1947. return TRUE;
  1948. }
  1949. return FALSE;
  1950. }
  1951. #ifdef H323_H450
  1952. MyH4504Handler::MyH4504Handler(MyH323Connection &_conn, H450xDispatcher &_disp)
  1953. :H4504Handler(_conn, _disp)
  1954. {
  1955. conn = &_conn;
  1956. }
  1957. void MyH4504Handler::OnReceivedLocalCallHold(int linkedId)
  1958. {
  1959. if (conn) {
  1960. conn->Lock();
  1961. conn->OnReceivedLocalCallHold(linkedId);
  1962. conn->Unlock();
  1963. }
  1964. }
  1965. void MyH4504Handler::OnReceivedLocalCallRetrieve(int linkedId)
  1966. {
  1967. if (conn) {
  1968. conn->Lock();
  1969. conn->OnReceivedLocalCallRetrieve(linkedId);
  1970. conn->Unlock();
  1971. }
  1972. }
  1973. #endif
  1974. /** IMPLEMENTATION OF C FUNCTIONS */
  1975. /**
  1976. * The extern "C" directive takes care for
  1977. * the ANSI-C representation of linkable symbols
  1978. */
  1979. extern "C" {
  1980. int h323_end_point_exist(void)
  1981. {
  1982. if (!endPoint) {
  1983. return 0;
  1984. }
  1985. return 1;
  1986. }
  1987. void h323_end_point_create(void)
  1988. {
  1989. channelsOpen = 0;
  1990. logstream = new PAsteriskLog();
  1991. PTrace::SetStream(logstream);
  1992. endPoint = new MyH323EndPoint();
  1993. }
  1994. void h323_gk_urq(void)
  1995. {
  1996. if (!h323_end_point_exist()) {
  1997. cout << " ERROR: [h323_gk_urq] No Endpoint, this is bad" << endl;
  1998. return;
  1999. }
  2000. endPoint->RemoveGatekeeper();
  2001. }
  2002. void h323_debug(int flag, unsigned level)
  2003. {
  2004. if (flag) {
  2005. PTrace:: SetLevel(level);
  2006. } else {
  2007. PTrace:: SetLevel(0);
  2008. }
  2009. }
  2010. /** Installs the callback functions on behalf of the PBX application */
  2011. void h323_callback_register(setup_incoming_cb ifunc,
  2012. setup_outbound_cb sfunc,
  2013. on_rtp_cb rtpfunc,
  2014. start_rtp_cb lfunc,
  2015. clear_con_cb clfunc,
  2016. chan_ringing_cb rfunc,
  2017. con_established_cb efunc,
  2018. receive_digit_cb dfunc,
  2019. answer_call_cb acfunc,
  2020. progress_cb pgfunc,
  2021. rfc2833_cb dtmffunc,
  2022. hangup_cb hangupfunc,
  2023. setcapabilities_cb capabilityfunc,
  2024. setpeercapabilities_cb peercapabilityfunc,
  2025. onhold_cb holdfunc)
  2026. {
  2027. on_incoming_call = ifunc;
  2028. on_outgoing_call = sfunc;
  2029. on_external_rtp_create = rtpfunc;
  2030. on_start_rtp_channel = lfunc;
  2031. on_connection_cleared = clfunc;
  2032. on_chan_ringing = rfunc;
  2033. on_connection_established = efunc;
  2034. on_receive_digit = dfunc;
  2035. on_answer_call = acfunc;
  2036. on_progress = pgfunc;
  2037. on_set_rfc2833_payload = dtmffunc;
  2038. on_hangup = hangupfunc;
  2039. on_setcapabilities = capabilityfunc;
  2040. on_setpeercapabilities = peercapabilityfunc;
  2041. on_hold = holdfunc;
  2042. }
  2043. /**
  2044. * Add capability to the capability table of the end point.
  2045. */
  2046. int h323_set_capabilities(const char *token, int cap, int dtmf_mode, struct ast_codec_pref *prefs, int pref_codec)
  2047. {
  2048. MyH323Connection *conn;
  2049. if (!h323_end_point_exist()) {
  2050. cout << " ERROR: [h323_set_capablities] No Endpoint, this is bad" << endl;
  2051. return 1;
  2052. }
  2053. if (!token || !*token) {
  2054. cout << " ERROR: [h323_set_capabilities] Invalid call token specified." << endl;
  2055. return 1;
  2056. }
  2057. PString myToken(token);
  2058. conn = (MyH323Connection *)endPoint->FindConnectionWithLock(myToken);
  2059. if (!conn) {
  2060. cout << " ERROR: [h323_set_capabilities] Unable to find connection " << token << endl;
  2061. return 1;
  2062. }
  2063. conn->SetCapabilities((/*conn->bridging ? conn->redir_capabilities :*/ cap), dtmf_mode, prefs, pref_codec);
  2064. conn->Unlock();
  2065. return 0;
  2066. }
  2067. /** Start the H.323 listener */
  2068. int h323_start_listener(int listenPort, struct sockaddr_in bindaddr)
  2069. {
  2070. if (!h323_end_point_exist()) {
  2071. cout << "ERROR: [h323_start_listener] No Endpoint, this is bad!" << endl;
  2072. return 1;
  2073. }
  2074. PIPSocket::Address interfaceAddress(bindaddr.sin_addr);
  2075. if (!listenPort) {
  2076. listenPort = 1720;
  2077. }
  2078. /** H.323 listener */
  2079. H323ListenerTCP *tcpListener;
  2080. tcpListener = new H323ListenerTCP(*endPoint, interfaceAddress, (WORD)listenPort);
  2081. if (!endPoint->StartListener(tcpListener)) {
  2082. cout << "ERROR: Could not open H.323 listener port on " << ((H323ListenerTCP *) tcpListener)->GetListenerPort() << endl;
  2083. delete tcpListener;
  2084. return 1;
  2085. }
  2086. cout << " == H.323 listener started" << endl;
  2087. return 0;
  2088. };
  2089. /* Addition of functions just to make the channel driver compile with H323Plus */
  2090. #if VERSION(OPENH323_MAJOR, OPENH323_MINOR, OPENH323_BUILD) > VERSION(1,19,4)
  2091. /* Alternate RTP port information for Same NAT */
  2092. BOOL MyH323_ExternalRTPChannel::OnReceivedAltPDU(const H245_ArrayOf_GenericInformation & alternate )
  2093. {
  2094. return TRUE;
  2095. }
  2096. /* Alternate RTP port information for Same NAT */
  2097. BOOL MyH323_ExternalRTPChannel::OnSendingAltPDU(H245_ArrayOf_GenericInformation & alternate) const
  2098. {
  2099. return TRUE;
  2100. }
  2101. /* Alternate RTP port information for Same NAT */
  2102. void MyH323_ExternalRTPChannel::OnSendOpenAckAlt(H245_ArrayOf_GenericInformation & alternate) const
  2103. {
  2104. }
  2105. /* Alternate RTP port information for Same NAT */
  2106. BOOL MyH323_ExternalRTPChannel::OnReceivedAckAltPDU(const H245_ArrayOf_GenericInformation & alternate)
  2107. {
  2108. return TRUE;
  2109. }
  2110. #endif
  2111. int h323_set_alias(struct oh323_alias *alias)
  2112. {
  2113. char *p;
  2114. char *num;
  2115. PString h323id(alias->name);
  2116. PString e164(alias->e164);
  2117. char *prefix;
  2118. if (!h323_end_point_exist()) {
  2119. cout << "ERROR: [h323_set_alias] No Endpoint, this is bad!" << endl;
  2120. return 1;
  2121. }
  2122. cout << "== Adding alias \"" << h323id << "\" to endpoint" << endl;
  2123. endPoint->AddAliasName(h323id);
  2124. endPoint->RemoveAliasName(PProcess::Current().GetName());
  2125. if (!e164.IsEmpty()) {
  2126. cout << "== Adding E.164 \"" << e164 << "\" to endpoint" << endl;
  2127. endPoint->AddAliasName(e164);
  2128. }
  2129. if (strlen(alias->prefix)) {
  2130. p = prefix = strdup(alias->prefix);
  2131. while((num = strsep(&p, ",")) != (char *)NULL) {
  2132. cout << "== Adding Prefix \"" << num << "\" to endpoint" << endl;
  2133. endPoint->SupportedPrefixes += PString(num);
  2134. endPoint->SetGateway();
  2135. }
  2136. if (prefix)
  2137. ast_free(prefix);
  2138. }
  2139. return 0;
  2140. }
  2141. void h323_set_id(char *id)
  2142. {
  2143. PString h323id(id);
  2144. if (h323debug) {
  2145. cout << " == Using '" << h323id << "' as our H.323ID for this call" << endl;
  2146. }
  2147. /* EVIL HACK */
  2148. endPoint->SetLocalUserName(h323id);
  2149. }
  2150. void h323_show_tokens(void)
  2151. {
  2152. cout << "Current call tokens: " << setprecision(2) << endPoint->GetAllConnections() << endl;
  2153. }
  2154. void h323_show_version(void)
  2155. {
  2156. cout << "H.323 version: " << OPENH323_MAJOR << "." << OPENH323_MINOR << "." << OPENH323_BUILD << endl;
  2157. }
  2158. /** Establish Gatekeeper communiations, if so configured,
  2159. * register aliases for the H.323 endpoint to respond to.
  2160. */
  2161. int h323_set_gk(int gatekeeper_discover, char *gatekeeper, char *secret)
  2162. {
  2163. PString gkName = PString(gatekeeper);
  2164. PString pass = PString(secret);
  2165. H323TransportUDP *rasChannel;
  2166. if (!h323_end_point_exist()) {
  2167. cout << "ERROR: [h323_set_gk] No Endpoint, this is bad!" << endl;
  2168. return 1;
  2169. }
  2170. if (!gatekeeper) {
  2171. cout << "Error: Gatekeeper cannot be NULL" << endl;
  2172. return 1;
  2173. }
  2174. if (strlen(secret)) {
  2175. endPoint->SetGatekeeperPassword(pass);
  2176. }
  2177. if (gatekeeper_discover) {
  2178. /* discover the gk using multicast */
  2179. if (endPoint->DiscoverGatekeeper(new MyH323TransportUDP(*endPoint))) {
  2180. cout << "== Using " << (endPoint->GetGatekeeper())->GetName() << " as our Gatekeeper." << endl;
  2181. } else {
  2182. cout << "Warning: Could not find a gatekeeper." << endl;
  2183. return 1;
  2184. }
  2185. } else {
  2186. rasChannel = new MyH323TransportUDP(*endPoint);
  2187. if (!rasChannel) {
  2188. cout << "Error: No RAS Channel, this is bad" << endl;
  2189. return 1;
  2190. }
  2191. if (endPoint->SetGatekeeper(gkName, rasChannel)) {
  2192. cout << "== Using " << (endPoint->GetGatekeeper())->GetName() << " as our Gatekeeper." << endl;
  2193. } else {
  2194. cout << "Error registering with gatekeeper \"" << gkName << "\". " << endl;
  2195. /* XXX Maybe we should fire a new thread to attempt to re-register later and not kill asterisk here? */
  2196. return 1;
  2197. }
  2198. }
  2199. return 0;
  2200. }
  2201. /** Send a DTMF tone over the H323Connection with the
  2202. * specified token.
  2203. */
  2204. void h323_send_tone(const char *call_token, char tone)
  2205. {
  2206. if (!h323_end_point_exist()) {
  2207. cout << "ERROR: [h323_send_tone] No Endpoint, this is bad!" << endl;
  2208. return;
  2209. }
  2210. PString token = PString(call_token);
  2211. endPoint->SendUserTone(token, tone);
  2212. }
  2213. /** Make a call to the remote endpoint.
  2214. */
  2215. int h323_make_call(char *dest, call_details_t *cd, call_options_t *call_options)
  2216. {
  2217. int res;
  2218. PString token;
  2219. PString host(dest);
  2220. if (!h323_end_point_exist()) {
  2221. return 1;
  2222. }
  2223. res = endPoint->MyMakeCall(host, token, &cd->call_reference, call_options);
  2224. memcpy((char *)(cd->call_token), (const unsigned char *)token, token.GetLength());
  2225. return res;
  2226. };
  2227. int h323_clear_call(const char *call_token, int cause)
  2228. {
  2229. H225_ReleaseCompleteReason dummy;
  2230. H323Connection::CallEndReason r = H323Connection::EndedByLocalUser;
  2231. MyH323Connection *connection;
  2232. const PString currentToken(call_token);
  2233. if (!h323_end_point_exist()) {
  2234. return 1;
  2235. }
  2236. if (cause) {
  2237. r = H323TranslateToCallEndReason((Q931::CauseValues)(cause), dummy);
  2238. }
  2239. connection = (MyH323Connection *)endPoint->FindConnectionWithLock(currentToken);
  2240. if (connection) {
  2241. connection->SetCause(cause);
  2242. connection->SetCallEndReason(r);
  2243. connection->Unlock();
  2244. }
  2245. endPoint->ClearCall(currentToken, r);
  2246. return 0;
  2247. };
  2248. /* Send Alerting PDU to H.323 caller */
  2249. int h323_send_alerting(const char *token)
  2250. {
  2251. const PString currentToken(token);
  2252. H323Connection * connection;
  2253. if (h323debug) {
  2254. cout << "\tSending alerting" << endl;
  2255. }
  2256. connection = endPoint->FindConnectionWithLock(currentToken);
  2257. if (!connection) {
  2258. cout << "No connection found for " << token << endl;
  2259. return -1;
  2260. }
  2261. connection->AnsweringCall(H323Connection::AnswerCallPending);
  2262. connection->Unlock();
  2263. return 0;
  2264. }
  2265. /* Send Progress PDU to H.323 caller */
  2266. int h323_send_progress(const char *token)
  2267. {
  2268. const PString currentToken(token);
  2269. H323Connection * connection;
  2270. connection = endPoint->FindConnectionWithLock(currentToken);
  2271. if (!connection) {
  2272. cout << "No connection found for " << token << endl;
  2273. return -1;
  2274. }
  2275. #if 1
  2276. ((MyH323Connection *)connection)->MySendProgress();
  2277. #else
  2278. connection->AnsweringCall(H323Connection::AnswerCallDeferredWithMedia);
  2279. #endif
  2280. connection->Unlock();
  2281. return 0;
  2282. }
  2283. /** This function tells the h.323 stack to either
  2284. answer or deny an incoming call */
  2285. int h323_answering_call(const char *token, int busy)
  2286. {
  2287. const PString currentToken(token);
  2288. H323Connection * connection;
  2289. connection = endPoint->FindConnectionWithLock(currentToken);
  2290. if (!connection) {
  2291. cout << "No connection found for " << token << endl;
  2292. return -1;
  2293. }
  2294. if (!busy) {
  2295. if (h323debug) {
  2296. cout << "\tAnswering call " << token << endl;
  2297. }
  2298. connection->AnsweringCall(H323Connection::AnswerCallNow);
  2299. } else {
  2300. if (h323debug) {
  2301. cout << "\tdenying call " << token << endl;
  2302. }
  2303. connection->AnsweringCall(H323Connection::AnswerCallDenied);
  2304. }
  2305. connection->Unlock();
  2306. return 0;
  2307. }
  2308. int h323_soft_hangup(const char *data)
  2309. {
  2310. PString token(data);
  2311. PBoolean result;
  2312. cout << "Soft hangup" << endl;
  2313. result = endPoint->ClearCall(token);
  2314. return result;
  2315. }
  2316. /* alas, this doesn't work :( */
  2317. void h323_native_bridge(const char *token, const char *them, char *capability)
  2318. {
  2319. H323Channel *channel;
  2320. MyH323Connection *connection = (MyH323Connection *)endPoint->FindConnectionWithLock(token);
  2321. if (!connection) {
  2322. cout << "ERROR: No connection found, this is bad" << endl;
  2323. return;
  2324. }
  2325. cout << "Native Bridge: them [" << them << "]" << endl;
  2326. channel = connection->FindChannel(connection->sessionId, TRUE);
  2327. connection->bridging = TRUE;
  2328. connection->CloseLogicalChannelNumber(channel->GetNumber());
  2329. connection->Unlock();
  2330. return;
  2331. }
  2332. int h323_hold_call(const char *token, int is_hold)
  2333. {
  2334. MyH323Connection *conn = (MyH323Connection *)endPoint->FindConnectionWithLock(token);
  2335. if (!conn) {
  2336. cout << "ERROR: No connection found, this is bad" << endl;
  2337. return -1;
  2338. }
  2339. conn->MyHoldCall((PBoolean)is_hold);
  2340. conn->Unlock();
  2341. return 0;
  2342. }
  2343. #undef cout
  2344. #undef endl
  2345. void h323_end_process(void)
  2346. {
  2347. if (endPoint) {
  2348. delete endPoint;
  2349. endPoint = NULL;
  2350. }
  2351. #ifndef SKIP_PWLIB_PIPE_BUG_WORKAROUND
  2352. close(_timerChangePipe[0]);
  2353. close(_timerChangePipe[1]);
  2354. #endif
  2355. if (logstream) {
  2356. PTrace::SetStream(NULL);
  2357. delete logstream;
  2358. logstream = NULL;
  2359. }
  2360. }
  2361. } /* extern "C" */