Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

6105 lines
210 KiB

  1. /****************************************************************************
  2. *
  3. * $Archive: S:/STURGEON/SRC/Q931/VCS/q931pdu.c_v $
  4. *
  5. * INTEL Corporation Prorietary Information
  6. *
  7. * This listing is supplied under the terms of a license agreement
  8. * with INTEL Corporation and may not be copied nor disclosed except
  9. * in accordance with the terms of that agreement.
  10. *
  11. * Copyright (c) 1996 Intel Corporation.
  12. *
  13. * $Revision: 1.67.1.1 $
  14. * $Date: 20 Jun 1997 14:13:22 $
  15. * $Author: MANDREWS $
  16. *
  17. * Deliverable:
  18. *
  19. * Abstract: Parser routines for Q931 PDUs
  20. *
  21. * Notes:
  22. *
  23. ***************************************************************************/
  24. #pragma comment (exestr, "$Workfile: q931pdu.c $ $Revision: 1.67.1.1 $")
  25. // [ ] Do another integration of own q931test area.
  26. // [ ] Alias values displayed in tracing routines.
  27. // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  28. // STANDARDS ISSUES
  29. // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  30. // [ ] !!! EndpointType contains MC info, so Setup_UUIE doesnt need MC field !!!
  31. // [ ] !!! Need to decide how CallType is to be used !!!
  32. // [ ] !!! ALERTING message is missing the ConferenceID field !!!
  33. // [ ] !!! Place needed for Caller and Callee transport addr, or else explanation of how this information is available round-trip !!!
  34. // [ ] !!! FACILITY message is missing the protocolIdentifier field !!!
  35. //------------------------------------------------------------------------------
  36. // Note: These parsing details have not yet been supported:
  37. // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  38. // 1) variable octet fields having extending groups,
  39. // extending indications, or escape for extensions. (See 4.5.1)
  40. // 2) codeset recognition and exclusion based on SHIFT (See 4.5.2)
  41. // 3) correct ignoring of escapes for nationally specific message types.
  42. // 4) The call reference value is 2 bytes long sizeof(WORD).
  43. // A call reference of 0 means, the message pertains to all
  44. // calls on the same data link.
  45. //------------------------------------------------------------------------------
  46. #pragma warning ( disable : 4100 4115 4201 4214 4514 )
  47. #include <nt.h>
  48. #include <ntrtl.h>
  49. #include <nturtl.h>
  50. #include <windows.h>
  51. #include <string.h>
  52. #include "q931asn.h"
  53. #include "q931asn1.h"
  54. #include "common.h"
  55. #include "q931.h"
  56. #include "isrg.h"
  57. #include "utils.h"
  58. #include "q931pdu.h"
  59. #ifdef UNICODE_TRACE
  60. // We include this header to fix problems with macro expansion when Unicode is turned on.
  61. #include "unifix.h"
  62. #endif
  63. //==========================================================
  64. // CALLED PARTY FIELD DEFINITIONS
  65. //==========================================================
  66. // called party encoding bits...
  67. #define CALLED_PARTY_EXT_BIT 0x80
  68. // called party number type
  69. #define CALLED_PARTY_TYPE_UNKNOWN 0x00
  70. // ...other types are not defined because they are not used...
  71. // called party numbering plan
  72. #define CALLED_PARTY_PLAN_E164 0x01
  73. // ...other plans are not defined because they are not used...
  74. //==========================================================
  75. // BEARER FIELD DEFINITIONS
  76. //==========================================================
  77. // bearer encoding bits...
  78. #define BEAR_EXT_BIT 0x80
  79. // bearer coding standards...
  80. #define BEAR_CCITT 0x00
  81. // ...others not needed...
  82. // bearer information transfer capability...
  83. #define BEAR_UNRESTRICTED_DIGITAL 0x08
  84. // ...others not needed...
  85. // bearer transfer mode...
  86. #define BEAR_CIRCUIT_MODE 0x00
  87. #define BEAR_PACKET_MODE 0x40
  88. // ...others not needed...
  89. // bearer information transfer rate...
  90. #define BEAR_NO_CIRCUIT_RATE 0x00
  91. #define BEAR_MULTIRATE 0x18
  92. // ...others not needed...
  93. // bearer layer1 protocol...
  94. #define BEAR_LAYER1_INDICATOR 0x20
  95. #define BEAR_LAYER1_H221_H242 0x05
  96. // ...others not needed...
  97. #define Q931_PROTOCOL_ID1 0
  98. #define Q931_PROTOCOL_ID2 0
  99. #define Q931_PROTOCOL_ID3 8
  100. #define Q931_PROTOCOL_ID4 2250
  101. #define Q931_PROTOCOL_ID5 0
  102. #define Q931_PROTOCOL_ID6 1
  103. static struct ObjectID_ ProtocolId1;
  104. static struct ObjectID_ ProtocolId2;
  105. static struct ObjectID_ ProtocolId3;
  106. static struct ObjectID_ ProtocolId4;
  107. static struct ObjectID_ ProtocolId5;
  108. static struct ObjectID_ ProtocolId6;
  109. static struct _seqof1 TempProtocol;
  110. MESSAGEIDTYPE MessageSet[] =
  111. {
  112. ALERTINGMESSAGETYPE,
  113. PROCEEDINGMESSAGETYPE,
  114. CONNECTMESSAGETYPE,
  115. CONNECTACKMESSAGETYPE,
  116. PROGRESSMESSAGETYPE,
  117. SETUPMESSAGETYPE,
  118. SETUPACKMESSAGETYPE,
  119. RESUMEMESSAGETYPE,
  120. RESUMEACKMESSAGETYPE,
  121. RESUMEREJMESSAGETYPE,
  122. SUSPENDMESSAGETYPE,
  123. SUSPENDACKMESSAGETYPE,
  124. SUSPENDREJMESSAGETYPE,
  125. USERINFOMESSAGETYPE,
  126. DISCONNECTMESSAGETYPE,
  127. RELEASEMESSAGETYPE,
  128. RELEASECOMPLMESSAGETYPE,
  129. RESTARTMESSAGETYPE,
  130. RESTARTACKMESSAGETYPE,
  131. SEGMENTMESSAGETYPE,
  132. CONGCTRLMESSAGETYPE,
  133. INFORMATIONMESSAGETYPE,
  134. NOTIFYMESSAGETYPE,
  135. STATUSMESSAGETYPE,
  136. STATUSENQUIRYMESSAGETYPE,
  137. HOLDMESSAGETYPE,
  138. HOLDACKMESSAGETYPE,
  139. HOLDREJECTMESSAGETYPE,
  140. RETRIEVEMESSAGETYPE,
  141. RETRIEVEACKMESSAGETYPE,
  142. RETRIEVEREJECTMESSAGETYPE,
  143. FACILITYMESSAGETYPE,
  144. REGISTERMESSAGETYPE
  145. };
  146. //====================================================================================
  147. //====================================================================================
  148. static CS_STATUS
  149. AliasToSeqof(struct _seqof3 **ppTarget, PCC_ALIASNAMES pSource)
  150. {
  151. if (ppTarget == NULL)
  152. {
  153. return CS_BAD_PARAM;
  154. }
  155. *ppTarget = NULL;
  156. if (pSource == NULL)
  157. {
  158. return CS_OK;
  159. }
  160. if (pSource && (pSource->wCount))
  161. {
  162. struct _seqof3 *ListHead = NULL;
  163. struct _seqof3 *CurrentNode = NULL;
  164. LPWSTR pData = NULL; // UNICODE STRING
  165. int SourceItem;
  166. WORD x;
  167. for (SourceItem = pSource->wCount - 1; SourceItem >= 0; SourceItem--)
  168. {
  169. BOOL Cleanup = FALSE;
  170. // first do the required memory allocations...
  171. CurrentNode = (struct _seqof3 *)Malloc(sizeof(struct _seqof3));
  172. if (CurrentNode == NULL)
  173. {
  174. Cleanup = TRUE;
  175. }
  176. else
  177. {
  178. if (pSource->pItems[SourceItem].wType == CC_ALIAS_H323_ID)
  179. {
  180. if ((pSource->pItems[SourceItem].wDataLength != 0) &&
  181. (pSource->pItems[SourceItem].pData != NULL))
  182. {
  183. pData = (LPWSTR)Malloc(pSource->pItems[SourceItem].wDataLength *
  184. sizeof(WCHAR));
  185. if (pData == NULL)
  186. {
  187. Free(CurrentNode);
  188. Cleanup = TRUE;
  189. }
  190. }
  191. }
  192. }
  193. if (Cleanup)
  194. {
  195. for (CurrentNode = ListHead; CurrentNode; CurrentNode = ListHead)
  196. {
  197. ListHead = CurrentNode->next;
  198. if (CurrentNode->value.choice == h323_ID_chosen)
  199. {
  200. if (CurrentNode->value.u.h323_ID.value)
  201. {
  202. Free(CurrentNode->value.u.h323_ID.value);
  203. }
  204. }
  205. Free(CurrentNode);
  206. }
  207. return CS_NO_MEMORY;
  208. }
  209. // then do the required memory copying.
  210. if (pSource->pItems[SourceItem].wType == CC_ALIAS_H323_ID)
  211. {
  212. CurrentNode->value.choice = h323_ID_chosen;
  213. if ((pSource->pItems[SourceItem].wDataLength != 0) &&
  214. (pSource->pItems[SourceItem].pData != NULL))
  215. {
  216. CurrentNode->value.u.h323_ID.length =
  217. pSource->pItems[SourceItem].wDataLength;
  218. for (x = 0; x < pSource->pItems[SourceItem].wDataLength; x++)
  219. {
  220. pData[x] = pSource->pItems[SourceItem].pData[x];
  221. }
  222. CurrentNode->value.u.h323_ID.value = pData;
  223. }
  224. else
  225. {
  226. CurrentNode->value.u.h323_ID.length = 0;
  227. CurrentNode->value.u.h323_ID.value = NULL;
  228. }
  229. }
  230. else if (pSource->pItems[SourceItem].wType == CC_ALIAS_H323_PHONE)
  231. {
  232. CurrentNode->value.choice = e164_chosen;
  233. if ((pSource->pItems[SourceItem].wDataLength != 0) &&
  234. (pSource->pItems[SourceItem].pData != NULL))
  235. {
  236. for (x = 0; x < pSource->pItems[SourceItem].wDataLength; x++)
  237. {
  238. CurrentNode->value.u.e164[x] = (BYTE)(pSource->pItems[SourceItem].pData[x]);
  239. }
  240. CurrentNode->value.u.e164[pSource->pItems[SourceItem].wDataLength] = '\0';
  241. }
  242. else
  243. {
  244. CurrentNode->value.u.e164[0] = '\0';
  245. }
  246. }
  247. CurrentNode->next = ListHead;
  248. ListHead = CurrentNode;
  249. }
  250. *ppTarget = ListHead;
  251. }
  252. return CS_OK;
  253. }
  254. //====================================================================================
  255. //====================================================================================
  256. static CS_STATUS
  257. AliasWithPrefixToSeqof(struct _seqof3 **ppTarget, PCC_ALIASNAMES pSource)
  258. {
  259. if (ppTarget == NULL)
  260. {
  261. return CS_BAD_PARAM;
  262. }
  263. *ppTarget = NULL;
  264. if (pSource == NULL)
  265. {
  266. return CS_OK;
  267. }
  268. if (pSource && (pSource->wCount))
  269. {
  270. struct _seqof3 *ListHead = NULL;
  271. struct _seqof3 *CurrentNode = NULL;
  272. int SourceItem;
  273. for (SourceItem = pSource->wCount - 1; SourceItem >= 0; SourceItem--)
  274. {
  275. PCC_ALIASITEM pItem = &pSource->pItems[SourceItem];
  276. LPWSTR pData = NULL; // UNICODE STRING
  277. BOOL Cleanup = FALSE;
  278. unsigned uPrefixLength;
  279. unsigned uDataLength;
  280. unsigned x;
  281. if (pItem->pPrefix != NULL &&
  282. pItem->wPrefixLength > 0)
  283. {
  284. uPrefixLength = (unsigned) pItem->wPrefixLength;
  285. }
  286. else
  287. {
  288. uPrefixLength = 0;
  289. }
  290. if (pItem->pData != NULL &&
  291. pItem->wDataLength > 0)
  292. {
  293. uDataLength = (unsigned) pItem->wDataLength;
  294. }
  295. else
  296. {
  297. uDataLength = 0;
  298. }
  299. // first do the required memory allocations...
  300. CurrentNode = (struct _seqof3 *)Malloc(sizeof(struct _seqof3));
  301. if (CurrentNode == NULL)
  302. {
  303. Cleanup = TRUE;
  304. }
  305. else
  306. {
  307. if (pItem->wType == CC_ALIAS_H323_ID)
  308. {
  309. #ifdef USE_PREFIX_FOR_H323_ID
  310. if (uPrefixLength != 0 || uDataLength != 0)
  311. {
  312. pData = (LPWSTR)Malloc((uPrefixLength + uDataLength) * sizeof(WCHAR));
  313. #else
  314. if (uDataLength != 0)
  315. {
  316. pData = (LPWSTR)Malloc((uDataLength) * sizeof(WCHAR));
  317. #endif
  318. if (pData == NULL)
  319. {
  320. Free(CurrentNode);
  321. Cleanup = TRUE;
  322. }
  323. }
  324. }
  325. }
  326. if (Cleanup)
  327. {
  328. for (CurrentNode = ListHead; CurrentNode; CurrentNode = ListHead)
  329. {
  330. ListHead = CurrentNode->next;
  331. if (CurrentNode->value.choice == h323_ID_chosen)
  332. {
  333. if (CurrentNode->value.u.h323_ID.value)
  334. {
  335. Free(CurrentNode->value.u.h323_ID.value);
  336. }
  337. }
  338. Free(CurrentNode);
  339. }
  340. return CS_NO_MEMORY;
  341. }
  342. // then do the required memory copying.
  343. switch (pItem->wType)
  344. {
  345. case CC_ALIAS_H323_ID:
  346. CurrentNode->value.choice = h323_ID_chosen;
  347. #ifdef USE_PREFIX_FOR_H323_ID
  348. if (uPrefixLength != 0 || uDataLength != 0)
  349. {
  350. CurrentNode->value.u.h323_ID.length = (WORD)(uPrefixLength + uDataLength);
  351. for (x = 0; x < uPrefixLength; ++x)
  352. {
  353. pData[x] = pItem->pPrefix[x];
  354. }
  355. for (x = 0; x < uDataLength; ++x)
  356. {
  357. pData[uPrefixLength + x] = pItem->pData[x];
  358. }
  359. #else
  360. if (uDataLength != 0)
  361. {
  362. CurrentNode->value.u.h323_ID.length = (WORD)(uDataLength);
  363. for (x = 0; x < uDataLength; ++x)
  364. {
  365. pData[x] = pItem->pData[x];
  366. }
  367. #endif
  368. CurrentNode->value.u.h323_ID.value = pData;
  369. }
  370. else
  371. {
  372. CurrentNode->value.u.h323_ID.length = 0;
  373. CurrentNode->value.u.h323_ID.value = NULL;
  374. }
  375. break;
  376. case CC_ALIAS_H323_PHONE:
  377. CurrentNode->value.choice = e164_chosen;
  378. for (x = 0; x < uPrefixLength; ++x)
  379. {
  380. CurrentNode->value.u.e164[x] = (BYTE)(pItem->pPrefix[x]);
  381. }
  382. for (x = 0; x < uDataLength; ++x)
  383. {
  384. CurrentNode->value.u.e164[uPrefixLength + x] = (BYTE)(pItem->pData[x]);
  385. }
  386. for (x = uDataLength + uPrefixLength; x < sizeof(CurrentNode->value.u.e164); ++x)
  387. {
  388. CurrentNode->value.u.e164[x] = 0;
  389. }
  390. break;
  391. default:
  392. Free(CurrentNode);
  393. for (CurrentNode = ListHead; CurrentNode; CurrentNode = ListHead)
  394. {
  395. ListHead = CurrentNode->next;
  396. if (CurrentNode->value.choice == h323_ID_chosen)
  397. {
  398. if (CurrentNode->value.u.h323_ID.value)
  399. {
  400. Free(CurrentNode->value.u.h323_ID.value);
  401. }
  402. }
  403. Free(CurrentNode);
  404. }
  405. return CS_BAD_PARAM;
  406. } // switch
  407. CurrentNode->next = ListHead;
  408. ListHead = CurrentNode;
  409. }
  410. *ppTarget = ListHead;
  411. }
  412. return CS_OK;
  413. }
  414. //====================================================================================
  415. //====================================================================================
  416. static CS_STATUS
  417. SeqofToAlias(PCC_ALIASNAMES *ppTarget, struct _seqof3 *pSource)
  418. {
  419. struct _seqof3 *ListHead = NULL;
  420. struct _seqof3 *CurrentNode = NULL;
  421. WORD wCount;
  422. WORD x = 0;
  423. PCC_ALIASITEM p = NULL;
  424. CS_STATUS status = CS_OK;
  425. if (ppTarget == NULL)
  426. {
  427. return CS_BAD_PARAM;
  428. }
  429. *ppTarget = NULL;
  430. if (pSource == NULL)
  431. {
  432. return CS_OK;
  433. }
  434. wCount = 0;
  435. for (CurrentNode = pSource; CurrentNode; CurrentNode = CurrentNode->next)
  436. {
  437. wCount++;
  438. }
  439. *ppTarget = (PCC_ALIASNAMES)Malloc(sizeof(CC_ALIASNAMES));
  440. if (*ppTarget == NULL)
  441. {
  442. return CS_NO_MEMORY;
  443. }
  444. (*ppTarget)->pItems = (PCC_ALIASITEM)Malloc(wCount * sizeof(CC_ALIASITEM));
  445. if ((*ppTarget)->pItems == NULL)
  446. {
  447. Free(*ppTarget);
  448. *ppTarget = NULL;
  449. return CS_NO_MEMORY;
  450. }
  451. p = (*ppTarget)->pItems;
  452. for (CurrentNode = pSource; CurrentNode; CurrentNode = CurrentNode->next)
  453. {
  454. WORD y;
  455. p[x].wPrefixLength = 0;
  456. p[x].pPrefix = NULL;
  457. switch (CurrentNode->value.choice)
  458. {
  459. case h323_ID_chosen:
  460. p[x].wType = CC_ALIAS_H323_ID;
  461. if ((CurrentNode->value.u.h323_ID.length != 0) &&
  462. (CurrentNode->value.u.h323_ID.value != NULL))
  463. {
  464. p[x].wDataLength = (WORD)CurrentNode->value.u.h323_ID.length;
  465. p[x].pData = (LPWSTR)Malloc(CurrentNode->value.u.h323_ID.length * sizeof(p[x].pData[0]));
  466. if (p[x].pData != NULL)
  467. {
  468. for (y = 0; y < CurrentNode->value.u.h323_ID.length; y++)
  469. {
  470. p[x].pData[y] = (WCHAR)((CurrentNode->value.u.h323_ID.value)[y]);
  471. }
  472. x++;
  473. }
  474. else
  475. {
  476. status = CS_NO_MEMORY;
  477. }
  478. }
  479. break;
  480. case e164_chosen:
  481. p[x].wType = CC_ALIAS_H323_PHONE;
  482. p[x].wDataLength = (WORD)strlen(CurrentNode->value.u.e164);
  483. p[x].pData = (LPWSTR)Malloc((p[x].wDataLength+1) * sizeof(p[x].pData[0]));
  484. if (p[x].pData != NULL)
  485. {
  486. for (y = 0; y < p[x].wDataLength; y++)
  487. {
  488. p[x].pData[y] = CurrentNode->value.u.e164[y];
  489. }
  490. p[x].pData[p[x].wDataLength] = 0;
  491. x++;
  492. }
  493. else
  494. {
  495. status = CS_NO_MEMORY;
  496. }
  497. break;
  498. default:
  499. // we don't currently handle other alias types
  500. break;
  501. } // switch
  502. if (status != CS_OK)
  503. {
  504. // Free everything that has been allocated so far...
  505. for (y = 0; y < x; y++)
  506. {
  507. Free(p[y].pData);
  508. }
  509. Free(p);
  510. Free(*ppTarget);
  511. *ppTarget = NULL;
  512. return status;
  513. }
  514. }
  515. // any aliases?
  516. if (x > 0) {
  517. // save number of aliases
  518. (*ppTarget)->wCount = x;
  519. } else {
  520. //
  521. // Note Q931FreeAliasNames does not free CC_ALIASNAMES structure
  522. // when wCount is set to zero
  523. //
  524. Free(p);
  525. Free(*ppTarget);
  526. *ppTarget = NULL;
  527. }
  528. return CS_OK;
  529. }
  530. //====================================================================================
  531. //====================================================================================
  532. static CS_STATUS
  533. FreeSeqof(struct _seqof3 *pSource)
  534. {
  535. struct _seqof3 *CurrentNode = NULL;
  536. for (CurrentNode = pSource; CurrentNode; CurrentNode = pSource)
  537. {
  538. pSource = CurrentNode->next;
  539. if (CurrentNode->value.choice == h323_ID_chosen)
  540. {
  541. if (CurrentNode->value.u.h323_ID.value)
  542. {
  543. Free(CurrentNode->value.u.h323_ID.value);
  544. }
  545. }
  546. Free(CurrentNode);
  547. }
  548. return CS_OK;
  549. }
  550. //====================================================================================
  551. //====================================================================================
  552. static CS_STATUS
  553. Q931CopyAliasItemToAliasAddr(AliasAddress *pTarget, PCC_ALIASITEM pSource)
  554. {
  555. AliasAddress *pNewAddress = NULL;
  556. WORD x;
  557. if (pTarget == NULL)
  558. {
  559. return CS_BAD_PARAM;
  560. }
  561. if (pSource == NULL)
  562. {
  563. return CS_BAD_PARAM;
  564. }
  565. pNewAddress = pTarget;
  566. if (pSource->wType == CC_ALIAS_H323_ID)
  567. {
  568. pNewAddress->choice = h323_ID_chosen;
  569. if ((pSource->wDataLength != 0) && (pSource->pData != NULL))
  570. {
  571. LPWSTR pData = NULL; // UNICODE STRING
  572. pData = (LPWSTR)Malloc(pSource->wDataLength * sizeof(WCHAR));
  573. if (pData == NULL)
  574. {
  575. return CS_NO_MEMORY;
  576. }
  577. pNewAddress->u.h323_ID.length = pSource->wDataLength;
  578. for (x = 0; x < pSource->wDataLength; x++)
  579. {
  580. pData[x] = pSource->pData[x];
  581. }
  582. pNewAddress->u.h323_ID.value = pData;
  583. }
  584. else
  585. {
  586. pNewAddress->u.h323_ID.length = 0;
  587. pNewAddress->u.h323_ID.value = NULL;
  588. }
  589. }
  590. else if (pSource->wType == CC_ALIAS_H323_PHONE)
  591. {
  592. pNewAddress->choice = e164_chosen;
  593. if ((pSource->wDataLength != 0) && (pSource->pData != NULL))
  594. {
  595. for (x = 0; x < pSource->wDataLength; x++)
  596. {
  597. pNewAddress->u.e164[x] = (BYTE)(pSource->pData[x]);
  598. }
  599. pNewAddress->u.e164[pSource->wDataLength] = '\0';
  600. }
  601. else
  602. {
  603. pNewAddress->u.e164[0] = '\0';
  604. }
  605. }
  606. return CS_OK;
  607. }
  608. //====================================================================================
  609. //====================================================================================
  610. static CS_STATUS
  611. Q931AliasAddrToAliasItem(PCC_ALIASITEM *ppTarget, AliasAddress *pSource)
  612. {
  613. PCC_ALIASITEM pNewItem = NULL;
  614. WORD y;
  615. if (ppTarget == NULL)
  616. {
  617. return CS_BAD_PARAM;
  618. }
  619. if (pSource == NULL)
  620. {
  621. *ppTarget = NULL;
  622. return CS_OK;
  623. }
  624. pNewItem = (PCC_ALIASITEM)Malloc(sizeof(CC_ALIASITEM));
  625. if (pNewItem == NULL)
  626. {
  627. *ppTarget = NULL;
  628. return CS_NO_MEMORY;
  629. }
  630. memset(pNewItem, 0, sizeof(*pNewItem));
  631. switch (pSource->choice)
  632. {
  633. case h323_ID_chosen:
  634. pNewItem->wType = CC_ALIAS_H323_ID;
  635. if ((pSource->u.h323_ID.length != 0) &&
  636. (pSource->u.h323_ID.value != NULL))
  637. {
  638. // convert the text from UNICODE to ascii.
  639. pNewItem->wDataLength = (WORD)pSource->u.h323_ID.length;
  640. pNewItem->pData = (LPWSTR)Malloc(pSource->u.h323_ID.length * sizeof(pNewItem->pData[0]));
  641. if (pNewItem->pData == NULL)
  642. {
  643. Free(pNewItem);
  644. return CS_NO_MEMORY;
  645. }
  646. for (y = 0; y < pSource->u.h323_ID.length; y++)
  647. {
  648. pNewItem->pData[y] = (WCHAR)((pSource->u.h323_ID.value)[y]);
  649. }
  650. }
  651. break;
  652. case e164_chosen:
  653. pNewItem->wType = CC_ALIAS_H323_PHONE;
  654. pNewItem->wDataLength = (WORD)strlen(pSource->u.e164);
  655. pNewItem->pData = (LPWSTR)Malloc((pNewItem->wDataLength + 1) * sizeof(pNewItem->pData[0]));
  656. if (pNewItem->pData == NULL)
  657. {
  658. Free(pNewItem);
  659. return CS_NO_MEMORY;
  660. }
  661. for (y = 0; y < pNewItem->wDataLength; y++)
  662. {
  663. pNewItem->pData[y] = pSource->u.e164[y];
  664. }
  665. pNewItem->pData[pNewItem->wDataLength] = 0;
  666. break;
  667. default:
  668. Free(pNewItem);
  669. *ppTarget = NULL;
  670. return CS_BAD_PARAM;
  671. } // switch
  672. *ppTarget = pNewItem;
  673. return CS_OK;
  674. }
  675. //====================================================================================
  676. //====================================================================================
  677. static CS_STATUS
  678. Q931ClearAliasAddr(AliasAddress *pSource)
  679. {
  680. if (pSource)
  681. {
  682. if (pSource->choice == h323_ID_chosen)
  683. {
  684. if (pSource->u.h323_ID.value)
  685. {
  686. Free(pSource->u.h323_ID.value);
  687. }
  688. }
  689. }
  690. return CS_OK;
  691. }
  692. //------------------------------------------------------------------------------
  693. // Parse and return a single octet encoded value, See Q931 section 4.5.1.
  694. //
  695. // Parameters:
  696. // BufferPtr Pointer to a descriptor of the buffer
  697. // containing the length and a pointer
  698. // to the raw bytes of the input stream.
  699. // Ident Pointer to space for field identifier
  700. // Value Pointer to space for field value
  701. //------------------------------------------------------------------------------
  702. static HRESULT
  703. ParseSingleOctetType1(
  704. PBUFFERDESCR BufferDescriptor,
  705. BYTE *Ident,
  706. BYTE *Value)
  707. {
  708. // There has to be at least 1 byte in the stream to be
  709. // able to parse the single octet value
  710. if (BufferDescriptor->Length < 1)
  711. {
  712. return CS_ENDOFINPUT;
  713. }
  714. // low bits (0, 1, 2, 3) of the byte are the value
  715. *Value = (BYTE)(*BufferDescriptor->BufferPtr & TYPE1VALUEMASK);
  716. // higher bits (4, 5, 6) are the identifier. bit 7 is always 1,
  717. // and is not returned as part of the id.
  718. *Ident = (BYTE)((*BufferDescriptor->BufferPtr & 0x70) >> 4);
  719. BufferDescriptor->BufferPtr++;
  720. BufferDescriptor->Length--;
  721. return CS_OK;
  722. }
  723. //------------------------------------------------------------------------------
  724. // Parse and return a single octet encoded value, See Q931 section 4.5.1.
  725. // This octet has no value, only an identifier.
  726. //
  727. // Parameters:
  728. // BufferPtr Pointer to a descriptor of the buffer containing the
  729. // length and a pointer to the raw bytes of the input stream.
  730. // Ident Pointer to space for field identifier
  731. //------------------------------------------------------------------------------
  732. static HRESULT
  733. ParseSingleOctetType2(
  734. PBUFFERDESCR BufferDescriptor,
  735. BYTE *Ident)
  736. {
  737. // There has to be at least 1 byte in the stream to be
  738. // able to parse the single octet value
  739. if (BufferDescriptor->Length < 1)
  740. {
  741. return CS_ENDOFINPUT;
  742. }
  743. // low 7 bits of the byte are the identifier
  744. *Ident = (BYTE)(*BufferDescriptor->BufferPtr & 0x7f);
  745. BufferDescriptor->BufferPtr++;
  746. BufferDescriptor->Length--;
  747. return CS_OK;
  748. }
  749. //------------------------------------------------------------------------------
  750. // Parse and return a variable length Q931 field see Q931 section 4.5.1.
  751. //
  752. // Parameters :
  753. // BufferPtr Pointer to a descriptor of the buffer
  754. // containing the length and a pointer
  755. // to the raw bytes of the input stream.
  756. // Ident Pointer to space for field identifier
  757. // Length Pointer to space for the length
  758. // Contents Pointer to space for the bytes of the field
  759. //------------------------------------------------------------------------------
  760. static HRESULT
  761. ParseVariableOctet(
  762. PBUFFERDESCR BufferDescriptor,
  763. BYTE *Ident,
  764. BYTE *Length,
  765. BYTE *Contents)
  766. {
  767. register int i;
  768. BYTE *Tempptr;
  769. // There has to be at least 2 bytes in order just to get
  770. // the length and the identifier
  771. // able to parse the single octet value
  772. if (BufferDescriptor->Length < 2)
  773. {
  774. return CS_ENDOFINPUT;
  775. }
  776. // low 7 bits of the first byte are the identifier
  777. *Ident= (BYTE)(*BufferDescriptor->BufferPtr & 0x7f);
  778. BufferDescriptor->BufferPtr++;
  779. BufferDescriptor->Length--;
  780. // The next byte is the length
  781. *Length = *BufferDescriptor->BufferPtr;
  782. BufferDescriptor->BufferPtr++;
  783. BufferDescriptor->Length--;
  784. if (BufferDescriptor->Length < *Length)
  785. {
  786. return CS_ENDOFINPUT;
  787. }
  788. Tempptr = Contents;
  789. for (i = 0; i < *Length; i++)
  790. {
  791. // Copy the bytes out of the rest of the buffer
  792. *Tempptr = *BufferDescriptor->BufferPtr;
  793. BufferDescriptor->BufferPtr++;
  794. BufferDescriptor->Length--;
  795. Tempptr++;
  796. }
  797. return CS_OK;
  798. }
  799. //------------------------------------------------------------------------------
  800. // Parse and return a variable length Q931 field see Q931 section 4.5.1.
  801. //------------------------------------------------------------------------------
  802. static HRESULT
  803. ParseVariableASN(
  804. PBUFFERDESCR BufferDescriptor,
  805. BYTE *Ident,
  806. BYTE *ProtocolDiscriminator,
  807. WORD *UserInformationLength, // Length of the User Information.
  808. BYTE *UserInformation) // Bytes of the User Information.
  809. {
  810. register int i;
  811. BYTE *Tempptr;
  812. WORD ContentsLength; // Length of the full UserUser contents.
  813. *UserInformationLength = 0;
  814. // There has to be at least 4 bytes for the IE identifier,
  815. // the contents length, and the protocol discriminator (1 + 2 + 1).
  816. if (BufferDescriptor->Length < 4)
  817. {
  818. return CS_ENDOFINPUT;
  819. }
  820. // low 7 bits of the first byte are the identifier
  821. *Ident= (BYTE)(*BufferDescriptor->BufferPtr & 0x7f);
  822. BufferDescriptor->BufferPtr++;
  823. BufferDescriptor->Length--;
  824. // The next 2 bytes are the length
  825. ContentsLength = *(BufferDescriptor->BufferPtr);
  826. BufferDescriptor->BufferPtr++;
  827. BufferDescriptor->Length--;
  828. ContentsLength = (WORD)((ContentsLength << 8) + *BufferDescriptor->BufferPtr);
  829. BufferDescriptor->BufferPtr++;
  830. BufferDescriptor->Length--;
  831. if (BufferDescriptor->Length < ContentsLength)
  832. {
  833. return CS_ENDOFINPUT;
  834. }
  835. // The next byte is the protocol discriminator.
  836. *ProtocolDiscriminator = *BufferDescriptor->BufferPtr;
  837. BufferDescriptor->BufferPtr++;
  838. BufferDescriptor->Length--;
  839. if (ContentsLength > 0)
  840. {
  841. *UserInformationLength = (WORD)(ContentsLength - 1);
  842. }
  843. Tempptr = UserInformation;
  844. for (i = 0; i < *UserInformationLength; i++)
  845. {
  846. // Copy the bytes out of the rest of the buffer
  847. *Tempptr = *BufferDescriptor->BufferPtr;
  848. BufferDescriptor->BufferPtr++;
  849. BufferDescriptor->Length--;
  850. Tempptr++;
  851. }
  852. return CS_OK;
  853. }
  854. //------------------------------------------------------------------------------
  855. // Get the identifier of the next field from the buffer and
  856. // return it. The buffer pointer is not incremented, To
  857. // parse the field and extract its values, the above functions
  858. // should be used. See Q931 table 4-3 for the encodings of the
  859. // identifiers.
  860. //
  861. // Parameters:
  862. // BufferPtr Pointer to the buffer space
  863. //------------------------------------------------------------------------------
  864. static BYTE
  865. GetNextIdent(
  866. void *BufferPtr)
  867. {
  868. FIELDIDENTTYPE Ident;
  869. // Extract the first byte from the buffer
  870. Ident= (*(FIELDIDENTTYPE *)BufferPtr);
  871. // This value can be returned as the identifier as long
  872. // as it is not a single Octet - Type 1 element.
  873. // Those items must have the value removed from them
  874. // before they can be returned.
  875. if ((Ident & 0x80) && ((Ident & TYPE1IDENTMASK) != 0xA0))
  876. {
  877. return (BYTE)(Ident & TYPE1IDENTMASK);
  878. }
  879. return Ident;
  880. }
  881. //------------------------------------------------------------------------------
  882. // Parse and return a protocol discriminator. See Q931 section 4.2.
  883. // The octet pointed to by **BufferPtr is the protocol Discriminator.
  884. //
  885. // Parameters:
  886. // BufferPtr Pointer to a descriptor of the buffer
  887. // containing the length and a pointer
  888. // to the raw bytes of the input stream.
  889. // Discrim Pointer to space for discriminator
  890. //------------------------------------------------------------------------------
  891. static HRESULT
  892. ParseProtocolDiscriminator(
  893. PBUFFERDESCR BufferDescriptor,
  894. PDTYPE *Discrim)
  895. {
  896. // There has to be at least enough bytes left in the
  897. // string for the operation
  898. if (BufferDescriptor->Length < sizeof(PDTYPE))
  899. {
  900. return CS_MESSAGE_TOO_SHORT;
  901. }
  902. *Discrim = *(PDTYPE *)BufferDescriptor->BufferPtr;
  903. if (*Discrim != Q931PDVALUE)
  904. {
  905. return CS_INVALID_PROTOCOL;
  906. }
  907. BufferDescriptor->BufferPtr += sizeof(PDTYPE);
  908. BufferDescriptor->Length -= sizeof(PDTYPE);
  909. return CS_OK;
  910. }
  911. //------------------------------------------------------------------------------
  912. // Parse and return a variable length Q931 call reference see
  913. // Q931 section 4.3.
  914. //
  915. // Parameters:
  916. // BufferPtr Pointer to a descriptor of the buffer
  917. // containing the length and a pointer
  918. // to the raw bytes of the input stream.
  919. // Length Pointer to space for the length
  920. // Contents Pointer to space for the bytes of the field
  921. //------------------------------------------------------------------------------
  922. static HRESULT
  923. ParseCallReference(
  924. PBUFFERDESCR BufferDescriptor,
  925. CRTYPE *CallReference)
  926. {
  927. register int i;
  928. BYTE Length;
  929. // There has to be at least enough bytes left in the
  930. // string for the length byte
  931. if (BufferDescriptor->Length < 1)
  932. {
  933. return CS_MESSAGE_TOO_SHORT;
  934. }
  935. // low 4 bits of the first byte are the length.
  936. // the rest of the bits are zeroes.
  937. Length = (BYTE)(*BufferDescriptor->BufferPtr & 0x0f);
  938. BufferDescriptor->BufferPtr++;
  939. BufferDescriptor->Length--;
  940. // There has to be at least enough bytes left in the
  941. // string for the operation
  942. if (BufferDescriptor->Length < Length)
  943. {
  944. return CS_MESSAGE_TOO_SHORT;
  945. }
  946. *CallReference = 0; // length can be 0, so initialize here first...
  947. for (i = 0; i < Length; i++)
  948. {
  949. if (i < sizeof(CRTYPE))
  950. {
  951. // Copy the bytes out of the rest of the buffer
  952. *CallReference = (WORD)((*CallReference << 8) +
  953. *BufferDescriptor->BufferPtr);
  954. }
  955. BufferDescriptor->BufferPtr++;
  956. BufferDescriptor->Length--;
  957. }
  958. // note: the high order bit of the value represents callee relationship.
  959. return CS_OK;
  960. }
  961. //------------------------------------------------------------------------------
  962. // Parse and return a message type. See Q931 section 4.4.
  963. // The octet pointed to by **BufferPtr is the message type.
  964. //
  965. // Parameters:
  966. // BufferPtr Pointer to a descriptor of the buffer
  967. // containing the length and a pointer
  968. // to the raw bytes of the input stream.
  969. // MessageType Pointer to space for message type
  970. //------------------------------------------------------------------------------
  971. static HRESULT
  972. ParseMessageType(
  973. PBUFFERDESCR BufferDescriptor,
  974. MESSAGEIDTYPE *MessageType)
  975. {
  976. register int i;
  977. // There has to be at least enough bytes left in the
  978. // string for the operation
  979. if (BufferDescriptor->Length < sizeof(MESSAGEIDTYPE))
  980. {
  981. return CS_MESSAGE_TOO_SHORT;
  982. }
  983. *MessageType = (BYTE)(*((MESSAGEIDTYPE *)BufferDescriptor->BufferPtr) & MESSAGETYPEMASK);
  984. for (i = 0; i < sizeof(MessageSet) / sizeof(MESSAGEIDTYPE); i++)
  985. {
  986. if (MessageSet[i] == *MessageType)
  987. {
  988. break;
  989. }
  990. }
  991. if (i >= sizeof(MessageSet) / sizeof(MESSAGEIDTYPE))
  992. {
  993. return CS_INVALID_MESSAGE_TYPE;
  994. }
  995. BufferDescriptor->BufferPtr += sizeof(MESSAGEIDTYPE);
  996. BufferDescriptor->Length -= sizeof(MESSAGEIDTYPE);
  997. return CS_OK;
  998. }
  999. //------------------------------------------------------------------------------
  1000. // Parse an optional shift field
  1001. //
  1002. // Parameters:
  1003. // BufferPtr Pointer to a descriptor of the buffer containing the
  1004. // length and a pointer to the raw bytes of the input stream.
  1005. // FieldStruct Pointer to space for parsed shift message information.
  1006. //------------------------------------------------------------------------------
  1007. static HRESULT
  1008. ParseShift(
  1009. PBUFFERDESCR BufferDescriptor,
  1010. PSHIFTIE FieldStruct)
  1011. {
  1012. BYTE Ident;
  1013. memset(FieldStruct, 0, sizeof(SHIFTIE));
  1014. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_SHIFT)
  1015. {
  1016. FieldStruct->Present = TRUE;
  1017. return ParseSingleOctetType1(BufferDescriptor,
  1018. &Ident, &FieldStruct->Value);
  1019. }
  1020. else
  1021. {
  1022. FieldStruct->Present = FALSE;
  1023. }
  1024. return CS_OK;
  1025. }
  1026. //------------------------------------------------------------------------------
  1027. // Parse an optional facility ie field
  1028. //
  1029. // Parameters:
  1030. // BufferPtr Pointer to a descriptor of the buffer
  1031. // containing the length and a pointer
  1032. // to the raw bytes of the input stream.
  1033. // FieldStruct Pointer to space for parsed facility
  1034. // information.
  1035. //------------------------------------------------------------------------------
  1036. static HRESULT
  1037. ParseFacility(
  1038. PBUFFERDESCR BufferDescriptor,
  1039. PFACILITYIE FieldStruct)
  1040. {
  1041. BYTE Ident;
  1042. memset(FieldStruct, 0, sizeof(FACILITYIE));
  1043. FieldStruct->Present = FALSE;
  1044. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_FACILITY)
  1045. {
  1046. HRESULT ParseResult;
  1047. ParseResult = ParseVariableOctet(BufferDescriptor,
  1048. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1049. if (ParseResult != CS_OK)
  1050. {
  1051. return ParseResult;
  1052. }
  1053. if (FieldStruct->Length > 0)
  1054. {
  1055. FieldStruct->Present = TRUE;
  1056. }
  1057. }
  1058. return CS_OK;
  1059. }
  1060. //------------------------------------------------------------------------------
  1061. // Parse an optional more data field
  1062. //
  1063. // Parameters:
  1064. // BufferPtr Pointer to a descriptor of the buffer
  1065. // containing the length and a pointer
  1066. // to the raw bytes of the input stream.
  1067. // FieldStruct Pointer to space for parsed field information
  1068. //------------------------------------------------------------------------------
  1069. static HRESULT
  1070. ParseMoreData(
  1071. PBUFFERDESCR BufferDescriptor,
  1072. PMOREDATAIE FieldStruct)
  1073. {
  1074. BYTE Ident;
  1075. memset(FieldStruct, 0, sizeof(MOREDATAIE));
  1076. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_MORE)
  1077. {
  1078. FieldStruct->Present = TRUE;
  1079. return ParseSingleOctetType2(BufferDescriptor, &Ident);
  1080. }
  1081. else
  1082. {
  1083. FieldStruct->Present = FALSE;
  1084. }
  1085. return CS_OK;
  1086. }
  1087. //------------------------------------------------------------------------------
  1088. // Parse an optional sending clomplete field. Q931 section 4.4.
  1089. // The octet pointed to by **BufferPtr is the message type.
  1090. //
  1091. // Parameters:
  1092. // BufferPtr Pointer to a descriptor of the buffer
  1093. // containing the length and a pointer
  1094. // to the raw bytes of the input stream.
  1095. // MessageType Pointer to space for message type
  1096. //------------------------------------------------------------------------------
  1097. static HRESULT
  1098. ParseSendingComplete(
  1099. PBUFFERDESCR BufferDescriptor,
  1100. PSENDCOMPLIE FieldStruct)
  1101. {
  1102. BYTE Ident;
  1103. memset(FieldStruct, 0, sizeof(SENDCOMPLIE));
  1104. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_SENDINGCOMPLETE)
  1105. {
  1106. FieldStruct->Present = TRUE;
  1107. return ParseSingleOctetType2(BufferDescriptor, &Ident);
  1108. }
  1109. else
  1110. {
  1111. FieldStruct->Present = FALSE;
  1112. }
  1113. return CS_OK;
  1114. }
  1115. //------------------------------------------------------------------------------
  1116. // Parse an optional congestion level field
  1117. //
  1118. // Parameters:
  1119. // BufferPtr Pointer to a descriptor of the buffer
  1120. // containing the length and a pointer
  1121. // to the raw bytes of the input stream.
  1122. // FieldStruct Pointer to space for parsed congestion
  1123. // level information.
  1124. //------------------------------------------------------------------------------
  1125. static HRESULT
  1126. ParseCongestionLevel(
  1127. PBUFFERDESCR BufferDescriptor,
  1128. PCONGESTIONIE FieldStruct)
  1129. {
  1130. BYTE Ident;
  1131. memset(FieldStruct, 0, sizeof(CONGESTIONIE));
  1132. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CONGESTION)
  1133. {
  1134. FieldStruct->Present = TRUE;
  1135. return ParseSingleOctetType1(BufferDescriptor,
  1136. &Ident, &FieldStruct->Value);
  1137. }
  1138. else
  1139. {
  1140. FieldStruct->Present = FALSE;
  1141. }
  1142. return CS_OK;
  1143. }
  1144. //------------------------------------------------------------------------------
  1145. // Parse an optional repeat indicator field
  1146. //
  1147. // Parameters:
  1148. // BufferPtr Pointer to a descriptor of the buffer
  1149. // containing the length and a pointer
  1150. // to the raw bytes of the input stream.
  1151. // FieldStruct Pointer to space for parsed repeat
  1152. // information.
  1153. //------------------------------------------------------------------------------
  1154. static HRESULT
  1155. ParseRepeatIndicator(
  1156. PBUFFERDESCR BufferDescriptor,
  1157. PREPEATIE FieldStruct)
  1158. {
  1159. BYTE Ident;
  1160. memset(FieldStruct, 0, sizeof(REPEATIE));
  1161. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_REPEAT)
  1162. {
  1163. FieldStruct->Present = TRUE;
  1164. return ParseSingleOctetType1(BufferDescriptor,
  1165. &Ident, &FieldStruct->Value);
  1166. }
  1167. else
  1168. {
  1169. FieldStruct->Present = FALSE;
  1170. }
  1171. return CS_OK;
  1172. }
  1173. //------------------------------------------------------------------------------
  1174. // Parse an optional segmented message field
  1175. //
  1176. // Parameters:
  1177. // BufferPtr Pointer to a descriptor of the buffer
  1178. // containing the length and a pointer
  1179. // to the raw bytes of the input stream.
  1180. // FieldStruct Pointer to space for parsed segmented message
  1181. // information.
  1182. //------------------------------------------------------------------------------
  1183. static HRESULT
  1184. ParseSegmented(
  1185. PBUFFERDESCR BufferDescriptor,
  1186. PSEGMENTEDIE FieldStruct)
  1187. {
  1188. BYTE Ident;
  1189. memset(FieldStruct, 0, sizeof(SEGMENTEDIE));
  1190. FieldStruct->Present = FALSE;
  1191. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_SEGMENTED)
  1192. {
  1193. HRESULT ParseResult;
  1194. ParseResult = ParseVariableOctet(BufferDescriptor,
  1195. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1196. if (ParseResult != CS_OK)
  1197. {
  1198. return ParseResult;
  1199. }
  1200. if (FieldStruct->Length > 0)
  1201. {
  1202. FieldStruct->Present = TRUE;
  1203. }
  1204. }
  1205. return CS_OK;
  1206. }
  1207. //------------------------------------------------------------------------------
  1208. // Parse an optional bearer capability field
  1209. //
  1210. // Parameters:
  1211. // BufferPtr Pointer to a descriptor of the buffer
  1212. // containing the length and a pointer
  1213. // to the raw bytes of the input stream.
  1214. // FieldStruct Pointer to space for parsed bearer capability
  1215. // information.
  1216. //------------------------------------------------------------------------------
  1217. static HRESULT
  1218. ParseBearerCapability(
  1219. PBUFFERDESCR BufferDescriptor,
  1220. PBEARERCAPIE FieldStruct)
  1221. {
  1222. BYTE Ident;
  1223. memset(FieldStruct, 0, sizeof(BEARERCAPIE));
  1224. FieldStruct->Present = FALSE;
  1225. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_BEARERCAP)
  1226. {
  1227. HRESULT ParseResult;
  1228. ParseResult = ParseVariableOctet(BufferDescriptor,
  1229. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1230. if (ParseResult != CS_OK)
  1231. {
  1232. return ParseResult;
  1233. }
  1234. if (FieldStruct->Length > 0)
  1235. {
  1236. FieldStruct->Present = TRUE;
  1237. }
  1238. }
  1239. return CS_OK;
  1240. }
  1241. //------------------------------------------------------------------------------
  1242. // Parse an optional cause field
  1243. //
  1244. // Parameters:
  1245. // BufferPtr Pointer to a descriptor of the buffer
  1246. // containing the length and a pointer
  1247. // to the raw bytes of the input stream.
  1248. // FieldStruct Pointer to space for parsed cause
  1249. // information.
  1250. //------------------------------------------------------------------------------
  1251. static HRESULT
  1252. ParseCause(
  1253. PBUFFERDESCR BufferDescriptor,
  1254. PCAUSEIE FieldStruct)
  1255. {
  1256. BYTE Ident;
  1257. memset(FieldStruct, 0, sizeof(CAUSEIE));
  1258. FieldStruct->Present = FALSE;
  1259. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CAUSE)
  1260. {
  1261. HRESULT ParseResult;
  1262. ParseResult = ParseVariableOctet(BufferDescriptor,
  1263. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1264. if (ParseResult != CS_OK)
  1265. {
  1266. return ParseResult;
  1267. }
  1268. if (FieldStruct->Length > 0)
  1269. {
  1270. FieldStruct->Present = TRUE;
  1271. }
  1272. }
  1273. return CS_OK;
  1274. }
  1275. //------------------------------------------------------------------------------
  1276. // Parse an optional call identity field
  1277. //
  1278. // Parameters:
  1279. // BufferPtr Pointer to a descriptor of the buffer
  1280. // containing the length and a pointer
  1281. // to the raw bytes of the input stream.
  1282. // FieldStruct Pointer to space for parsed call identity
  1283. // information.
  1284. //------------------------------------------------------------------------------
  1285. static HRESULT
  1286. ParseCallIdentity(
  1287. PBUFFERDESCR BufferDescriptor,
  1288. PCALLIDENTIE FieldStruct)
  1289. {
  1290. BYTE Ident;
  1291. memset(FieldStruct, 0, sizeof(CALLIDENTIE));
  1292. FieldStruct->Present = FALSE;
  1293. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CALLIDENT)
  1294. {
  1295. HRESULT ParseResult;
  1296. ParseResult = ParseVariableOctet(BufferDescriptor,
  1297. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1298. if (ParseResult != CS_OK)
  1299. {
  1300. return ParseResult;
  1301. }
  1302. if (FieldStruct->Length > 0)
  1303. {
  1304. FieldStruct->Present = TRUE;
  1305. }
  1306. }
  1307. return CS_OK;
  1308. }
  1309. //------------------------------------------------------------------------------
  1310. // Parse an optional call state field
  1311. //
  1312. // Parameters:
  1313. // BufferPtr Pointer to a descriptor of the buffer
  1314. // containing the length and a pointer
  1315. // to the raw bytes of the input stream.
  1316. // FieldStruct Pointer to space for parsed call state
  1317. // information.
  1318. //------------------------------------------------------------------------------
  1319. static HRESULT
  1320. ParseCallState(
  1321. PBUFFERDESCR BufferDescriptor,
  1322. PCALLSTATEIE FieldStruct)
  1323. {
  1324. BYTE Ident;
  1325. memset(FieldStruct, 0, sizeof(CALLSTATEIE));
  1326. FieldStruct->Present = FALSE;
  1327. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CALLSTATE)
  1328. {
  1329. HRESULT ParseResult;
  1330. ParseResult = ParseVariableOctet(BufferDescriptor,
  1331. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1332. if (ParseResult != CS_OK)
  1333. {
  1334. return ParseResult;
  1335. }
  1336. if (FieldStruct->Length > 0)
  1337. {
  1338. FieldStruct->Present = TRUE;
  1339. }
  1340. }
  1341. return CS_OK;
  1342. }
  1343. //------------------------------------------------------------------------------
  1344. // Parse an optional channel identification field
  1345. //
  1346. // Parameters:
  1347. // BufferPtr Pointer to a descriptor of the buffer
  1348. // containing the length and a pointer
  1349. // to the raw bytes of the input stream.
  1350. // FieldStruct Pointer to space for parsed channel identity
  1351. // information.
  1352. //------------------------------------------------------------------------------
  1353. static HRESULT
  1354. ParseChannelIdentification(
  1355. PBUFFERDESCR BufferDescriptor,
  1356. PCHANIDENTIE FieldStruct)
  1357. {
  1358. BYTE Ident;
  1359. memset(FieldStruct, 0, sizeof(CHANIDENTIE));
  1360. FieldStruct->Present = FALSE;
  1361. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CHANNELIDENT)
  1362. {
  1363. HRESULT ParseResult;
  1364. ParseResult = ParseVariableOctet(BufferDescriptor,
  1365. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1366. if (ParseResult != CS_OK)
  1367. {
  1368. return ParseResult;
  1369. }
  1370. if (FieldStruct->Length > 0)
  1371. {
  1372. FieldStruct->Present = TRUE;
  1373. }
  1374. }
  1375. return CS_OK;
  1376. }
  1377. //------------------------------------------------------------------------------
  1378. // Parse an optional progress indication field
  1379. //
  1380. // Parameters:
  1381. // BufferPtr Pointer to a descriptor of the buffer
  1382. // containing the length and a pointer
  1383. // to the raw bytes of the input stream.
  1384. // FieldStruct Pointer to space for parsed progress
  1385. // information.
  1386. //------------------------------------------------------------------------------
  1387. static HRESULT
  1388. ParseProgress(
  1389. PBUFFERDESCR BufferDescriptor,
  1390. PPROGRESSIE FieldStruct)
  1391. {
  1392. BYTE Ident;
  1393. memset(FieldStruct, 0, sizeof(PROGRESSIE));
  1394. FieldStruct->Present = FALSE;
  1395. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_PROGRESS)
  1396. {
  1397. HRESULT ParseResult;
  1398. ParseResult = ParseVariableOctet(BufferDescriptor,
  1399. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1400. if (ParseResult != CS_OK)
  1401. {
  1402. return ParseResult;
  1403. }
  1404. if (FieldStruct->Length > 0)
  1405. {
  1406. FieldStruct->Present = TRUE;
  1407. }
  1408. }
  1409. return CS_OK;
  1410. }
  1411. //------------------------------------------------------------------------------
  1412. // Parse an optional network specific facilities field
  1413. //
  1414. // Parameters:
  1415. // BufferPtr Pointer to a descriptor of the buffer
  1416. // containing the length and a pointer
  1417. // to the raw bytes of the input stream.
  1418. // FieldStruct Pointer to space for parsed network facitlities
  1419. // information.
  1420. //------------------------------------------------------------------------------
  1421. static HRESULT
  1422. ParseNetworkSpec(
  1423. PBUFFERDESCR BufferDescriptor,
  1424. PNETWORKIE FieldStruct)
  1425. {
  1426. BYTE Ident;
  1427. memset(FieldStruct, 0, sizeof(NETWORKIE));
  1428. FieldStruct->Present = FALSE;
  1429. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_NETWORKSPEC)
  1430. {
  1431. HRESULT ParseResult;
  1432. ParseResult = ParseVariableOctet(BufferDescriptor,
  1433. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1434. if (ParseResult != CS_OK)
  1435. {
  1436. return ParseResult;
  1437. }
  1438. if (FieldStruct->Length > 0)
  1439. {
  1440. FieldStruct->Present = TRUE;
  1441. }
  1442. }
  1443. return CS_OK;
  1444. }
  1445. //------------------------------------------------------------------------------
  1446. // Parse an optional notification indicator field
  1447. //
  1448. // Parameters:
  1449. // BufferPtr Pointer to a descriptor of the buffer
  1450. // containing the length and a pointer
  1451. // to the raw bytes of the input stream.
  1452. // FieldStruct Pointer to space for parse notification indicator
  1453. // information.
  1454. //------------------------------------------------------------------------------
  1455. static HRESULT
  1456. ParseNotificationIndicator(
  1457. PBUFFERDESCR BufferDescriptor,
  1458. PNOTIFICATIONINDIE FieldStruct)
  1459. {
  1460. BYTE Ident;
  1461. memset(FieldStruct, 0, sizeof(NOTIFICATIONINDIE));
  1462. FieldStruct->Present = FALSE;
  1463. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_NOTIFICATION)
  1464. {
  1465. HRESULT ParseResult;
  1466. ParseResult = ParseVariableOctet(BufferDescriptor,
  1467. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1468. if (ParseResult != CS_OK)
  1469. {
  1470. return ParseResult;
  1471. }
  1472. if (FieldStruct->Length > 0)
  1473. {
  1474. FieldStruct->Present = TRUE;
  1475. }
  1476. }
  1477. return CS_OK;
  1478. }
  1479. //------------------------------------------------------------------------------
  1480. // Parse an optional display field
  1481. //
  1482. // Parameters:
  1483. // BufferPtr Pointer to a descriptor of the buffer
  1484. // containing the length and a pointer
  1485. // to the raw bytes of the input stream.
  1486. // FieldStruct Pointer to space for parsed display
  1487. // information.
  1488. //------------------------------------------------------------------------------
  1489. static HRESULT
  1490. ParseDisplay(
  1491. PBUFFERDESCR BufferDescriptor,
  1492. PDISPLAYIE FieldStruct)
  1493. {
  1494. BYTE Ident;
  1495. memset(FieldStruct, 0, sizeof(DISPLAYIE));
  1496. FieldStruct->Present = FALSE;
  1497. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_DISPLAY)
  1498. {
  1499. HRESULT ParseResult;
  1500. ParseResult = ParseVariableOctet(BufferDescriptor,
  1501. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1502. if (ParseResult != CS_OK)
  1503. {
  1504. return ParseResult;
  1505. }
  1506. if (FieldStruct->Length > 0)
  1507. {
  1508. FieldStruct->Present = TRUE;
  1509. }
  1510. }
  1511. return CS_OK;
  1512. }
  1513. //------------------------------------------------------------------------------
  1514. // Parse an optional date/time field
  1515. //
  1516. // Parameters:
  1517. // BufferPtr Pointer to a descriptor of the buffer
  1518. // containing the length and a pointer
  1519. // to the raw bytes of the input stream.
  1520. // FieldStruct Pointer to space for parsed date/time
  1521. // information.
  1522. //------------------------------------------------------------------------------
  1523. static HRESULT
  1524. ParseDate(
  1525. PBUFFERDESCR BufferDescriptor,
  1526. PDATEIE FieldStruct)
  1527. {
  1528. BYTE Ident;
  1529. memset(FieldStruct, 0, sizeof(DATEIE));
  1530. FieldStruct->Present = FALSE;
  1531. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_DATE)
  1532. {
  1533. HRESULT ParseResult;
  1534. ParseResult = ParseVariableOctet(BufferDescriptor,
  1535. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1536. if (ParseResult != CS_OK)
  1537. {
  1538. return ParseResult;
  1539. }
  1540. if (FieldStruct->Length > 0)
  1541. {
  1542. FieldStruct->Present = TRUE;
  1543. }
  1544. }
  1545. return CS_OK;
  1546. }
  1547. //------------------------------------------------------------------------------
  1548. // Parse an optional keypad field
  1549. //
  1550. // Parameters:
  1551. // BufferPtr Pointer to a descriptor of the buffer
  1552. // containing the length and a pointer
  1553. // to the raw bytes of the input stream.
  1554. // FieldStruct Pointer to space for parsed keypad
  1555. // information.
  1556. //------------------------------------------------------------------------------
  1557. static HRESULT
  1558. ParseKeypad(
  1559. PBUFFERDESCR BufferDescriptor,
  1560. PKEYPADIE FieldStruct)
  1561. {
  1562. BYTE Ident;
  1563. memset(FieldStruct, 0, sizeof(KEYPADIE));
  1564. FieldStruct->Present = FALSE;
  1565. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_KEYPAD)
  1566. {
  1567. HRESULT ParseResult;
  1568. ParseResult = ParseVariableOctet(BufferDescriptor,
  1569. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1570. if (ParseResult != CS_OK)
  1571. {
  1572. return ParseResult;
  1573. }
  1574. if (FieldStruct->Length > 0)
  1575. {
  1576. FieldStruct->Present = TRUE;
  1577. }
  1578. }
  1579. return CS_OK;
  1580. }
  1581. //------------------------------------------------------------------------------
  1582. // Parse an optional signal field
  1583. //
  1584. // Parameters:
  1585. // BufferPtr Pointer to a descriptor of the buffer
  1586. // containing the length and a pointer
  1587. // to the raw bytes of the input stream.
  1588. // FieldStruct Pointer to space for parsed signal
  1589. // information.
  1590. //------------------------------------------------------------------------------
  1591. static HRESULT
  1592. ParseSignal(
  1593. PBUFFERDESCR BufferDescriptor,
  1594. PSIGNALIE FieldStruct)
  1595. {
  1596. BYTE Ident;
  1597. memset(FieldStruct, 0, sizeof(SIGNALIE));
  1598. FieldStruct->Present = FALSE;
  1599. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_SIGNAL)
  1600. {
  1601. HRESULT ParseResult;
  1602. ParseResult = ParseVariableOctet(BufferDescriptor,
  1603. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1604. if (ParseResult != CS_OK)
  1605. {
  1606. return ParseResult;
  1607. }
  1608. if (FieldStruct->Length > 0)
  1609. {
  1610. FieldStruct->Present = TRUE;
  1611. }
  1612. }
  1613. return CS_OK;
  1614. }
  1615. //------------------------------------------------------------------------------
  1616. // Parse an optional information rate field
  1617. //
  1618. // Parameters:
  1619. // BufferPtr Pointer to a descriptor of the buffer
  1620. // containing the length and a pointer
  1621. // to the raw bytes of the input stream.
  1622. // FieldStruct Pointer to space for parsed information rate
  1623. // information.
  1624. //------------------------------------------------------------------------------
  1625. static HRESULT
  1626. ParseInformationRate(
  1627. PBUFFERDESCR BufferDescriptor,
  1628. PINFORATEIE FieldStruct)
  1629. {
  1630. BYTE Ident;
  1631. memset(FieldStruct, 0, sizeof(INFORATEIE));
  1632. FieldStruct->Present = FALSE;
  1633. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_INFORMATIONRATE)
  1634. {
  1635. HRESULT ParseResult;
  1636. ParseResult = ParseVariableOctet(BufferDescriptor,
  1637. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1638. if (ParseResult != CS_OK)
  1639. {
  1640. return ParseResult;
  1641. }
  1642. if (FieldStruct->Length > 0)
  1643. {
  1644. FieldStruct->Present = TRUE;
  1645. }
  1646. }
  1647. return CS_OK;
  1648. }
  1649. //------------------------------------------------------------------------------
  1650. // Parse an optional end to end transit delay field
  1651. //
  1652. // Parameters:
  1653. // BufferPtr Pointer to a descriptor of the buffer
  1654. // containing the length and a pointer
  1655. // to the raw bytes of the input stream.
  1656. // FieldStruct Pointer to space for parsed end to end
  1657. // information.
  1658. //------------------------------------------------------------------------------
  1659. static HRESULT
  1660. ParseEndToEndDelay(
  1661. PBUFFERDESCR BufferDescriptor,
  1662. PENDTOENDDELAYIE FieldStruct)
  1663. {
  1664. BYTE Ident;
  1665. memset(FieldStruct, 0, sizeof(ENDTOENDDELAYIE));
  1666. FieldStruct->Present = FALSE;
  1667. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_ENDTOENDDELAY)
  1668. {
  1669. HRESULT ParseResult;
  1670. ParseResult = ParseVariableOctet(BufferDescriptor,
  1671. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1672. if (ParseResult != CS_OK)
  1673. {
  1674. return ParseResult;
  1675. }
  1676. if (FieldStruct->Length > 0)
  1677. {
  1678. FieldStruct->Present = TRUE;
  1679. }
  1680. }
  1681. return CS_OK;
  1682. }
  1683. //------------------------------------------------------------------------------
  1684. // Parse an optional transit delay field
  1685. //
  1686. // Parameters:
  1687. // BufferPtr Pointer to a descriptor of the buffer
  1688. // containing the length and a pointer
  1689. // to the raw bytes of the input stream.
  1690. // FieldStruct Pointer to space for parsed transit delay
  1691. // information.
  1692. //------------------------------------------------------------------------------
  1693. static HRESULT
  1694. ParseTransitDelay(
  1695. PBUFFERDESCR BufferDescriptor,
  1696. PTRANSITDELAYIE FieldStruct)
  1697. {
  1698. BYTE Ident;
  1699. memset(FieldStruct, 0, sizeof(TRANSITDELAYIE));
  1700. FieldStruct->Present = FALSE;
  1701. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_TRANSITDELAY)
  1702. {
  1703. HRESULT ParseResult;
  1704. ParseResult = ParseVariableOctet(BufferDescriptor,
  1705. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1706. if (ParseResult != CS_OK)
  1707. {
  1708. return ParseResult;
  1709. }
  1710. if (FieldStruct->Length > 0)
  1711. {
  1712. FieldStruct->Present = TRUE;
  1713. }
  1714. }
  1715. return CS_OK;
  1716. }
  1717. //------------------------------------------------------------------------------
  1718. // Parse an optional packet layer binary params field
  1719. //
  1720. // Parameters:
  1721. // BufferPtr Pointer to a descriptor of the buffer
  1722. // containing the length and a pointer
  1723. // to the raw bytes of the input stream.
  1724. // FieldStruct Pointer to space for parsed
  1725. // information.
  1726. //------------------------------------------------------------------------------
  1727. static HRESULT
  1728. ParsePacketLayerParams(
  1729. PBUFFERDESCR BufferDescriptor,
  1730. PPLBINARYPARAMSIE FieldStruct)
  1731. {
  1732. BYTE Ident;
  1733. memset(FieldStruct, 0, sizeof(PLBINARYPARAMSIE));
  1734. FieldStruct->Present = FALSE;
  1735. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_PLBINARYPARAMS)
  1736. {
  1737. HRESULT ParseResult;
  1738. ParseResult = ParseVariableOctet(BufferDescriptor,
  1739. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1740. if (ParseResult != CS_OK)
  1741. {
  1742. return ParseResult;
  1743. }
  1744. if (FieldStruct->Length > 0)
  1745. {
  1746. FieldStruct->Present = TRUE;
  1747. }
  1748. }
  1749. return CS_OK;
  1750. }
  1751. //------------------------------------------------------------------------------
  1752. // Parse an optional packet layer window size field
  1753. //
  1754. // Parameters:
  1755. // BufferPtr Pointer to a descriptor of the buffer
  1756. // containing the length and a pointer
  1757. // to the raw bytes of the input stream.
  1758. // FieldStruct Pointer to space for parsed
  1759. // information.
  1760. //------------------------------------------------------------------------------
  1761. static HRESULT
  1762. ParsePacketLayerWindowSize(
  1763. PBUFFERDESCR BufferDescriptor,
  1764. PPLWINDOWSIZEIE FieldStruct)
  1765. {
  1766. BYTE Ident;
  1767. memset(FieldStruct, 0, sizeof(PLWINDOWSIZEIE));
  1768. FieldStruct->Present = FALSE;
  1769. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_PLWINDOWSIZE)
  1770. {
  1771. HRESULT ParseResult;
  1772. ParseResult = ParseVariableOctet(BufferDescriptor,
  1773. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1774. if (ParseResult != CS_OK)
  1775. {
  1776. return ParseResult;
  1777. }
  1778. if (FieldStruct->Length > 0)
  1779. {
  1780. FieldStruct->Present = TRUE;
  1781. }
  1782. }
  1783. return CS_OK;
  1784. }
  1785. //------------------------------------------------------------------------------
  1786. // Parse an optional packet size field
  1787. //
  1788. // Parameters:
  1789. // BufferPtr Pointer to a descriptor of the buffer
  1790. // containing the length and a pointer
  1791. // to the raw bytes of the input stream.
  1792. // FieldStruct Pointer to space for parse packet size
  1793. // information.
  1794. //------------------------------------------------------------------------------
  1795. static HRESULT
  1796. ParsePacketSize(
  1797. PBUFFERDESCR BufferDescriptor,
  1798. PPACKETSIZEIE FieldStruct)
  1799. {
  1800. BYTE Ident;
  1801. memset(FieldStruct, 0, sizeof(PACKETSIZEIE));
  1802. FieldStruct->Present = FALSE;
  1803. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_PACKETSIZE)
  1804. {
  1805. HRESULT ParseResult;
  1806. ParseResult = ParseVariableOctet(BufferDescriptor,
  1807. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1808. if (ParseResult != CS_OK)
  1809. {
  1810. return ParseResult;
  1811. }
  1812. if (FieldStruct->Length > 0)
  1813. {
  1814. FieldStruct->Present = TRUE;
  1815. }
  1816. }
  1817. return CS_OK;
  1818. }
  1819. //------------------------------------------------------------------------------
  1820. // Parse an optional closed user group field
  1821. //
  1822. // Parameters:
  1823. // BufferPtr Pointer to a descriptor of the buffer
  1824. // containing the length and a pointer
  1825. // to the raw bytes of the input stream.
  1826. // FieldStruct Pointer to space for parsed
  1827. // information.
  1828. //------------------------------------------------------------------------------
  1829. static HRESULT
  1830. ParseClosedUserGroup(
  1831. PBUFFERDESCR BufferDescriptor,
  1832. PCLOSEDUGIE FieldStruct)
  1833. {
  1834. BYTE Ident;
  1835. memset(FieldStruct, 0, sizeof(CLOSEDUGIE));
  1836. FieldStruct->Present = FALSE;
  1837. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CLOSEDUG)
  1838. {
  1839. HRESULT ParseResult;
  1840. ParseResult = ParseVariableOctet(BufferDescriptor,
  1841. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1842. if (ParseResult != CS_OK)
  1843. {
  1844. return ParseResult;
  1845. }
  1846. if (FieldStruct->Length > 0)
  1847. {
  1848. FieldStruct->Present = TRUE;
  1849. }
  1850. }
  1851. return CS_OK;
  1852. }
  1853. //------------------------------------------------------------------------------
  1854. // Parse an optional reverse charge field
  1855. //
  1856. // Parameters:
  1857. // BufferPtr Pointer to a descriptor of the buffer
  1858. // containing the length and a pointer
  1859. // to the raw bytes of the input stream.
  1860. // FieldStruct Pointer to space for parsed
  1861. // information.
  1862. //------------------------------------------------------------------------------
  1863. static HRESULT
  1864. ParseReverseCharge(
  1865. PBUFFERDESCR BufferDescriptor,
  1866. PREVERSECHARGEIE FieldStruct)
  1867. {
  1868. BYTE Ident;
  1869. memset(FieldStruct, 0, sizeof(REVERSECHARGEIE));
  1870. FieldStruct->Present = FALSE;
  1871. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_REVCHARGE)
  1872. {
  1873. HRESULT ParseResult;
  1874. ParseResult = ParseVariableOctet(BufferDescriptor,
  1875. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1876. if (ParseResult != CS_OK)
  1877. {
  1878. return ParseResult;
  1879. }
  1880. if (FieldStruct->Length > 0)
  1881. {
  1882. FieldStruct->Present = TRUE;
  1883. }
  1884. }
  1885. return CS_OK;
  1886. }
  1887. //------------------------------------------------------------------------------
  1888. // Parse an optional calling party number field
  1889. //
  1890. // Parameters:
  1891. // BufferPtr Pointer to a descriptor of the buffer
  1892. // containing the length and a pointer
  1893. // to the raw bytes of the input stream.
  1894. // FieldStruct Pointer to space for parsed
  1895. // information.
  1896. //------------------------------------------------------------------------------
  1897. static HRESULT
  1898. ParseCallingPartyNumber(
  1899. PBUFFERDESCR BufferDescriptor,
  1900. PCALLINGNUMBERIE FieldStruct)
  1901. {
  1902. BYTE Ident;
  1903. memset(FieldStruct, 0, sizeof(CALLINGNUMBERIE));
  1904. FieldStruct->Present = FALSE;
  1905. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CALLINGNUMBER)
  1906. {
  1907. HRESULT ParseResult;
  1908. ParseResult = ParseVariableOctet(BufferDescriptor,
  1909. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1910. if (ParseResult != CS_OK)
  1911. {
  1912. return ParseResult;
  1913. }
  1914. if (FieldStruct->Length > 0)
  1915. {
  1916. FieldStruct->Present = TRUE;
  1917. }
  1918. }
  1919. return CS_OK;
  1920. }
  1921. //------------------------------------------------------------------------------
  1922. // Parse an optional calling party subaddress field
  1923. //
  1924. // Parameters:
  1925. // BufferPtr Pointer to a descriptor of the buffer
  1926. // containing the length and a pointer
  1927. // to the raw bytes of the input stream.
  1928. // FieldStruct Pointer to space for parsed
  1929. // information.
  1930. //------------------------------------------------------------------------------
  1931. static HRESULT
  1932. ParseCallingPartySubaddress(
  1933. PBUFFERDESCR BufferDescriptor,
  1934. PCALLINGSUBADDRIE FieldStruct)
  1935. {
  1936. BYTE Ident;
  1937. memset(FieldStruct, 0, sizeof(CALLINGSUBADDRIE));
  1938. FieldStruct->Present = FALSE;
  1939. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CALLINGSUBADDR)
  1940. {
  1941. HRESULT ParseResult;
  1942. ParseResult = ParseVariableOctet(BufferDescriptor,
  1943. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  1944. if (ParseResult != CS_OK)
  1945. {
  1946. return ParseResult;
  1947. }
  1948. if (FieldStruct->Length > 0)
  1949. {
  1950. FieldStruct->Present = TRUE;
  1951. }
  1952. }
  1953. return CS_OK;
  1954. }
  1955. //------------------------------------------------------------------------------
  1956. // Parse an optional called party number field
  1957. //
  1958. // Parameters:
  1959. // BufferPtr Pointer to a descriptor of the buffer
  1960. // containing the length and a pointer
  1961. // to the raw bytes of the input stream.
  1962. // FieldStruct Pointer to space for parsed
  1963. // information.
  1964. //------------------------------------------------------------------------------
  1965. static HRESULT
  1966. ParseCalledPartyNumber(
  1967. PBUFFERDESCR BufferDescriptor,
  1968. PCALLEDNUMBERIE FieldStruct)
  1969. {
  1970. memset(FieldStruct, 0, sizeof(PCALLEDNUMBERIE));
  1971. FieldStruct->Present = FALSE;
  1972. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CALLEDNUMBER)
  1973. {
  1974. register int i;
  1975. BYTE RemainingLength = 0;
  1976. BYTE *Tempptr;
  1977. // Need 3 bytes for the ident (1), length (1),
  1978. // and type + plan (1) fields.
  1979. if (BufferDescriptor->Length < 3)
  1980. {
  1981. return CS_ENDOFINPUT;
  1982. }
  1983. // skip the ie identifier...
  1984. BufferDescriptor->BufferPtr++;
  1985. BufferDescriptor->Length--;
  1986. // Get the length of the contents following the length field.
  1987. RemainingLength = *BufferDescriptor->BufferPtr;
  1988. BufferDescriptor->BufferPtr++;
  1989. BufferDescriptor->Length--;
  1990. // make sure we have at least that much length left...
  1991. if (BufferDescriptor->Length < RemainingLength)
  1992. {
  1993. return CS_ENDOFINPUT;
  1994. }
  1995. // Get the type + plan fields.
  1996. if (*(BufferDescriptor->BufferPtr) & 0x80)
  1997. {
  1998. FieldStruct->NumberType =
  1999. (BYTE)(*BufferDescriptor->BufferPtr & 0xf0);
  2000. FieldStruct->NumberingPlan =
  2001. (BYTE)(*BufferDescriptor->BufferPtr & 0x0f);
  2002. BufferDescriptor->BufferPtr++;
  2003. BufferDescriptor->Length--;
  2004. RemainingLength--;
  2005. }
  2006. FieldStruct->PartyNumberLength = RemainingLength;
  2007. FieldStruct->Present = TRUE;
  2008. Tempptr = FieldStruct->PartyNumbers;
  2009. for (i = 0; i < RemainingLength; i++)
  2010. {
  2011. // Copy the bytes out of the rest of the buffer
  2012. *Tempptr = *(BufferDescriptor->BufferPtr);
  2013. BufferDescriptor->BufferPtr++;
  2014. BufferDescriptor->Length--;
  2015. Tempptr++;
  2016. }
  2017. *Tempptr = (BYTE)0;
  2018. }
  2019. return CS_OK;
  2020. }
  2021. //------------------------------------------------------------------------------
  2022. // Parse an optional called party subaddress field
  2023. //
  2024. // Parameters:
  2025. // BufferPtr Pointer to a descriptor of the buffer
  2026. // containing the length and a pointer
  2027. // to the raw bytes of the input stream.
  2028. // FieldStruct Pointer to space for parsed
  2029. // information.
  2030. //------------------------------------------------------------------------------
  2031. static HRESULT
  2032. ParseCalledPartySubaddress(
  2033. PBUFFERDESCR BufferDescriptor,
  2034. PCALLEDSUBADDRIE FieldStruct)
  2035. {
  2036. BYTE Ident;
  2037. memset(FieldStruct, 0, sizeof(CALLEDSUBADDRIE));
  2038. FieldStruct->Present = FALSE;
  2039. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_CALLEDSUBADDR)
  2040. {
  2041. HRESULT ParseResult;
  2042. ParseResult = ParseVariableOctet(BufferDescriptor,
  2043. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  2044. if (ParseResult != CS_OK)
  2045. {
  2046. return ParseResult;
  2047. }
  2048. if (FieldStruct->Length > 0)
  2049. {
  2050. FieldStruct->Present = TRUE;
  2051. }
  2052. }
  2053. return CS_OK;
  2054. }
  2055. //------------------------------------------------------------------------------
  2056. // Parse an optional redirecting number field
  2057. //
  2058. // Parameters:
  2059. // BufferPtr Pointer to a descriptor of the buffer
  2060. // containing the length and a pointer
  2061. // to the raw bytes of the input stream.
  2062. // FieldStruct Pointer to space for parsed
  2063. // information.
  2064. //------------------------------------------------------------------------------
  2065. static HRESULT
  2066. ParseRedirectingNumber(
  2067. PBUFFERDESCR BufferDescriptor,
  2068. PREDIRECTINGIE FieldStruct)
  2069. {
  2070. BYTE Ident;
  2071. memset(FieldStruct, 0, sizeof(REDIRECTINGIE));
  2072. FieldStruct->Present = FALSE;
  2073. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_REDIRECTING)
  2074. {
  2075. HRESULT ParseResult;
  2076. ParseResult = ParseVariableOctet(BufferDescriptor,
  2077. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  2078. if (ParseResult != CS_OK)
  2079. {
  2080. return ParseResult;
  2081. }
  2082. if (FieldStruct->Length > 0)
  2083. {
  2084. FieldStruct->Present = TRUE;
  2085. }
  2086. }
  2087. return CS_OK;
  2088. }
  2089. //------------------------------------------------------------------------------
  2090. // Parse an optional transit network selection field
  2091. //
  2092. // Parameters:
  2093. // BufferPtr Pointer to a descriptor of the buffer
  2094. // containing the length and a pointer
  2095. // to the raw bytes of the input stream.
  2096. // FieldStruct Pointer to space for parsed
  2097. // information.
  2098. //------------------------------------------------------------------------------
  2099. static HRESULT
  2100. ParseTransitNetwork(
  2101. PBUFFERDESCR BufferDescriptor,
  2102. PTRANSITNETIE FieldStruct)
  2103. {
  2104. BYTE Ident;
  2105. memset(FieldStruct, 0, sizeof(TRANSITNETIE));
  2106. FieldStruct->Present = FALSE;
  2107. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_TRANSITNET)
  2108. {
  2109. HRESULT ParseResult;
  2110. ParseResult = ParseVariableOctet(BufferDescriptor,
  2111. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  2112. if (ParseResult != CS_OK)
  2113. {
  2114. return ParseResult;
  2115. }
  2116. if (FieldStruct->Length > 0)
  2117. {
  2118. FieldStruct->Present = TRUE;
  2119. }
  2120. }
  2121. return CS_OK;
  2122. }
  2123. //------------------------------------------------------------------------------
  2124. // Parse an optional restart indicator field
  2125. //
  2126. // Parameters:
  2127. // BufferPtr Pointer to a descriptor of the buffer
  2128. // containing the length and a pointer
  2129. // to the raw bytes of the input stream.
  2130. // FieldStruct Pointer to space for parsed
  2131. // information.
  2132. //------------------------------------------------------------------------------
  2133. static HRESULT
  2134. ParseRestart(
  2135. PBUFFERDESCR BufferDescriptor,
  2136. PRESTARTIE FieldStruct)
  2137. {
  2138. BYTE Ident;
  2139. memset(FieldStruct, 0, sizeof(PRESTARTIE));
  2140. FieldStruct->Present = FALSE;
  2141. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_RESTART)
  2142. {
  2143. HRESULT ParseResult;
  2144. ParseResult = ParseVariableOctet(BufferDescriptor,
  2145. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  2146. if (ParseResult != CS_OK)
  2147. {
  2148. return ParseResult;
  2149. }
  2150. if (FieldStruct->Length > 0)
  2151. {
  2152. FieldStruct->Present = TRUE;
  2153. }
  2154. }
  2155. return CS_OK;
  2156. }
  2157. //------------------------------------------------------------------------------
  2158. // Parse an optional lower layer compatibility field
  2159. //
  2160. // Parameters:
  2161. // BufferPtr Pointer to a descriptor of the buffer
  2162. // containing the length and a pointer
  2163. // to the raw bytes of the input stream.
  2164. // FieldStruct Pointer to space for parsed
  2165. // information.
  2166. //------------------------------------------------------------------------------
  2167. static HRESULT
  2168. ParseLowLayerCompatibility(
  2169. PBUFFERDESCR BufferDescriptor,
  2170. PLLCOMPATIBILITYIE FieldStruct)
  2171. {
  2172. BYTE Ident;
  2173. memset(FieldStruct, 0, sizeof(LLCOMPATIBILITYIE));
  2174. FieldStruct->Present = FALSE;
  2175. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_LLCOMPATIBILITY)
  2176. {
  2177. HRESULT ParseResult;
  2178. ParseResult = ParseVariableOctet(BufferDescriptor,
  2179. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  2180. if (ParseResult != CS_OK)
  2181. {
  2182. return ParseResult;
  2183. }
  2184. if (FieldStruct->Length > 0)
  2185. {
  2186. FieldStruct->Present = TRUE;
  2187. }
  2188. }
  2189. return CS_OK;
  2190. }
  2191. //------------------------------------------------------------------------------
  2192. // Parse an optional higher layer compatibility field
  2193. //
  2194. // Parameters:
  2195. // BufferPtr Pointer to a descriptor of the buffer
  2196. // containing the length and a pointer
  2197. // to the raw bytes of the input stream.
  2198. // FieldStruct Pointer to space for parsed
  2199. // information.
  2200. //------------------------------------------------------------------------------
  2201. static HRESULT
  2202. ParseHighLayerCompatibility(
  2203. PBUFFERDESCR BufferDescriptor,
  2204. PHLCOMPATIBILITYIE FieldStruct)
  2205. {
  2206. BYTE Ident;
  2207. memset(FieldStruct, 0, sizeof(HLCOMPATIBILITYIE));
  2208. FieldStruct->Present = FALSE;
  2209. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_HLCOMPATIBILITY)
  2210. {
  2211. HRESULT ParseResult;
  2212. ParseResult = ParseVariableOctet(BufferDescriptor,
  2213. &Ident, &FieldStruct->Length, &FieldStruct->Contents[0]);
  2214. if (ParseResult != CS_OK)
  2215. {
  2216. return ParseResult;
  2217. }
  2218. if (FieldStruct->Length > 0)
  2219. {
  2220. FieldStruct->Present = TRUE;
  2221. }
  2222. }
  2223. return CS_OK;
  2224. }
  2225. //------------------------------------------------------------------------------
  2226. // Parse an optional user to user field
  2227. //
  2228. // Parameters:
  2229. // BufferPtr Pointer to a descriptor of the buffer
  2230. // containing the length and a pointer
  2231. // to the raw bytes of the input stream.
  2232. // FieldStruct Pointer to space for parsed
  2233. // information.
  2234. //------------------------------------------------------------------------------
  2235. static HRESULT
  2236. ParseUserToUser(
  2237. PBUFFERDESCR BufferDescriptor,
  2238. PUSERUSERIE FieldStruct)
  2239. {
  2240. BYTE Ident;
  2241. memset(FieldStruct, 0, sizeof(USERUSERIE));
  2242. FieldStruct->Present = FALSE;
  2243. if (GetNextIdent(BufferDescriptor->BufferPtr) == IDENT_USERUSER)
  2244. {
  2245. HRESULT ParseResult;
  2246. ParseResult = ParseVariableASN(BufferDescriptor,
  2247. &Ident, &(FieldStruct->ProtocolDiscriminator),
  2248. &(FieldStruct->UserInformationLength),
  2249. &(FieldStruct->UserInformation[0]));
  2250. if (ParseResult != CS_OK)
  2251. {
  2252. return ParseResult;
  2253. }
  2254. if (FieldStruct->UserInformationLength > 0)
  2255. {
  2256. FieldStruct->Present = TRUE;
  2257. }
  2258. }
  2259. return CS_OK;
  2260. }
  2261. //------------------------------------------------------------------------------
  2262. // Parse the next Q931 field in the given message
  2263. //
  2264. // Parameters:
  2265. // BufferDescriptor Pointer to buffer descriptor of a
  2266. // the network packet of the 931 message
  2267. // Message Pointer to space for parsed information.
  2268. //------------------------------------------------------------------------------
  2269. static HRESULT
  2270. ParseQ931Field(
  2271. PBUFFERDESCR BufferDescriptor,
  2272. PQ931MESSAGE Message)
  2273. {
  2274. FIELDIDENTTYPE Ident;
  2275. Ident = GetNextIdent(BufferDescriptor->BufferPtr);
  2276. switch (Ident)
  2277. {
  2278. case IDENT_SHIFT:
  2279. return ParseShift(BufferDescriptor,
  2280. &Message->Shift);
  2281. case IDENT_FACILITY:
  2282. return ParseFacility(BufferDescriptor,
  2283. &Message->Facility);
  2284. case IDENT_MORE:
  2285. return ParseMoreData(BufferDescriptor,
  2286. &Message->MoreData);
  2287. case IDENT_SENDINGCOMPLETE:
  2288. return ParseSendingComplete(BufferDescriptor,
  2289. &Message->SendingComplete);
  2290. case IDENT_CONGESTION:
  2291. return ParseCongestionLevel(BufferDescriptor,
  2292. &Message->CongestionLevel);
  2293. case IDENT_REPEAT:
  2294. return ParseRepeatIndicator(BufferDescriptor,
  2295. &Message->RepeatIndicator);
  2296. case IDENT_SEGMENTED:
  2297. return ParseSegmented(BufferDescriptor,
  2298. &Message->SegmentedMessage);
  2299. case IDENT_BEARERCAP:
  2300. return ParseBearerCapability(BufferDescriptor,
  2301. &Message->BearerCapability);
  2302. case IDENT_CAUSE:
  2303. return ParseCause(BufferDescriptor,
  2304. &Message->Cause);
  2305. case IDENT_CALLIDENT:
  2306. return ParseCallIdentity(BufferDescriptor,
  2307. &Message->CallIdentity);
  2308. case IDENT_CALLSTATE:
  2309. return ParseCallState(BufferDescriptor,
  2310. &Message->CallState);
  2311. case IDENT_CHANNELIDENT:
  2312. return ParseChannelIdentification(BufferDescriptor,
  2313. &Message->ChannelIdentification);
  2314. case IDENT_PROGRESS:
  2315. return ParseProgress(BufferDescriptor,
  2316. &Message->ProgressIndicator);
  2317. case IDENT_NETWORKSPEC:
  2318. return ParseNetworkSpec(BufferDescriptor,
  2319. &Message->NetworkFacilities);
  2320. case IDENT_NOTIFICATION:
  2321. return ParseNotificationIndicator(BufferDescriptor,
  2322. &Message->NotificationIndicator);
  2323. case IDENT_DISPLAY:
  2324. return ParseDisplay(BufferDescriptor,
  2325. &Message->Display);
  2326. case IDENT_DATE:
  2327. return ParseDate(BufferDescriptor,
  2328. &Message->Date);
  2329. case IDENT_KEYPAD:
  2330. return ParseKeypad(BufferDescriptor,
  2331. &Message->Keypad);
  2332. case IDENT_SIGNAL:
  2333. return ParseSignal(BufferDescriptor,
  2334. &Message->Signal);
  2335. case IDENT_INFORMATIONRATE:
  2336. return ParseInformationRate(BufferDescriptor,
  2337. &Message->InformationRate);
  2338. case IDENT_ENDTOENDDELAY:
  2339. return ParseEndToEndDelay(BufferDescriptor,
  2340. &Message->EndToEndTransitDelay);
  2341. case IDENT_TRANSITDELAY:
  2342. return ParseTransitDelay(BufferDescriptor,
  2343. &Message->TransitDelay);
  2344. case IDENT_PLBINARYPARAMS:
  2345. return ParsePacketLayerParams(BufferDescriptor,
  2346. &Message->PacketLayerBinaryParams);
  2347. case IDENT_PLWINDOWSIZE:
  2348. return ParsePacketLayerWindowSize(BufferDescriptor,
  2349. &Message->PacketLayerWindowSize);
  2350. case IDENT_PACKETSIZE:
  2351. return ParsePacketSize(BufferDescriptor,
  2352. &Message->PacketSize);
  2353. case IDENT_CLOSEDUG:
  2354. return ParseClosedUserGroup(BufferDescriptor,
  2355. &Message->ClosedUserGroup);
  2356. case IDENT_REVCHARGE:
  2357. return ParseReverseCharge(BufferDescriptor,
  2358. &Message->ReverseChargeIndication);
  2359. case IDENT_CALLINGNUMBER:
  2360. return ParseCallingPartyNumber(BufferDescriptor,
  2361. &Message->CallingPartyNumber);
  2362. case IDENT_CALLINGSUBADDR:
  2363. return ParseCallingPartySubaddress(BufferDescriptor,
  2364. &Message->CallingPartySubaddress);
  2365. case IDENT_CALLEDNUMBER:
  2366. return ParseCalledPartyNumber(BufferDescriptor,
  2367. &Message->CalledPartyNumber);
  2368. case IDENT_CALLEDSUBADDR:
  2369. return ParseCalledPartySubaddress(BufferDescriptor,
  2370. &Message->CalledPartySubaddress);
  2371. case IDENT_REDIRECTING:
  2372. return ParseRedirectingNumber(BufferDescriptor,
  2373. &Message->RedirectingNumber);
  2374. case IDENT_TRANSITNET:
  2375. return ParseTransitNetwork(BufferDescriptor,
  2376. &Message->TransitNetworkSelection);
  2377. case IDENT_RESTART:
  2378. return ParseRestart(BufferDescriptor,
  2379. &Message->RestartIndicator);
  2380. case IDENT_LLCOMPATIBILITY:
  2381. return ParseLowLayerCompatibility(BufferDescriptor,
  2382. &Message->LowLayerCompatibility);
  2383. case IDENT_HLCOMPATIBILITY:
  2384. return ParseHighLayerCompatibility(BufferDescriptor,
  2385. &Message->HighLayerCompatibility);
  2386. case IDENT_USERUSER:
  2387. return ParseUserToUser(BufferDescriptor,
  2388. &Message->UserToUser);
  2389. default:
  2390. return CS_INVALID_FIELD;
  2391. }
  2392. }
  2393. //------------------------------------------------------------------------------
  2394. // Parse a generic Q931 message and place the fields of the buffer
  2395. // into the appropriate structure fields.
  2396. //
  2397. // Parameters:
  2398. // BufferDescriptor Pointer to buffer descriptor of an
  2399. // input packet containing the 931 message.
  2400. // Message Pointer to space for parsed output information.
  2401. //------------------------------------------------------------------------------
  2402. HRESULT
  2403. Q931ParseMessage(
  2404. BYTE *CodedBufferPtr,
  2405. DWORD CodedBufferLength,
  2406. PQ931MESSAGE Message)
  2407. {
  2408. HRESULT Result;
  2409. BUFFERDESCR BufferDescriptor;
  2410. BufferDescriptor.Length = CodedBufferLength;
  2411. BufferDescriptor.BufferPtr = CodedBufferPtr;
  2412. memset(Message, 0, sizeof(Q931MESSAGE));
  2413. if ((Result = ParseProtocolDiscriminator(&BufferDescriptor,
  2414. &Message->ProtocolDiscriminator)) != CS_OK)
  2415. {
  2416. return Result;
  2417. }
  2418. if ((Result = ParseCallReference(&BufferDescriptor,
  2419. &Message->CallReference)) != CS_OK)
  2420. {
  2421. return Result;
  2422. }
  2423. if ((Result = ParseMessageType(&BufferDescriptor,
  2424. &Message->MessageType)) != CS_OK)
  2425. {
  2426. return Result;
  2427. }
  2428. while (BufferDescriptor.Length)
  2429. {
  2430. Result = ParseQ931Field(&BufferDescriptor, Message);
  2431. if (Result != CS_OK)
  2432. {
  2433. return Result;
  2434. }
  2435. }
  2436. return CS_OK;
  2437. }
  2438. //==============================================================================
  2439. //==============================================================================
  2440. //==============================================================================
  2441. // BELOW HERE ARE THE OUTPUT ROUTINES...
  2442. //==============================================================================
  2443. //==============================================================================
  2444. //==============================================================================
  2445. //------------------------------------------------------------------------------
  2446. // Write the protocol discriminator. See Q931 section 4.2.
  2447. //------------------------------------------------------------------------------
  2448. static HRESULT
  2449. WriteProtocolDiscriminator(
  2450. PBUFFERDESCR BufferDescriptor)
  2451. {
  2452. BufferDescriptor->Length += sizeof(PDTYPE);
  2453. if (BufferDescriptor->BufferPtr)
  2454. {
  2455. *(PDTYPE *)BufferDescriptor->BufferPtr = Q931PDVALUE;
  2456. BufferDescriptor->BufferPtr += sizeof(PDTYPE);
  2457. }
  2458. return CS_OK;
  2459. }
  2460. //------------------------------------------------------------------------------
  2461. // Write a variable length Q931 call reference. See Q931 section 4.3.
  2462. //------------------------------------------------------------------------------
  2463. static HRESULT
  2464. WriteCallReference(
  2465. PBUFFERDESCR BufferDescriptor,
  2466. CRTYPE *CallReference)
  2467. {
  2468. register int i;
  2469. // space for the length byte
  2470. BufferDescriptor->Length++;
  2471. // the length byte
  2472. if (BufferDescriptor->BufferPtr != NULL)
  2473. {
  2474. *BufferDescriptor->BufferPtr = (BYTE)sizeof(CRTYPE);
  2475. BufferDescriptor->BufferPtr++;
  2476. }
  2477. for (i = 0; i < sizeof(CRTYPE); i++)
  2478. {
  2479. // Copy the value bytes to the buffer
  2480. BufferDescriptor->Length++;
  2481. if (BufferDescriptor->BufferPtr != NULL)
  2482. {
  2483. *BufferDescriptor->BufferPtr =
  2484. (BYTE)(((*CallReference) >> ((sizeof(CRTYPE) - 1 -i) * 8)) & 0xff);
  2485. BufferDescriptor->BufferPtr++;
  2486. }
  2487. }
  2488. return CS_OK;
  2489. }
  2490. //------------------------------------------------------------------------------
  2491. // Write a Q931 message type. See Q931 section 4.4.
  2492. //------------------------------------------------------------------------------
  2493. static HRESULT
  2494. WriteMessageType(
  2495. PBUFFERDESCR BufferDescriptor,
  2496. MESSAGEIDTYPE *MessageType)
  2497. {
  2498. register int i;
  2499. for (i = 0; i < sizeof(MessageSet) / sizeof(MESSAGEIDTYPE); i++)
  2500. {
  2501. if (MessageSet[i] == *MessageType)
  2502. {
  2503. break;
  2504. }
  2505. }
  2506. if (i >= sizeof(MessageSet) / sizeof(MESSAGEIDTYPE))
  2507. {
  2508. return CS_INVALID_MESSAGE_TYPE;
  2509. }
  2510. BufferDescriptor->Length += sizeof(MESSAGEIDTYPE);
  2511. if (BufferDescriptor->BufferPtr != NULL)
  2512. {
  2513. *(MESSAGEIDTYPE *)(BufferDescriptor->BufferPtr) =
  2514. (BYTE)(*MessageType & MESSAGETYPEMASK);
  2515. BufferDescriptor->BufferPtr += sizeof(MESSAGEIDTYPE);
  2516. }
  2517. return CS_OK;
  2518. }
  2519. //------------------------------------------------------------------------------
  2520. // Write a single octet encoded value, See Q931 section 4.5.1.
  2521. //------------------------------------------------------------------------------
  2522. static HRESULT
  2523. WriteSingleOctetType1(
  2524. PBUFFERDESCR BufferDescriptor,
  2525. BYTE Ident,
  2526. BYTE Value)
  2527. {
  2528. BufferDescriptor->Length++;
  2529. if (BufferDescriptor->BufferPtr)
  2530. {
  2531. *BufferDescriptor->BufferPtr =
  2532. (BYTE)(0x80 | Ident | (Value & TYPE1VALUEMASK));
  2533. BufferDescriptor->BufferPtr++;
  2534. }
  2535. return CS_OK;
  2536. }
  2537. //------------------------------------------------------------------------------
  2538. // Write a single octet encoded value, See Q931 section 4.5.1.
  2539. //------------------------------------------------------------------------------
  2540. static HRESULT
  2541. WriteSingleOctetType2(
  2542. PBUFFERDESCR BufferDescriptor,
  2543. BYTE Ident)
  2544. {
  2545. BufferDescriptor->Length++;
  2546. if (BufferDescriptor->BufferPtr)
  2547. {
  2548. *BufferDescriptor->BufferPtr = (BYTE)(0x80 | Ident);
  2549. BufferDescriptor->BufferPtr++;
  2550. }
  2551. return CS_OK;
  2552. }
  2553. //------------------------------------------------------------------------------
  2554. // Parse and return a variable length Q931 field see Q931 section 4.5.1.
  2555. //------------------------------------------------------------------------------
  2556. static HRESULT
  2557. WriteVariableOctet(
  2558. PBUFFERDESCR BufferDescriptor,
  2559. BYTE Ident,
  2560. BYTE Length,
  2561. BYTE *Contents)
  2562. {
  2563. register int i;
  2564. BYTE *Tempptr;
  2565. if (Contents == NULL)
  2566. {
  2567. Length = 0;
  2568. }
  2569. // space for the length and the identifier bytes
  2570. BufferDescriptor->Length += 2;
  2571. // the id byte, then the length byte
  2572. if (BufferDescriptor->BufferPtr != NULL)
  2573. {
  2574. // low 7 bits of the first byte are the identifier
  2575. *BufferDescriptor->BufferPtr = (BYTE)(Ident & 0x7f);
  2576. BufferDescriptor->BufferPtr++;
  2577. *BufferDescriptor->BufferPtr = Length;
  2578. BufferDescriptor->BufferPtr++;
  2579. }
  2580. Tempptr = Contents;
  2581. for (i = 0; i < Length; i++)
  2582. {
  2583. // Copy the value bytes to the buffer
  2584. BufferDescriptor->Length++;
  2585. if (BufferDescriptor->BufferPtr != NULL)
  2586. {
  2587. *BufferDescriptor->BufferPtr = *Tempptr;
  2588. BufferDescriptor->BufferPtr++;
  2589. Tempptr++;
  2590. }
  2591. }
  2592. return CS_OK;
  2593. }
  2594. //------------------------------------------------------------------------------
  2595. //Write out the Party number.
  2596. //------------------------------------------------------------------------------
  2597. static HRESULT
  2598. WritePartyNumber(
  2599. PBUFFERDESCR BufferDescriptor,
  2600. BYTE Ident,
  2601. BYTE NumberType,
  2602. BYTE NumberingPlan,
  2603. BYTE PartyNumberLength,
  2604. BYTE *PartyNumbers)
  2605. {
  2606. register int i;
  2607. BYTE *Tempptr;
  2608. if (PartyNumbers == NULL)
  2609. {
  2610. PartyNumberLength = 0;
  2611. }
  2612. // space for the ident (1), length (1), and type + plan (1) fields.
  2613. BufferDescriptor->Length += 3;
  2614. // write the fields out.
  2615. if (BufferDescriptor->BufferPtr != NULL)
  2616. {
  2617. // low 7 bits of byte 1 are the ie identifier
  2618. *BufferDescriptor->BufferPtr = (BYTE)(Ident & 0x7f);
  2619. BufferDescriptor->BufferPtr++;
  2620. // byte 2 is the ie contents length following the length field.
  2621. *BufferDescriptor->BufferPtr = (BYTE)(PartyNumberLength + 1);
  2622. BufferDescriptor->BufferPtr++;
  2623. // byte 3 is the type and plan field.
  2624. *BufferDescriptor->BufferPtr = (BYTE)(NumberType | NumberingPlan);
  2625. BufferDescriptor->BufferPtr++;
  2626. }
  2627. Tempptr = PartyNumbers;
  2628. for (i = 0; i < PartyNumberLength; i++)
  2629. {
  2630. // Copy the value bytes to the buffer
  2631. BufferDescriptor->Length++;
  2632. if (BufferDescriptor->BufferPtr != NULL)
  2633. {
  2634. *BufferDescriptor->BufferPtr = *Tempptr;
  2635. BufferDescriptor->BufferPtr++;
  2636. Tempptr++;
  2637. }
  2638. }
  2639. return CS_OK;
  2640. }
  2641. //------------------------------------------------------------------------------
  2642. // Parse and return a variable length Q931 field see Q931 section 4.5.1.
  2643. //------------------------------------------------------------------------------
  2644. static HRESULT
  2645. WriteVariableASN(
  2646. PBUFFERDESCR BufferDescriptor,
  2647. BYTE Ident,
  2648. WORD UserInformationLength,
  2649. BYTE *UserInformation)
  2650. {
  2651. register int i;
  2652. BYTE *Tempptr;
  2653. WORD ContentsLength = (WORD)(UserInformationLength + 1);
  2654. // There has to be at least 4 bytes for the IE identifier,
  2655. // the contents length, and the protocol discriminator (1 + 2 + 1).
  2656. BufferDescriptor->Length += 4;
  2657. if (BufferDescriptor->BufferPtr != NULL)
  2658. {
  2659. // low 7 bits of the first byte are the identifier
  2660. *BufferDescriptor->BufferPtr = (BYTE)(Ident & 0x7f);
  2661. BufferDescriptor->BufferPtr++;
  2662. // write the contents length bytes.
  2663. *BufferDescriptor->BufferPtr = (BYTE)(ContentsLength >> 8);
  2664. BufferDescriptor->BufferPtr++;
  2665. *BufferDescriptor->BufferPtr = (BYTE)ContentsLength;
  2666. BufferDescriptor->BufferPtr++;
  2667. // write the protocol discriminator byte.
  2668. *(BufferDescriptor->BufferPtr) = Q931_PROTOCOL_X209;
  2669. BufferDescriptor->BufferPtr++;
  2670. }
  2671. Tempptr = UserInformation;
  2672. for (i = 0; i < UserInformationLength; i++)
  2673. {
  2674. // Copy the value bytes to the buffer
  2675. BufferDescriptor->Length++;
  2676. if (BufferDescriptor->BufferPtr != NULL)
  2677. {
  2678. *BufferDescriptor->BufferPtr = *Tempptr;
  2679. BufferDescriptor->BufferPtr++;
  2680. Tempptr++;
  2681. }
  2682. }
  2683. return CS_OK;
  2684. }
  2685. //------------------------------------------------------------------------------
  2686. // Write the Q931 fields to the encoding buffer.
  2687. //
  2688. // Parameters:
  2689. // BufferDescriptor Pointer to buffer descriptor for
  2690. // the encoded output buffer.
  2691. // Message Pointer to space for parsed input information.
  2692. //------------------------------------------------------------------------------
  2693. static HRESULT
  2694. WriteQ931Fields(
  2695. PBUFFERDESCR BufferDescriptor,
  2696. PQ931MESSAGE Message)
  2697. {
  2698. // write the required information elements...
  2699. WriteProtocolDiscriminator(BufferDescriptor);
  2700. WriteCallReference(BufferDescriptor,
  2701. &Message->CallReference);
  2702. WriteMessageType(BufferDescriptor,
  2703. &Message->MessageType);
  2704. // try to write all other information elements...
  2705. // don't write this message.
  2706. #if 0
  2707. if (Message->Shift.Present)
  2708. {
  2709. WriteSingleOctetType1(BufferDescriptor, IDENT_SHIFT,
  2710. Message->Shift.Value);
  2711. }
  2712. #endif
  2713. if (Message->Facility.Present)
  2714. {
  2715. WriteVariableOctet(BufferDescriptor, IDENT_FACILITY,
  2716. Message->Facility.Length,
  2717. Message->Facility.Contents);
  2718. }
  2719. if (Message->MoreData.Present)
  2720. {
  2721. WriteSingleOctetType2(BufferDescriptor, IDENT_MORE);
  2722. }
  2723. if (Message->SendingComplete.Present)
  2724. {
  2725. WriteSingleOctetType2(BufferDescriptor, IDENT_SENDINGCOMPLETE);
  2726. }
  2727. if (Message->CongestionLevel.Present)
  2728. {
  2729. WriteSingleOctetType1(BufferDescriptor, IDENT_CONGESTION,
  2730. Message->CongestionLevel.Value);
  2731. }
  2732. if (Message->RepeatIndicator.Present)
  2733. {
  2734. WriteSingleOctetType1(BufferDescriptor, IDENT_REPEAT,
  2735. Message->RepeatIndicator.Value);
  2736. }
  2737. if (Message->SegmentedMessage.Present &&
  2738. Message->SegmentedMessage.Length)
  2739. {
  2740. WriteVariableOctet(BufferDescriptor, IDENT_SEGMENTED,
  2741. Message->SegmentedMessage.Length,
  2742. Message->SegmentedMessage.Contents);
  2743. }
  2744. if (Message->BearerCapability.Present &&
  2745. Message->BearerCapability.Length)
  2746. {
  2747. WriteVariableOctet(BufferDescriptor, IDENT_BEARERCAP,
  2748. Message->BearerCapability.Length,
  2749. Message->BearerCapability.Contents);
  2750. }
  2751. if (Message->Cause.Present &&
  2752. Message->Cause.Length)
  2753. {
  2754. WriteVariableOctet(BufferDescriptor, IDENT_CAUSE,
  2755. Message->Cause.Length,
  2756. Message->Cause.Contents);
  2757. }
  2758. if (Message->CallIdentity.Present &&
  2759. Message->CallIdentity.Length)
  2760. {
  2761. WriteVariableOctet(BufferDescriptor, IDENT_CALLIDENT,
  2762. Message->CallIdentity.Length,
  2763. Message->CallIdentity.Contents);
  2764. }
  2765. if (Message->CallState.Present &&
  2766. Message->CallState.Length)
  2767. {
  2768. WriteVariableOctet(BufferDescriptor, IDENT_CALLSTATE,
  2769. Message->CallState.Length,
  2770. Message->CallState.Contents);
  2771. }
  2772. if (Message->ChannelIdentification.Present &&
  2773. Message->ChannelIdentification.Length)
  2774. {
  2775. WriteVariableOctet(BufferDescriptor, IDENT_CHANNELIDENT,
  2776. Message->ChannelIdentification.Length,
  2777. Message->ChannelIdentification.Contents);
  2778. }
  2779. if (Message->ProgressIndicator.Present &&
  2780. Message->ProgressIndicator.Length)
  2781. {
  2782. WriteVariableOctet(BufferDescriptor, IDENT_PROGRESS,
  2783. Message->ProgressIndicator.Length,
  2784. Message->ProgressIndicator.Contents);
  2785. }
  2786. if (Message->NetworkFacilities.Present &&
  2787. Message->NetworkFacilities.Length)
  2788. {
  2789. WriteVariableOctet(BufferDescriptor, IDENT_NETWORKSPEC,
  2790. Message->NetworkFacilities.Length,
  2791. Message->NetworkFacilities.Contents);
  2792. }
  2793. if (Message->NotificationIndicator.Present &&
  2794. Message->NotificationIndicator.Length)
  2795. {
  2796. WriteVariableOctet(BufferDescriptor, IDENT_NOTIFICATION,
  2797. Message->NotificationIndicator.Length,
  2798. Message->NotificationIndicator.Contents);
  2799. }
  2800. if (Message->Display.Present &&
  2801. Message->Display.Length)
  2802. {
  2803. WriteVariableOctet(BufferDescriptor, IDENT_DISPLAY,
  2804. Message->Display.Length,
  2805. Message->Display.Contents);
  2806. }
  2807. if (Message->Date.Present &&
  2808. Message->Date.Length)
  2809. {
  2810. WriteVariableOctet(BufferDescriptor, IDENT_DATE,
  2811. Message->Date.Length,
  2812. Message->Date.Contents);
  2813. }
  2814. if (Message->Keypad.Present &&
  2815. Message->Keypad.Length)
  2816. {
  2817. WriteVariableOctet(BufferDescriptor, IDENT_KEYPAD,
  2818. Message->Keypad.Length,
  2819. Message->Keypad.Contents);
  2820. }
  2821. if (Message->Signal.Present &&
  2822. Message->Signal.Length)
  2823. {
  2824. WriteVariableOctet(BufferDescriptor, IDENT_SIGNAL,
  2825. Message->Signal.Length,
  2826. Message->Signal.Contents);
  2827. }
  2828. if (Message->InformationRate.Present &&
  2829. Message->InformationRate.Length)
  2830. {
  2831. WriteVariableOctet(BufferDescriptor, IDENT_INFORMATIONRATE,
  2832. Message->InformationRate.Length,
  2833. Message->InformationRate.Contents);
  2834. }
  2835. if (Message->EndToEndTransitDelay.Present &&
  2836. Message->EndToEndTransitDelay.Length)
  2837. {
  2838. WriteVariableOctet(BufferDescriptor, IDENT_ENDTOENDDELAY,
  2839. Message->EndToEndTransitDelay.Length,
  2840. Message->EndToEndTransitDelay.Contents);
  2841. }
  2842. if (Message->TransitDelay.Present &&
  2843. Message->TransitDelay.Length)
  2844. {
  2845. WriteVariableOctet(BufferDescriptor, IDENT_TRANSITDELAY,
  2846. Message->TransitDelay.Length,
  2847. Message->TransitDelay.Contents);
  2848. }
  2849. if (Message->PacketLayerBinaryParams.Present &&
  2850. Message->PacketLayerBinaryParams.Length)
  2851. {
  2852. WriteVariableOctet(BufferDescriptor, IDENT_PLBINARYPARAMS,
  2853. Message->PacketLayerBinaryParams.Length,
  2854. Message->PacketLayerBinaryParams.Contents);
  2855. }
  2856. if (Message->PacketLayerWindowSize.Present &&
  2857. Message->PacketLayerWindowSize.Length)
  2858. {
  2859. WriteVariableOctet(BufferDescriptor, IDENT_PLWINDOWSIZE,
  2860. Message->PacketLayerWindowSize.Length,
  2861. Message->PacketLayerWindowSize.Contents);
  2862. }
  2863. if (Message->PacketSize.Present &&
  2864. Message->PacketSize.Length)
  2865. {
  2866. WriteVariableOctet(BufferDescriptor, IDENT_PACKETSIZE,
  2867. Message->PacketSize.Length,
  2868. Message->PacketSize.Contents);
  2869. }
  2870. if (Message->ClosedUserGroup.Present &&
  2871. Message->ClosedUserGroup.Length)
  2872. {
  2873. WriteVariableOctet(BufferDescriptor, IDENT_CLOSEDUG,
  2874. Message->ClosedUserGroup.Length,
  2875. Message->ClosedUserGroup.Contents);
  2876. }
  2877. if (Message->ReverseChargeIndication.Present &&
  2878. Message->ReverseChargeIndication.Length)
  2879. {
  2880. WriteVariableOctet(BufferDescriptor, IDENT_REVCHARGE,
  2881. Message->ReverseChargeIndication.Length,
  2882. Message->ReverseChargeIndication.Contents);
  2883. }
  2884. if (Message->CallingPartyNumber.Present &&
  2885. Message->CallingPartyNumber.Length)
  2886. {
  2887. WriteVariableOctet(BufferDescriptor, IDENT_CALLINGNUMBER,
  2888. Message->CallingPartyNumber.Length,
  2889. Message->CallingPartyNumber.Contents);
  2890. }
  2891. if (Message->CallingPartySubaddress.Present &&
  2892. Message->CallingPartySubaddress.Length)
  2893. {
  2894. WriteVariableOctet(BufferDescriptor, IDENT_CALLINGSUBADDR,
  2895. Message->CallingPartySubaddress.Length,
  2896. Message->CallingPartySubaddress.Contents);
  2897. }
  2898. if (Message->CalledPartyNumber.Present)
  2899. {
  2900. WritePartyNumber(BufferDescriptor, IDENT_CALLEDNUMBER,
  2901. Message->CalledPartyNumber.NumberType,
  2902. Message->CalledPartyNumber.NumberingPlan,
  2903. Message->CalledPartyNumber.PartyNumberLength,
  2904. Message->CalledPartyNumber.PartyNumbers);
  2905. }
  2906. if (Message->CalledPartySubaddress.Present &&
  2907. Message->CalledPartySubaddress.Length)
  2908. {
  2909. WriteVariableOctet(BufferDescriptor, IDENT_CALLEDSUBADDR,
  2910. Message->CalledPartySubaddress.Length,
  2911. Message->CalledPartySubaddress.Contents);
  2912. }
  2913. if (Message->RedirectingNumber.Present &&
  2914. Message->RedirectingNumber.Length)
  2915. {
  2916. WriteVariableOctet(BufferDescriptor, IDENT_REDIRECTING,
  2917. Message->RedirectingNumber.Length,
  2918. Message->RedirectingNumber.Contents);
  2919. }
  2920. if (Message->TransitNetworkSelection.Present &&
  2921. Message->TransitNetworkSelection.Length)
  2922. {
  2923. WriteVariableOctet(BufferDescriptor, IDENT_TRANSITNET,
  2924. Message->TransitNetworkSelection.Length,
  2925. Message->TransitNetworkSelection.Contents);
  2926. }
  2927. if (Message->RestartIndicator.Present &&
  2928. Message->RestartIndicator.Length)
  2929. {
  2930. WriteVariableOctet(BufferDescriptor, IDENT_RESTART,
  2931. Message->RestartIndicator.Length,
  2932. Message->RestartIndicator.Contents);
  2933. }
  2934. if (Message->LowLayerCompatibility.Present &&
  2935. Message->LowLayerCompatibility.Length)
  2936. {
  2937. WriteVariableOctet(BufferDescriptor, IDENT_LLCOMPATIBILITY,
  2938. Message->LowLayerCompatibility.Length,
  2939. Message->LowLayerCompatibility.Contents);
  2940. }
  2941. if (Message->HighLayerCompatibility.Present &&
  2942. Message->HighLayerCompatibility.Length)
  2943. {
  2944. WriteVariableOctet(BufferDescriptor, IDENT_HLCOMPATIBILITY,
  2945. Message->HighLayerCompatibility.Length,
  2946. Message->HighLayerCompatibility.Contents);
  2947. }
  2948. if (Message->UserToUser.Present &&
  2949. Message->UserToUser.UserInformationLength)
  2950. {
  2951. WriteVariableASN(BufferDescriptor,
  2952. IDENT_USERUSER,
  2953. Message->UserToUser.UserInformationLength,
  2954. Message->UserToUser.UserInformation);
  2955. }
  2956. return CS_OK;
  2957. }
  2958. //------------------------------------------------------------------------------
  2959. // Parse a generic Q931 message and place the fields of the
  2960. // of the buffer into the appropriate field structure.
  2961. //
  2962. // Parameters:
  2963. // BufferDescriptor Pointer to buffer descriptor of a
  2964. // the network packet of the 931 message
  2965. // Message Pointer to space for parsed information.
  2966. //------------------------------------------------------------------------------
  2967. HRESULT
  2968. Q931MakeEncodedMessage(
  2969. PQ931MESSAGE Message,
  2970. BYTE **CodedBufferPtr,
  2971. DWORD *CodedBufferLength)
  2972. {
  2973. BUFFERDESCR BufferDescriptor;
  2974. BYTE *OutBuffer = NULL;
  2975. DWORD Pass1Length = 0;
  2976. if ((CodedBufferPtr == NULL) || (CodedBufferLength == NULL))
  2977. {
  2978. return CS_BAD_PARAM;
  2979. }
  2980. BufferDescriptor.Length = 0;
  2981. BufferDescriptor.BufferPtr = NULL;
  2982. WriteQ931Fields(&BufferDescriptor, Message);
  2983. if (BufferDescriptor.Length == 0)
  2984. {
  2985. return CS_NO_FIELD_DATA;
  2986. }
  2987. Pass1Length = BufferDescriptor.Length;
  2988. OutBuffer = (BYTE *)Malloc(BufferDescriptor.Length + 1000);
  2989. if (OutBuffer == NULL)
  2990. {
  2991. return CS_NO_MEMORY;
  2992. }
  2993. BufferDescriptor.Length = 0;
  2994. BufferDescriptor.BufferPtr = OutBuffer;
  2995. WriteQ931Fields(&BufferDescriptor, Message);
  2996. if (Pass1Length != BufferDescriptor.Length)
  2997. {
  2998. // this is a serious error, since memory may have been overrun.
  2999. return CS_BAD_PARAM;
  3000. }
  3001. *CodedBufferPtr = OutBuffer;
  3002. *CodedBufferLength = BufferDescriptor.Length;
  3003. return CS_OK;
  3004. }
  3005. //-------------------------------------------------------------------------------------
  3006. //-------------------------------------------------------------------------------------
  3007. HRESULT
  3008. Q931SetupEncodePDU(
  3009. WORD wCallReference,
  3010. char *pszDisplay,
  3011. char *pszCalledPartyNumber,
  3012. DWORD dwBandwidth,
  3013. BINARY_STRING *pUserUserData,
  3014. BYTE **CodedBufferPtr,
  3015. DWORD *CodedBufferLength)
  3016. {
  3017. Q931MESSAGE *pMessage;
  3018. HRESULT Result = CS_OK;
  3019. BYTE bBandwidth;
  3020. pMessage = (Q931MESSAGE *)Malloc(sizeof(Q931MESSAGE));
  3021. if (pMessage == NULL)
  3022. {
  3023. return CS_NO_MEMORY;
  3024. }
  3025. // fill in the required fields for the setup message.
  3026. memset(pMessage, 0, sizeof(Q931MESSAGE));
  3027. pMessage->ProtocolDiscriminator = Q931PDVALUE;
  3028. pMessage->CallReference = wCallReference;
  3029. pMessage->MessageType = SETUPMESSAGETYPE;
  3030. pMessage->BearerCapability.Present = TRUE;
  3031. pMessage->BearerCapability.Length = 4;
  3032. pMessage->BearerCapability.Contents[0] =
  3033. (BYTE)(BEAR_EXT_BIT | BEAR_CCITT | BEAR_UNRESTRICTED_DIGITAL);
  3034. pMessage->BearerCapability.Contents[1] =
  3035. (BYTE)(BEAR_CIRCUIT_MODE | BEAR_MULTIRATE);
  3036. bBandwidth = (BYTE)(dwBandwidth / 64000);
  3037. if ((dwBandwidth % 64000) != 0)
  3038. bBandwidth++;
  3039. pMessage->BearerCapability.Contents[2] =
  3040. (BYTE)(BEAR_EXT_BIT | bBandwidth);
  3041. pMessage->BearerCapability.Contents[3] =
  3042. (BYTE)(BEAR_EXT_BIT | BEAR_LAYER1_INDICATOR | BEAR_LAYER1_H221_H242);
  3043. if (pszDisplay && *pszDisplay)
  3044. {
  3045. pMessage->Display.Present = TRUE;
  3046. pMessage->Display.Length = (BYTE)(strlen(pszDisplay) + 1);
  3047. strcpy((char *)pMessage->Display.Contents, pszDisplay);
  3048. }
  3049. if (pszCalledPartyNumber && *pszCalledPartyNumber)
  3050. {
  3051. WORD wLen = (WORD)strlen(pszCalledPartyNumber);
  3052. pMessage->CalledPartyNumber.Present = TRUE;
  3053. pMessage->CalledPartyNumber.NumberType =
  3054. (BYTE)(CALLED_PARTY_EXT_BIT | CALLED_PARTY_TYPE_UNKNOWN);
  3055. pMessage->CalledPartyNumber.NumberingPlan =
  3056. (BYTE)(CALLED_PARTY_PLAN_E164);
  3057. pMessage->CalledPartyNumber.PartyNumberLength = (BYTE)wLen;
  3058. memcpy(pMessage->CalledPartyNumber.PartyNumbers,
  3059. pszCalledPartyNumber, wLen);
  3060. }
  3061. if (pUserUserData && pUserUserData->ptr)
  3062. {
  3063. if (pUserUserData->length > sizeof(pMessage->UserToUser.UserInformation))
  3064. {
  3065. Free(pMessage);
  3066. return CS_BAD_PARAM;
  3067. }
  3068. pMessage->UserToUser.Present = TRUE;
  3069. pMessage->UserToUser.UserInformationLength = (pUserUserData->length);
  3070. memcpy(pMessage->UserToUser.UserInformation,
  3071. pUserUserData->ptr, pUserUserData->length);
  3072. }
  3073. Result = Q931MakeEncodedMessage(pMessage, CodedBufferPtr,
  3074. CodedBufferLength);
  3075. Free(pMessage);
  3076. return Result;
  3077. }
  3078. //-------------------------------------------------------------------------------------
  3079. //-------------------------------------------------------------------------------------
  3080. HRESULT
  3081. Q931ReleaseCompleteEncodePDU(
  3082. WORD wCallReference,
  3083. BYTE *pbCause,
  3084. BINARY_STRING *pUserUserData,
  3085. BYTE **CodedBufferPtr,
  3086. DWORD *CodedBufferLength)
  3087. {
  3088. Q931MESSAGE *pMessage;
  3089. HRESULT Result = CS_OK;
  3090. if (pbCause)
  3091. {
  3092. switch (*pbCause)
  3093. {
  3094. case CAUSE_VALUE_NORMAL_CLEAR:
  3095. case CAUSE_VALUE_USER_BUSY:
  3096. case CAUSE_VALUE_NO_ANSWER:
  3097. case CAUSE_VALUE_REJECTED:
  3098. case CAUSE_VALUE_NOT_IMPLEMENTED:
  3099. case CAUSE_VALUE_INVALID_CRV:
  3100. case CAUSE_VALUE_IE_MISSING:
  3101. case CAUSE_VALUE_IE_CONTENTS:
  3102. case CAUSE_VALUE_TIMER_EXPIRED:
  3103. break;
  3104. default:
  3105. return CS_BAD_PARAM;
  3106. break;
  3107. }
  3108. }
  3109. pMessage = (Q931MESSAGE *)Malloc(sizeof(Q931MESSAGE));
  3110. if (pMessage == NULL)
  3111. {
  3112. return CS_NO_MEMORY;
  3113. }
  3114. // fill in the required fields for the setup message.
  3115. memset(pMessage, 0, sizeof(Q931MESSAGE));
  3116. pMessage->ProtocolDiscriminator = Q931PDVALUE;
  3117. pMessage->CallReference = wCallReference;
  3118. pMessage->MessageType = RELEASECOMPLMESSAGETYPE;
  3119. if (pbCause)
  3120. {
  3121. pMessage->Cause.Present = TRUE;
  3122. pMessage->Cause.Length = 3;
  3123. pMessage->Cause.Contents[0] = (BYTE)(CAUSE_CODING_CCITT | CAUSE_LOCATION_USER);
  3124. pMessage->Cause.Contents[1] = (BYTE)(CAUSE_RECOMMENDATION_Q931);
  3125. pMessage->Cause.Contents[2] = (BYTE)(CAUSE_EXT_BIT | *pbCause);
  3126. }
  3127. else
  3128. {
  3129. pMessage->Cause.Present = FALSE;
  3130. }
  3131. if (pUserUserData && pUserUserData->ptr)
  3132. {
  3133. if (pUserUserData->length > sizeof(pMessage->UserToUser.UserInformation))
  3134. {
  3135. Free(pMessage);
  3136. return CS_BAD_PARAM;
  3137. }
  3138. pMessage->UserToUser.Present = TRUE;
  3139. pMessage->UserToUser.UserInformationLength = (pUserUserData->length);
  3140. memcpy(pMessage->UserToUser.UserInformation,
  3141. pUserUserData->ptr, pUserUserData->length);
  3142. }
  3143. Result = Q931MakeEncodedMessage(pMessage, CodedBufferPtr,
  3144. CodedBufferLength);
  3145. Free(pMessage);
  3146. return Result;
  3147. }
  3148. //-------------------------------------------------------------------------------------
  3149. //-------------------------------------------------------------------------------------
  3150. HRESULT
  3151. Q931ConnectEncodePDU(
  3152. WORD wCallReference,
  3153. char *pszDisplay,
  3154. DWORD dwBandwidth,
  3155. BINARY_STRING *pUserUserData,
  3156. BYTE **CodedBufferPtr,
  3157. DWORD *CodedBufferLength)
  3158. {
  3159. Q931MESSAGE *pMessage;
  3160. HRESULT Result = CS_OK;
  3161. BYTE bBandwidth;
  3162. pMessage = (Q931MESSAGE *)Malloc(sizeof(Q931MESSAGE));
  3163. if (pMessage == NULL)
  3164. {
  3165. return CS_NO_MEMORY;
  3166. }
  3167. // fill in the required fields for the setup message.
  3168. memset(pMessage, 0, sizeof(Q931MESSAGE));
  3169. pMessage->ProtocolDiscriminator = Q931PDVALUE;
  3170. pMessage->CallReference = wCallReference;
  3171. pMessage->MessageType = CONNECTMESSAGETYPE;
  3172. pMessage->BearerCapability.Present = TRUE;
  3173. pMessage->BearerCapability.Length = 4;
  3174. pMessage->BearerCapability.Contents[0] =
  3175. (BYTE)(BEAR_EXT_BIT | BEAR_CCITT | BEAR_UNRESTRICTED_DIGITAL);
  3176. pMessage->BearerCapability.Contents[1] =
  3177. (BYTE)(BEAR_CIRCUIT_MODE | BEAR_MULTIRATE);
  3178. bBandwidth = (BYTE)(dwBandwidth / 64000);
  3179. if ((dwBandwidth % 64000) != 0)
  3180. bBandwidth++;
  3181. pMessage->BearerCapability.Contents[2] =
  3182. (BYTE)(BEAR_EXT_BIT | bBandwidth);
  3183. pMessage->BearerCapability.Contents[3] =
  3184. (BYTE)(BEAR_EXT_BIT | BEAR_LAYER1_INDICATOR | BEAR_LAYER1_H221_H242);
  3185. if (pszDisplay && *pszDisplay)
  3186. {
  3187. pMessage->Display.Present = TRUE;
  3188. pMessage->Display.Length = (BYTE)strlen(pszDisplay);
  3189. strcpy((char *)pMessage->Display.Contents, pszDisplay);
  3190. }
  3191. if (pUserUserData && pUserUserData->ptr)
  3192. {
  3193. if (pUserUserData->length > sizeof(pMessage->UserToUser.UserInformation))
  3194. {
  3195. Free(pMessage);
  3196. return CS_BAD_PARAM;
  3197. }
  3198. pMessage->UserToUser.Present = TRUE;
  3199. pMessage->UserToUser.UserInformationLength = (pUserUserData->length);
  3200. memcpy(pMessage->UserToUser.UserInformation,
  3201. pUserUserData->ptr, pUserUserData->length);
  3202. }
  3203. Result = Q931MakeEncodedMessage(pMessage, CodedBufferPtr,
  3204. CodedBufferLength);
  3205. Free(pMessage);
  3206. return Result;
  3207. }
  3208. //-------------------------------------------------------------------------------------
  3209. //-------------------------------------------------------------------------------------
  3210. HRESULT
  3211. Q931ProceedingEncodePDU(
  3212. WORD wCallReference,
  3213. BINARY_STRING *pUserUserData,
  3214. BYTE **CodedBufferPtr,
  3215. DWORD *CodedBufferLength)
  3216. {
  3217. Q931MESSAGE *pMessage;
  3218. HRESULT Result = CS_OK;
  3219. pMessage = (Q931MESSAGE *)Malloc(sizeof(Q931MESSAGE));
  3220. if (pMessage == NULL)
  3221. {
  3222. return CS_NO_MEMORY;
  3223. }
  3224. // fill in the required fields for the setup message.
  3225. memset(pMessage, 0, sizeof(Q931MESSAGE));
  3226. pMessage->ProtocolDiscriminator = Q931PDVALUE;
  3227. pMessage->CallReference = wCallReference;
  3228. pMessage->MessageType = PROCEEDINGMESSAGETYPE;
  3229. if (pUserUserData && pUserUserData->ptr)
  3230. {
  3231. if (pUserUserData->length > sizeof(pMessage->UserToUser.UserInformation))
  3232. {
  3233. Free(pMessage);
  3234. return CS_BAD_PARAM;
  3235. }
  3236. pMessage->UserToUser.Present = TRUE;
  3237. pMessage->UserToUser.UserInformationLength = (pUserUserData->length);
  3238. memcpy(pMessage->UserToUser.UserInformation,
  3239. pUserUserData->ptr, pUserUserData->length);
  3240. }
  3241. Result = Q931MakeEncodedMessage(pMessage, CodedBufferPtr,
  3242. CodedBufferLength);
  3243. Free(pMessage);
  3244. return Result;
  3245. }
  3246. //-------------------------------------------------------------------------------------
  3247. //-------------------------------------------------------------------------------------
  3248. HRESULT
  3249. Q931AlertingEncodePDU(
  3250. WORD wCallReference,
  3251. BINARY_STRING *pUserUserData,
  3252. BYTE **CodedBufferPtr,
  3253. DWORD *CodedBufferLength)
  3254. {
  3255. Q931MESSAGE *pMessage;
  3256. HRESULT Result = CS_OK;
  3257. pMessage = (Q931MESSAGE *)Malloc(sizeof(Q931MESSAGE));
  3258. if (pMessage == NULL)
  3259. {
  3260. return CS_NO_MEMORY;
  3261. }
  3262. // fill in the required fields for the setup message.
  3263. memset(pMessage, 0, sizeof(Q931MESSAGE));
  3264. pMessage->ProtocolDiscriminator = Q931PDVALUE;
  3265. pMessage->CallReference = wCallReference;
  3266. pMessage->MessageType = ALERTINGMESSAGETYPE;
  3267. if (pUserUserData && pUserUserData->ptr)
  3268. {
  3269. if (pUserUserData->length > sizeof(pMessage->UserToUser.UserInformation))
  3270. {
  3271. Free(pMessage);
  3272. return CS_BAD_PARAM;
  3273. }
  3274. pMessage->UserToUser.Present = TRUE;
  3275. pMessage->UserToUser.UserInformationLength = (pUserUserData->length);
  3276. memcpy(pMessage->UserToUser.UserInformation,
  3277. pUserUserData->ptr, pUserUserData->length);
  3278. }
  3279. Result = Q931MakeEncodedMessage(pMessage, CodedBufferPtr,
  3280. CodedBufferLength);
  3281. Free(pMessage);
  3282. return Result;
  3283. }
  3284. //-------------------------------------------------------------------------------------
  3285. //-------------------------------------------------------------------------------------
  3286. HRESULT
  3287. Q931FacilityEncodePDU(
  3288. WORD wCallReference,
  3289. BINARY_STRING *pUserUserData,
  3290. BYTE **CodedBufferPtr,
  3291. DWORD *CodedBufferLength)
  3292. {
  3293. Q931MESSAGE *pMessage;
  3294. HRESULT Result = CS_OK;
  3295. pMessage = (Q931MESSAGE *)Malloc(sizeof(Q931MESSAGE));
  3296. if (pMessage == NULL)
  3297. {
  3298. return CS_NO_MEMORY;
  3299. }
  3300. // fill in the required fields for the setup message.
  3301. memset(pMessage, 0, sizeof(Q931MESSAGE));
  3302. pMessage->ProtocolDiscriminator = Q931PDVALUE;
  3303. pMessage->CallReference = wCallReference;
  3304. pMessage->MessageType = FACILITYMESSAGETYPE;
  3305. // The facility ie is encoded as present, but empty...
  3306. pMessage->Facility.Present = TRUE;
  3307. pMessage->Facility.Length = 0;
  3308. pMessage->Facility.Contents[0] = 0;
  3309. if (pUserUserData && pUserUserData->ptr)
  3310. {
  3311. if (pUserUserData->length > sizeof(pMessage->UserToUser.UserInformation))
  3312. {
  3313. Free(pMessage);
  3314. return CS_BAD_PARAM;
  3315. }
  3316. pMessage->UserToUser.Present = TRUE;
  3317. pMessage->UserToUser.UserInformationLength = (pUserUserData->length);
  3318. memcpy(pMessage->UserToUser.UserInformation,
  3319. pUserUserData->ptr, pUserUserData->length);
  3320. }
  3321. Result = Q931MakeEncodedMessage(pMessage, CodedBufferPtr,
  3322. CodedBufferLength);
  3323. Free(pMessage);
  3324. return Result;
  3325. }
  3326. //-------------------------------------------------------------------------------------
  3327. //-------------------------------------------------------------------------------------
  3328. HRESULT
  3329. Q931StatusEncodePDU(
  3330. WORD wCallReference,
  3331. char *pszDisplay,
  3332. BYTE bCause,
  3333. BYTE bCallState,
  3334. BYTE **CodedBufferPtr,
  3335. DWORD *CodedBufferLength)
  3336. {
  3337. Q931MESSAGE *pMessage;
  3338. HRESULT Result = CS_OK;
  3339. pMessage = (Q931MESSAGE *)Malloc(sizeof(Q931MESSAGE));
  3340. if (pMessage == NULL)
  3341. {
  3342. return CS_NO_MEMORY;
  3343. }
  3344. // fill in the required fields for the setup message.
  3345. memset(pMessage, 0, sizeof(Q931MESSAGE));
  3346. pMessage->ProtocolDiscriminator = Q931PDVALUE;
  3347. pMessage->CallReference = wCallReference;
  3348. pMessage->MessageType = STATUSMESSAGETYPE;
  3349. if (pszDisplay && *pszDisplay)
  3350. {
  3351. pMessage->Display.Present = TRUE;
  3352. pMessage->Display.Length = (BYTE)(strlen(pszDisplay) + 1);
  3353. strcpy((char *)pMessage->Display.Contents, pszDisplay);
  3354. }
  3355. pMessage->Cause.Present = TRUE;
  3356. pMessage->Cause.Length = 3;
  3357. pMessage->Cause.Contents[0] = (BYTE)(CAUSE_CODING_CCITT | CAUSE_LOCATION_USER);
  3358. pMessage->Cause.Contents[1] = (BYTE)(CAUSE_RECOMMENDATION_Q931);
  3359. pMessage->Cause.Contents[2] = (BYTE)(CAUSE_EXT_BIT | bCause);
  3360. pMessage->CallState.Present = TRUE;
  3361. pMessage->CallState.Length = 1;
  3362. pMessage->CallState.Contents[0] = (BYTE)(bCallState);
  3363. Result = Q931MakeEncodedMessage(pMessage, CodedBufferPtr,
  3364. CodedBufferLength);
  3365. Free(pMessage);
  3366. return Result;
  3367. }
  3368. #if(0)
  3369. //========================================================================
  3370. //========================================================================
  3371. //========================================================================
  3372. // THIS IS THE ASN PART...
  3373. //========================================================================
  3374. //========================================================================
  3375. //========================================================================
  3376. static ERROR_MAP EncodeErrorMap[] =
  3377. {
  3378. PDU_ENCODED, __TEXT("PDU successfully encoded"),
  3379. MORE_BUF, __TEXT("User-provided output buffer too small"),
  3380. PDU_RANGE, __TEXT("PDU specified out of range"),
  3381. BAD_ARG, __TEXT("Bad pointer was passed"),
  3382. BAD_VERSION, __TEXT("Versions of encoder and table do not match"),
  3383. OUT_MEMORY, __TEXT("Memory-allocation error"),
  3384. BAD_CHOICE, __TEXT("Unknown selector for a choice"),
  3385. BAD_OBJID, __TEXT("Object identifier conflicts with x.208"),
  3386. BAD_PTR, __TEXT("Unexpected NULL pointer in input buffer"),
  3387. BAD_TIME, __TEXT("Bad value in time type"),
  3388. MEM_ERROR, __TEXT("Memory violation signal trapped"),
  3389. BAD_TABLE, __TEXT("Table was bad, but not NULL"),
  3390. TOO_LONG, __TEXT("Type was longer than constraint"),
  3391. CONSTRAINT_VIOLATED, __TEXT("Constraint violation error occured"),
  3392. FATAL_ERROR, __TEXT("Serious internal error"),
  3393. ACCESS_SERIALIZATION_ERROR, __TEXT("Thread access to global data failed"),
  3394. NULL_TBL, __TEXT("NULL control table pointer"),
  3395. NULL_FCN, __TEXT("Encoder called via a NULL pointer"),
  3396. BAD_ENCRULES, __TEXT("Unknown encoding rules"),
  3397. UNAVAIL_ENCRULES, __TEXT("Encoding rules requested are not implemented"),
  3398. UNIMPLEMENTED, __TEXT("Type was not implemented yet"),
  3399. // LOAD_ERR, __TEXT("Unable to load DLL"),
  3400. CANT_OPEN_TRACE_FILE, __TEXT("Error when opening a trace file"),
  3401. TRACE_FILE_ALREADY_OPEN, __TEXT("Trace file has been opened"),
  3402. TABLE_MISMATCH, __TEXT("Control table mismatch"),
  3403. 0, NULL
  3404. };
  3405. static ERROR_MAP DecodeErrorMap[] =
  3406. {
  3407. PDU_DECODED, __TEXT("PDU successfully decoded"),
  3408. MORE_BUF, __TEXT("User-provided output buffer too small"),
  3409. NEGATIVE_UINTEGER, __TEXT("The first unsigned bit of the encoding is 1"),
  3410. PDU_RANGE, __TEXT("Pdu specified out of range"),
  3411. MORE_INPUT, __TEXT("Unexpected end of input buffer"),
  3412. DATA_ERROR, __TEXT("An error exists in the encoded data"),
  3413. BAD_VERSION, __TEXT("Versions of encoder and table do not match"),
  3414. OUT_MEMORY, __TEXT("Memory-allocation error"),
  3415. PDU_MISMATCH, __TEXT("The PDU tag does not match data"),
  3416. LIMITED, __TEXT("Size implementation limit exceeded"),
  3417. CONSTRAINT_VIOLATED, __TEXT("Constraint violation error occured"),
  3418. ACCESS_SERIALIZATION_ERROR, __TEXT("Thread access to global data failed"),
  3419. NULL_TBL, __TEXT("NULL control table pointer"),
  3420. NULL_FCN, __TEXT("Encoder called via a NULL pointer"),
  3421. BAD_ENCRULES, __TEXT("Unknown encoding rules"),
  3422. UNAVAIL_ENCRULES, __TEXT("Encoding rules requested are not implemented"),
  3423. UNIMPLEMENTED, __TEXT("The type was not implemented yet"),
  3424. // LOAD_ERR, __TEXT("Unable to load DLL"),
  3425. CANT_OPEN_TRACE_FILE, __TEXT("Error when opening a trace file"),
  3426. TRACE_FILE_ALREADY_OPEN, __TEXT("The trace file has been opened"),
  3427. TABLE_MISMATCH, __TEXT("Control table mismatch"),
  3428. 0, NULL
  3429. };
  3430. #endif // if(0)
  3431. //====================================================================================
  3432. //====================================================================================
  3433. #ifdef UNICODE_TRACE
  3434. LPWSTR
  3435. #else
  3436. LPSTR
  3437. #endif
  3438. ErrorToTextASN(ERROR_MAP *Map, int nErrorCode)
  3439. {
  3440. register int nIndex = 0;
  3441. if (Map != NULL)
  3442. {
  3443. for (nIndex = 0; Map[nIndex].pszErrorText; nIndex++)
  3444. {
  3445. if (Map[nIndex].nErrorCode == nErrorCode)
  3446. {
  3447. return Map[nIndex].pszErrorText;
  3448. }
  3449. }
  3450. }
  3451. return __TEXT("Unknown ASN.1 Error");
  3452. }
  3453. #if 0
  3454. //------------------------------------------------------------------------
  3455. //------------------------------------------------------------------------
  3456. int
  3457. ASN1LinePrint(FILE *stream, const char *format, ...)
  3458. {
  3459. va_list marker;
  3460. char buf[300];
  3461. int i;
  3462. va_start(marker, format);
  3463. i = wsprintf(buf, format, marker);
  3464. va_end(marker);
  3465. // TRACE the buf...
  3466. QTRACE((buf));
  3467. return i;
  3468. }
  3469. #endif
  3470. //------------------------------------------------------------------------
  3471. //------------------------------------------------------------------------
  3472. HRESULT
  3473. Q931InitPER()
  3474. {
  3475. // initialize TELES ASN.1 module structure
  3476. if (Q931_InitModule() != ASN1_SUCCESS)
  3477. {
  3478. ASSERT(FALSE);
  3479. return CS_SUBSYSTEM_FAILURE;
  3480. }
  3481. // note: init of world struct moved to CreateCallObject()
  3482. ProtocolId1.value = Q931_PROTOCOL_ID1;
  3483. ProtocolId1.next = &ProtocolId2;
  3484. ProtocolId2.value = Q931_PROTOCOL_ID2;
  3485. ProtocolId2.next = &ProtocolId3;
  3486. ProtocolId3.value = Q931_PROTOCOL_ID3;
  3487. ProtocolId3.next = &ProtocolId4;
  3488. ProtocolId4.value = Q931_PROTOCOL_ID4;
  3489. ProtocolId4.next = &ProtocolId5;
  3490. ProtocolId5.value = Q931_PROTOCOL_ID5;
  3491. ProtocolId5.next = &ProtocolId6;
  3492. ProtocolId6.value = Q931_PROTOCOL_ID6;
  3493. ProtocolId6.next = NULL;
  3494. // gateway protocol supported. For now, hard-coded to only 1: H323.
  3495. TempProtocol.next = NULL;
  3496. TempProtocol.value.choice = h323_chosen;
  3497. return CS_OK;
  3498. }
  3499. //------------------------------------------------------------------------
  3500. //------------------------------------------------------------------------
  3501. HRESULT
  3502. Q931DeInitPER()
  3503. {
  3504. // clean up TELES ASN.1 module structure
  3505. Q931_TermModule();
  3506. return CS_OK;
  3507. }
  3508. #define USE_ASN1_ENCODING 5
  3509. //-------------------------------------------------------------------------------------
  3510. //-------------------------------------------------------------------------------------
  3511. HRESULT
  3512. Q931SetupEncodeASN(
  3513. PCC_NONSTANDARDDATA pNonStandardData,
  3514. CC_ADDR *pCallerAddr, // this data is not yet passed in the PDU...
  3515. CC_ADDR *pCalleeAddr,
  3516. WORD wGoal,
  3517. WORD wCallType,
  3518. BOOL bCallerIsMC,
  3519. CC_CONFERENCEID *pConferenceID,
  3520. PCC_ALIASNAMES pCallerAliasList,
  3521. PCC_ALIASNAMES pCalleeAliasList,
  3522. PCC_ALIASNAMES pExtraAliasList,
  3523. PCC_ALIASITEM pExtensionAliasItem,
  3524. PCC_VENDORINFO pVendorInfo,
  3525. BOOL bIsTerminal,
  3526. BOOL bIsGateway,
  3527. ASN1_CODER_INFO *pWorld,
  3528. BYTE **ppEncodedBuf,
  3529. DWORD *pdwEncodedLength)
  3530. {
  3531. int rc;
  3532. H323_UserInformation UserInfo;
  3533. *ppEncodedBuf = NULL;
  3534. *pdwEncodedLength = 0;
  3535. memset(&UserInfo, 0, sizeof(H323_UserInformation));
  3536. UserInfo.bit_mask = 0;
  3537. // make sure the user_data_present flag is turned off.
  3538. UserInfo.bit_mask &= (~user_data_present);
  3539. if (pNonStandardData)
  3540. {
  3541. UserInfo.h323_uu_pdu.bit_mask |= H323_UU_PDU_nnStndrdDt_present;
  3542. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice = h221NonStandard_chosen;
  3543. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode =
  3544. pNonStandardData->bCountryCode;
  3545. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension =
  3546. pNonStandardData->bExtension;
  3547. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode =
  3548. pNonStandardData->wManufacturerCode;
  3549. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length =
  3550. pNonStandardData->sData.wOctetStringLength;
  3551. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value =
  3552. pNonStandardData->sData.pOctetString;
  3553. }
  3554. else
  3555. {
  3556. UserInfo.h323_uu_pdu.bit_mask &= (~H323_UU_PDU_nnStndrdDt_present);
  3557. }
  3558. UserInfo.h323_uu_pdu.h323_message_body.choice = setup_chosen;
  3559. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask = 0;
  3560. UserInfo.h323_uu_pdu.h323_message_body.u.setup.protocolIdentifier = &ProtocolId1;
  3561. if (pCallerAliasList)
  3562. {
  3563. CS_STATUS AliasResult = CS_OK;
  3564. AliasResult = AliasToSeqof((struct _seqof3 **)&(UserInfo.h323_uu_pdu.
  3565. h323_message_body.u.setup.sourceAddress), pCallerAliasList);
  3566. if (AliasResult != CS_OK)
  3567. {
  3568. return CS_NO_MEMORY;
  3569. }
  3570. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask |=
  3571. (sourceAddress_present);
  3572. }
  3573. else
  3574. {
  3575. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask &=
  3576. (~sourceAddress_present);
  3577. }
  3578. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.bit_mask = 0;
  3579. if (pVendorInfo)
  3580. {
  3581. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.bit_mask |= vendor_present;
  3582. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.bit_mask = 0;
  3583. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.vendor.t35CountryCode = pVendorInfo->bCountryCode;
  3584. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.vendor.t35Extension = pVendorInfo->bExtension;
  3585. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.vendor.manufacturerCode = pVendorInfo->wManufacturerCode;
  3586. if (pVendorInfo->pProductNumber && pVendorInfo->pProductNumber->pOctetString &&
  3587. pVendorInfo->pProductNumber->wOctetStringLength)
  3588. {
  3589. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.bit_mask |= productId_present;
  3590. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.productId.length =
  3591. pVendorInfo->pProductNumber->wOctetStringLength;
  3592. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.productId.value,
  3593. pVendorInfo->pProductNumber->pOctetString,
  3594. pVendorInfo->pProductNumber->wOctetStringLength);
  3595. }
  3596. if (pVendorInfo->pVersionNumber && pVendorInfo->pVersionNumber->pOctetString &&
  3597. pVendorInfo->pVersionNumber->wOctetStringLength)
  3598. {
  3599. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.bit_mask |= versionId_present;
  3600. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.versionId.length =
  3601. pVendorInfo->pVersionNumber->wOctetStringLength;
  3602. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.versionId.value,
  3603. pVendorInfo->pVersionNumber->pOctetString,
  3604. pVendorInfo->pVersionNumber->wOctetStringLength);
  3605. }
  3606. }
  3607. if (bIsTerminal)
  3608. {
  3609. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.bit_mask |=
  3610. terminal_present;
  3611. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.terminal.bit_mask = 0;
  3612. }
  3613. if (bIsGateway)
  3614. {
  3615. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.bit_mask |=
  3616. gateway_present;
  3617. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.gateway.bit_mask = protocol_present;
  3618. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.gateway.protocol = &TempProtocol;
  3619. }
  3620. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.mc = (ASN1_BOOL)bCallerIsMC;
  3621. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceInfo.undefinedNode = 0;
  3622. if (pCalleeAliasList)
  3623. {
  3624. CS_STATUS AliasResult = CS_OK;
  3625. AliasResult = AliasWithPrefixToSeqof((struct _seqof3 **)&(UserInfo.h323_uu_pdu.
  3626. h323_message_body.u.setup.destinationAddress), pCalleeAliasList);
  3627. if (AliasResult != CS_OK)
  3628. {
  3629. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.
  3630. h323_message_body.u.setup.sourceAddress);
  3631. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceAddress = NULL;
  3632. return CS_NO_MEMORY;
  3633. }
  3634. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask |=
  3635. (destinationAddress_present);
  3636. }
  3637. else
  3638. {
  3639. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask &=
  3640. (~destinationAddress_present);
  3641. }
  3642. if (pExtraAliasList)
  3643. {
  3644. CS_STATUS AliasResult = CS_OK;
  3645. AliasResult = AliasWithPrefixToSeqof((struct _seqof3 **)&(UserInfo.h323_uu_pdu.
  3646. h323_message_body.u.setup.destExtraCallInfo), pExtraAliasList);
  3647. if (AliasResult != CS_OK)
  3648. {
  3649. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.setup.destinationAddress);
  3650. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destinationAddress = NULL;
  3651. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceAddress);
  3652. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceAddress = NULL;
  3653. return CS_NO_MEMORY;
  3654. }
  3655. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask |=
  3656. (destExtraCallInfo_present);
  3657. }
  3658. else
  3659. {
  3660. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask &=
  3661. (~destExtraCallInfo_present);
  3662. }
  3663. if (pCalleeAddr)
  3664. {
  3665. DWORD a = pCalleeAddr->Addr.IP_Binary.dwAddr;
  3666. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.choice = ipAddress_chosen;
  3667. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.length = 4;
  3668. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.port =
  3669. pCalleeAddr->Addr.IP_Binary.wPort;
  3670. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.value[0] =
  3671. ((BYTE *)&a)[3];
  3672. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.value[1] =
  3673. ((BYTE *)&a)[2];
  3674. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.value[2] =
  3675. ((BYTE *)&a)[1];
  3676. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.value[3] =
  3677. ((BYTE *)&a)[0];
  3678. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask |=
  3679. (destCallSignalAddress_present);
  3680. }
  3681. else
  3682. {
  3683. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask &=
  3684. (~destCallSignalAddress_present);
  3685. }
  3686. UserInfo.h323_uu_pdu.h323_message_body.u.setup.activeMC = (ASN1_BOOL)bCallerIsMC;
  3687. if (pConferenceID != NULL)
  3688. {
  3689. UserInfo.h323_uu_pdu.h323_message_body.u.setup.conferenceID.length =
  3690. sizeof(UserInfo.h323_uu_pdu.h323_message_body.u.setup.conferenceID.value);
  3691. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.setup.conferenceID.value,
  3692. pConferenceID->buffer,
  3693. UserInfo.h323_uu_pdu.h323_message_body.u.setup.conferenceID.length);
  3694. }
  3695. switch (wGoal)
  3696. {
  3697. case CSG_INVITE:
  3698. UserInfo.h323_uu_pdu.h323_message_body.u.setup.conferenceGoal.choice = invite_chosen;
  3699. break;
  3700. case CSG_JOIN:
  3701. UserInfo.h323_uu_pdu.h323_message_body.u.setup.conferenceGoal.choice = join_chosen;
  3702. break;
  3703. default:
  3704. UserInfo.h323_uu_pdu.h323_message_body.u.setup.conferenceGoal.choice = create_chosen;
  3705. } // switch
  3706. switch (wCallType)
  3707. {
  3708. case CC_CALLTYPE_1_N:
  3709. UserInfo.h323_uu_pdu.h323_message_body.u.setup.callType.choice = oneToN_chosen;
  3710. break;
  3711. case CC_CALLTYPE_N_1:
  3712. UserInfo.h323_uu_pdu.h323_message_body.u.setup.callType.choice = nToOne_chosen;
  3713. break;
  3714. case CC_CALLTYPE_N_N:
  3715. UserInfo.h323_uu_pdu.h323_message_body.u.setup.callType.choice = nToN_chosen;
  3716. break;
  3717. default:
  3718. UserInfo.h323_uu_pdu.h323_message_body.u.setup.callType.choice = pointToPoint_chosen;
  3719. } // switch
  3720. if (pCallerAddr)
  3721. {
  3722. DWORD a = pCallerAddr->Addr.IP_Binary.dwAddr;
  3723. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.choice = ipAddress_chosen;
  3724. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.length = 4;
  3725. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.port =
  3726. pCallerAddr->Addr.IP_Binary.wPort;
  3727. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.value[0] =
  3728. ((BYTE *)&a)[3];
  3729. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.value[1] =
  3730. ((BYTE *)&a)[2];
  3731. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.value[2] =
  3732. ((BYTE *)&a)[1];
  3733. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.value[3] =
  3734. ((BYTE *)&a)[0];
  3735. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask |=
  3736. (sourceCallSignalAddress_present);
  3737. }
  3738. else
  3739. {
  3740. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask &=
  3741. (~sourceCallSignalAddress_present);
  3742. }
  3743. if (pExtensionAliasItem)
  3744. {
  3745. CS_STATUS AliasResult = CS_OK;
  3746. AliasResult = Q931CopyAliasItemToAliasAddr(&(UserInfo.h323_uu_pdu.
  3747. h323_message_body.u.setup.remoteExtensionAddress), pExtensionAliasItem);
  3748. if (AliasResult != CS_OK)
  3749. {
  3750. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.setup.destExtraCallInfo);
  3751. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destExtraCallInfo = NULL;
  3752. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.setup.destinationAddress);
  3753. UserInfo.h323_uu_pdu.h323_message_body.u.setup.destinationAddress = NULL;
  3754. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceAddress);
  3755. UserInfo.h323_uu_pdu.h323_message_body.u.setup.sourceAddress = NULL;
  3756. return CS_NO_MEMORY;
  3757. }
  3758. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask |=
  3759. (remoteExtensionAddress_present);
  3760. }
  3761. else
  3762. {
  3763. UserInfo.h323_uu_pdu.h323_message_body.u.setup.bit_mask &=
  3764. (~remoteExtensionAddress_present);
  3765. }
  3766. rc = Q931_Encode(pWorld,
  3767. (void *) &UserInfo,
  3768. H323_UserInformation_PDU,
  3769. ppEncodedBuf,
  3770. pdwEncodedLength);
  3771. // Free the alias name structures from the UserInfo area.
  3772. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.
  3773. setup.sourceAddress);
  3774. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.
  3775. setup.destinationAddress);
  3776. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.
  3777. setup.destExtraCallInfo);
  3778. Q931ClearAliasAddr(&(UserInfo.h323_uu_pdu.h323_message_body.u.setup.remoteExtensionAddress));
  3779. if (ASN1_FAILED(rc))
  3780. {
  3781. ASSERT(FALSE);
  3782. return CS_SUBSYSTEM_FAILURE;
  3783. }
  3784. return CS_OK;
  3785. }
  3786. //-------------------------------------------------------------------------------------
  3787. //-------------------------------------------------------------------------------------
  3788. void
  3789. Q931FreeEncodedBuffer(ASN1_CODER_INFO *pWorld, BYTE *pEncodedBuf)
  3790. {
  3791. ASN1_FreeEncoded(pWorld->pEncInfo, pEncodedBuf);
  3792. }
  3793. //-------------------------------------------------------------------------------------
  3794. //-------------------------------------------------------------------------------------
  3795. HRESULT
  3796. Q931ReleaseCompleteEncodeASN(
  3797. PCC_NONSTANDARDDATA pNonStandardData,
  3798. CC_CONFERENCEID *pConferenceID, // not passed in PDU!
  3799. BYTE *pbReason,
  3800. ASN1_CODER_INFO *pWorld,
  3801. BYTE **ppEncodedBuf,
  3802. DWORD *pdwEncodedLength)
  3803. {
  3804. int rc;
  3805. H323_UserInformation UserInfo;
  3806. *ppEncodedBuf = NULL;
  3807. *pdwEncodedLength = 0;
  3808. memset(&UserInfo, 0, sizeof(H323_UserInformation));
  3809. UserInfo.bit_mask = 0;
  3810. // make sure the user_data_present flag is turned off.
  3811. UserInfo.bit_mask &= (~user_data_present);
  3812. UserInfo.h323_uu_pdu.bit_mask = 0;
  3813. if (pNonStandardData)
  3814. {
  3815. UserInfo.h323_uu_pdu.bit_mask |= H323_UU_PDU_nnStndrdDt_present;
  3816. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice = h221NonStandard_chosen;
  3817. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode =
  3818. pNonStandardData->bCountryCode;
  3819. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension =
  3820. pNonStandardData->bExtension;
  3821. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode =
  3822. pNonStandardData->wManufacturerCode;
  3823. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length =
  3824. pNonStandardData->sData.wOctetStringLength;
  3825. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value =
  3826. pNonStandardData->sData.pOctetString;
  3827. }
  3828. else
  3829. {
  3830. UserInfo.h323_uu_pdu.bit_mask &= (~H323_UU_PDU_nnStndrdDt_present);
  3831. }
  3832. UserInfo.h323_uu_pdu.h323_message_body.choice = releaseComplete_chosen;
  3833. UserInfo.h323_uu_pdu.h323_message_body.u.releaseComplete.protocolIdentifier = &ProtocolId1;
  3834. if (pbReason)
  3835. {
  3836. unsigned short choice = 0;
  3837. UserInfo.h323_uu_pdu.h323_message_body.u.releaseComplete.bit_mask |=
  3838. (reason_present);
  3839. switch (*pbReason)
  3840. {
  3841. case CC_REJECT_NO_BANDWIDTH:
  3842. choice = noBandwidth_chosen;
  3843. break;
  3844. case CC_REJECT_GATEKEEPER_RESOURCES:
  3845. choice = gatekeeperResources_chosen;
  3846. break;
  3847. case CC_REJECT_UNREACHABLE_DESTINATION:
  3848. choice = unreachableDestination_chosen;
  3849. break;
  3850. case CC_REJECT_DESTINATION_REJECTION:
  3851. choice = destinationRejection_chosen;
  3852. break;
  3853. case CC_REJECT_INVALID_REVISION:
  3854. choice = invalidRevision_chosen;
  3855. break;
  3856. case CC_REJECT_NO_PERMISSION:
  3857. choice = noPermission_chosen;
  3858. break;
  3859. case CC_REJECT_UNREACHABLE_GATEKEEPER:
  3860. choice = unreachableGatekeeper_chosen;
  3861. break;
  3862. case CC_REJECT_GATEWAY_RESOURCES:
  3863. choice = gatewayResources_chosen;
  3864. break;
  3865. case CC_REJECT_BAD_FORMAT_ADDRESS:
  3866. choice = badFormatAddress_chosen;
  3867. break;
  3868. case CC_REJECT_ADAPTIVE_BUSY:
  3869. choice = adaptiveBusy_chosen;
  3870. break;
  3871. case CC_REJECT_IN_CONF:
  3872. choice = inConf_chosen;
  3873. break;
  3874. case CC_REJECT_CALL_DEFLECTION:
  3875. choice = facilityCallDeflection_chosen;
  3876. break;
  3877. case CC_REJECT_UNDEFINED_REASON:
  3878. choice = RlsCmpltRsn_undfndRsn_chosen;
  3879. break;
  3880. case CC_REJECT_USER_BUSY:
  3881. choice = inConf_chosen;
  3882. break;
  3883. default:
  3884. return CS_BAD_PARAM;
  3885. break;
  3886. }
  3887. UserInfo.h323_uu_pdu.h323_message_body.u.releaseComplete.reason.choice = choice;
  3888. }
  3889. rc = Q931_Encode(pWorld,
  3890. (void *) &UserInfo,
  3891. H323_UserInformation_PDU,
  3892. ppEncodedBuf,
  3893. pdwEncodedLength);
  3894. if (ASN1_FAILED(rc))
  3895. {
  3896. ASSERT(FALSE);
  3897. return CS_SUBSYSTEM_FAILURE;
  3898. }
  3899. return CS_OK;
  3900. }
  3901. //-------------------------------------------------------------------------------------
  3902. //-------------------------------------------------------------------------------------
  3903. HRESULT
  3904. Q931ConnectEncodeASN(
  3905. PCC_NONSTANDARDDATA pNonStandardData,
  3906. CC_CONFERENCEID *pConferenceID, // must be able to support 16 byte conf id's!
  3907. CC_ADDR *h245Addr,
  3908. PCC_ENDPOINTTYPE pEndpointType,
  3909. ASN1_CODER_INFO *pWorld,
  3910. BYTE **ppEncodedBuf,
  3911. DWORD *pdwEncodedLength)
  3912. {
  3913. int rc;
  3914. H323_UserInformation UserInfo;
  3915. *ppEncodedBuf = NULL;
  3916. *pdwEncodedLength = 0;
  3917. memset(&UserInfo, 0, sizeof(H323_UserInformation));
  3918. UserInfo.bit_mask = 0;
  3919. // make sure the user_data_present flag is turned off.
  3920. UserInfo.bit_mask &= (~user_data_present);
  3921. UserInfo.h323_uu_pdu.bit_mask = 0;
  3922. if (pNonStandardData)
  3923. {
  3924. UserInfo.h323_uu_pdu.bit_mask |= H323_UU_PDU_nnStndrdDt_present;
  3925. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice = h221NonStandard_chosen;
  3926. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode =
  3927. pNonStandardData->bCountryCode;
  3928. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension =
  3929. pNonStandardData->bExtension;
  3930. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode =
  3931. pNonStandardData->wManufacturerCode;
  3932. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length =
  3933. pNonStandardData->sData.wOctetStringLength;
  3934. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value =
  3935. pNonStandardData->sData.pOctetString;
  3936. }
  3937. else
  3938. {
  3939. UserInfo.h323_uu_pdu.bit_mask &= (~H323_UU_PDU_nnStndrdDt_present);
  3940. }
  3941. UserInfo.h323_uu_pdu.h323_message_body.choice = connect_chosen;
  3942. UserInfo.h323_uu_pdu.h323_message_body.u.connect.protocolIdentifier = &ProtocolId1;
  3943. if (h245Addr != NULL)
  3944. {
  3945. DWORD a = h245Addr->Addr.IP_Binary.dwAddr;
  3946. UserInfo.h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.choice = ipAddress_chosen;
  3947. UserInfo.h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.length = 4;
  3948. UserInfo.h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.port =
  3949. h245Addr->Addr.IP_Binary.wPort;
  3950. UserInfo.h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.value[0] =
  3951. ((BYTE *)&a)[3];
  3952. UserInfo.h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.value[1] =
  3953. ((BYTE *)&a)[2];
  3954. UserInfo.h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.value[2] =
  3955. ((BYTE *)&a)[1];
  3956. UserInfo.h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.value[3] =
  3957. ((BYTE *)&a)[0];
  3958. UserInfo.h323_uu_pdu.h323_message_body.u.connect.bit_mask |=
  3959. (Cnnct_UUIE_h245Address_present);
  3960. }
  3961. else
  3962. {
  3963. UserInfo.h323_uu_pdu.h323_message_body.u.connect.bit_mask &=
  3964. (~Cnnct_UUIE_h245Address_present);
  3965. }
  3966. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.bit_mask = 0;
  3967. if (pEndpointType)
  3968. {
  3969. PCC_VENDORINFO pVendorInfo = pEndpointType->pVendorInfo;
  3970. if (pVendorInfo)
  3971. {
  3972. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.bit_mask |= vendor_present;
  3973. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.bit_mask = 0;
  3974. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.vendor.t35CountryCode = pVendorInfo->bCountryCode;
  3975. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.vendor.t35Extension = pVendorInfo->bExtension;
  3976. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.vendor.manufacturerCode = pVendorInfo->wManufacturerCode;
  3977. if (pVendorInfo->pProductNumber && pVendorInfo->pProductNumber->pOctetString &&
  3978. pVendorInfo->pProductNumber->wOctetStringLength)
  3979. {
  3980. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.bit_mask |= productId_present;
  3981. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.productId.length =
  3982. pVendorInfo->pProductNumber->wOctetStringLength;
  3983. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.productId.value,
  3984. pVendorInfo->pProductNumber->pOctetString,
  3985. pVendorInfo->pProductNumber->wOctetStringLength);
  3986. }
  3987. if (pVendorInfo->pVersionNumber && pVendorInfo->pVersionNumber->pOctetString &&
  3988. pVendorInfo->pVersionNumber->wOctetStringLength)
  3989. {
  3990. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.bit_mask |= versionId_present;
  3991. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.versionId.length =
  3992. pVendorInfo->pVersionNumber->wOctetStringLength;
  3993. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.versionId.value,
  3994. pVendorInfo->pVersionNumber->pOctetString,
  3995. pVendorInfo->pVersionNumber->wOctetStringLength);
  3996. }
  3997. }
  3998. if (pEndpointType->bIsTerminal)
  3999. {
  4000. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.bit_mask |=
  4001. terminal_present;
  4002. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.terminal.bit_mask = 0;
  4003. }
  4004. if (pEndpointType->bIsGateway)
  4005. {
  4006. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.bit_mask |=
  4007. gateway_present;
  4008. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.gateway.bit_mask = protocol_present;
  4009. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.gateway.protocol = &TempProtocol;
  4010. }
  4011. }
  4012. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.mc = 0;
  4013. UserInfo.h323_uu_pdu.h323_message_body.u.connect.destinationInfo.undefinedNode = 0;
  4014. if (pConferenceID != NULL)
  4015. {
  4016. UserInfo.h323_uu_pdu.h323_message_body.u.connect.conferenceID.length =
  4017. sizeof(UserInfo.h323_uu_pdu.h323_message_body.u.connect.conferenceID.value);
  4018. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.connect.conferenceID.value,
  4019. pConferenceID->buffer,
  4020. UserInfo.h323_uu_pdu.h323_message_body.u.connect.conferenceID.length);
  4021. }
  4022. rc = Q931_Encode(pWorld,
  4023. (void *) &UserInfo,
  4024. H323_UserInformation_PDU,
  4025. ppEncodedBuf,
  4026. pdwEncodedLength);
  4027. if (ASN1_FAILED(rc))
  4028. {
  4029. ASSERT(FALSE);
  4030. return CS_SUBSYSTEM_FAILURE;
  4031. }
  4032. return CS_OK;
  4033. }
  4034. //-------------------------------------------------------------------------------------
  4035. //-------------------------------------------------------------------------------------
  4036. HRESULT
  4037. Q931AlertingEncodeASN(
  4038. PCC_NONSTANDARDDATA pNonStandardData,
  4039. CC_ADDR *h245Addr,
  4040. PCC_ENDPOINTTYPE pEndpointType,
  4041. ASN1_CODER_INFO *pWorld,
  4042. BYTE **ppEncodedBuf,
  4043. DWORD *pdwEncodedLength)
  4044. {
  4045. int rc;
  4046. H323_UserInformation UserInfo;
  4047. *ppEncodedBuf = NULL;
  4048. *pdwEncodedLength = 0;
  4049. memset(&UserInfo, 0, sizeof(H323_UserInformation));
  4050. UserInfo.bit_mask = 0;
  4051. // make sure the user_data_present flag is turned off.
  4052. UserInfo.bit_mask &= (~user_data_present);
  4053. UserInfo.h323_uu_pdu.bit_mask = 0;
  4054. if (pNonStandardData)
  4055. {
  4056. UserInfo.h323_uu_pdu.bit_mask |= H323_UU_PDU_nnStndrdDt_present;
  4057. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice = h221NonStandard_chosen;
  4058. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode =
  4059. pNonStandardData->bCountryCode;
  4060. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension =
  4061. pNonStandardData->bExtension;
  4062. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode =
  4063. pNonStandardData->wManufacturerCode;
  4064. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length =
  4065. pNonStandardData->sData.wOctetStringLength;
  4066. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value =
  4067. pNonStandardData->sData.pOctetString;
  4068. }
  4069. else
  4070. {
  4071. UserInfo.h323_uu_pdu.bit_mask &= (~H323_UU_PDU_nnStndrdDt_present);
  4072. }
  4073. UserInfo.h323_uu_pdu.h323_message_body.choice = alerting_chosen;
  4074. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.protocolIdentifier = &ProtocolId1;
  4075. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.bit_mask = 0;
  4076. if (pEndpointType)
  4077. {
  4078. PCC_VENDORINFO pVendorInfo = pEndpointType->pVendorInfo;
  4079. if (pVendorInfo)
  4080. {
  4081. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.bit_mask |= vendor_present;
  4082. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.bit_mask = 0;
  4083. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.vendor.t35CountryCode = pVendorInfo->bCountryCode;
  4084. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.vendor.t35Extension = pVendorInfo->bExtension;
  4085. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.vendor.manufacturerCode = pVendorInfo->wManufacturerCode;
  4086. if (pVendorInfo->pProductNumber && pVendorInfo->pProductNumber->pOctetString &&
  4087. pVendorInfo->pProductNumber->wOctetStringLength)
  4088. {
  4089. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.bit_mask |= productId_present;
  4090. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.productId.length =
  4091. pVendorInfo->pProductNumber->wOctetStringLength;
  4092. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.productId.value,
  4093. pVendorInfo->pProductNumber->pOctetString,
  4094. pVendorInfo->pProductNumber->wOctetStringLength);
  4095. }
  4096. if (pVendorInfo->pVersionNumber && pVendorInfo->pVersionNumber->pOctetString &&
  4097. pVendorInfo->pVersionNumber->wOctetStringLength)
  4098. {
  4099. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.bit_mask |= versionId_present;
  4100. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.versionId.length =
  4101. pVendorInfo->pVersionNumber->wOctetStringLength;
  4102. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.vendor.versionId.value,
  4103. pVendorInfo->pVersionNumber->pOctetString,
  4104. pVendorInfo->pVersionNumber->wOctetStringLength);
  4105. }
  4106. }
  4107. if (pEndpointType->bIsTerminal)
  4108. {
  4109. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.bit_mask =
  4110. terminal_present;
  4111. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.terminal.bit_mask = 0;
  4112. }
  4113. if (pEndpointType->bIsGateway)
  4114. {
  4115. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.bit_mask =
  4116. gateway_present;
  4117. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.gateway.bit_mask = protocol_present;
  4118. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.gateway.protocol = &TempProtocol;
  4119. }
  4120. }
  4121. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.mc = 0;
  4122. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.destinationInfo.undefinedNode = 0;
  4123. if (h245Addr != NULL)
  4124. {
  4125. DWORD a = h245Addr->Addr.IP_Binary.dwAddr;
  4126. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.choice = ipAddress_chosen;
  4127. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.length = 4;
  4128. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.port =
  4129. h245Addr->Addr.IP_Binary.wPort;
  4130. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[0] =
  4131. ((BYTE *)&a)[3];
  4132. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[1] =
  4133. ((BYTE *)&a)[2];
  4134. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[2] =
  4135. ((BYTE *)&a)[1];
  4136. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[3] =
  4137. ((BYTE *)&a)[0];
  4138. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.bit_mask |=
  4139. (CPg_UUIE_h245Addrss_present);
  4140. }
  4141. else
  4142. {
  4143. UserInfo.h323_uu_pdu.h323_message_body.u.alerting.bit_mask &=
  4144. (~CPg_UUIE_h245Addrss_present);
  4145. }
  4146. rc = Q931_Encode(pWorld,
  4147. (void *) &UserInfo,
  4148. H323_UserInformation_PDU,
  4149. ppEncodedBuf,
  4150. pdwEncodedLength);
  4151. if (ASN1_FAILED(rc))
  4152. {
  4153. ASSERT(FALSE);
  4154. return CS_SUBSYSTEM_FAILURE;
  4155. }
  4156. return CS_OK;
  4157. }
  4158. //-------------------------------------------------------------------------------------
  4159. //-------------------------------------------------------------------------------------
  4160. HRESULT
  4161. Q931ProceedingEncodeASN(
  4162. PCC_NONSTANDARDDATA pNonStandardData,
  4163. CC_ADDR *h245Addr,
  4164. PCC_ENDPOINTTYPE pEndpointType,
  4165. ASN1_CODER_INFO *pWorld,
  4166. BYTE **ppEncodedBuf,
  4167. DWORD *pdwEncodedLength)
  4168. {
  4169. int rc;
  4170. H323_UserInformation UserInfo;
  4171. *ppEncodedBuf = NULL;
  4172. *pdwEncodedLength = 0;
  4173. memset(&UserInfo, 0, sizeof(H323_UserInformation));
  4174. UserInfo.bit_mask = 0;
  4175. // make sure the user_data_present flag is turned off.
  4176. UserInfo.bit_mask &= (~user_data_present);
  4177. UserInfo.h323_uu_pdu.bit_mask = 0;
  4178. if (pNonStandardData)
  4179. {
  4180. UserInfo.h323_uu_pdu.bit_mask |= H323_UU_PDU_nnStndrdDt_present;
  4181. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice = h221NonStandard_chosen;
  4182. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode =
  4183. pNonStandardData->bCountryCode;
  4184. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension =
  4185. pNonStandardData->bExtension;
  4186. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode =
  4187. pNonStandardData->wManufacturerCode;
  4188. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length =
  4189. pNonStandardData->sData.wOctetStringLength;
  4190. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value =
  4191. pNonStandardData->sData.pOctetString;
  4192. }
  4193. else
  4194. {
  4195. UserInfo.h323_uu_pdu.bit_mask &= (~H323_UU_PDU_nnStndrdDt_present);
  4196. }
  4197. UserInfo.h323_uu_pdu.h323_message_body.choice = callProceeding_chosen;
  4198. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.protocolIdentifier = &ProtocolId1;
  4199. if (h245Addr != NULL)
  4200. {
  4201. DWORD a = h245Addr->Addr.IP_Binary.dwAddr;
  4202. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.choice = ipAddress_chosen;
  4203. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.length = 4;
  4204. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.port =
  4205. h245Addr->Addr.IP_Binary.wPort;
  4206. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[0] =
  4207. ((BYTE *)&a)[3];
  4208. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[1] =
  4209. ((BYTE *)&a)[2];
  4210. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[2] =
  4211. ((BYTE *)&a)[1];
  4212. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[3] =
  4213. ((BYTE *)&a)[0];
  4214. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.bit_mask |=
  4215. (CPg_UUIE_h245Addrss_present);
  4216. }
  4217. else
  4218. {
  4219. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.bit_mask &=
  4220. (~CPg_UUIE_h245Addrss_present);
  4221. }
  4222. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.bit_mask = 0;
  4223. if (pEndpointType)
  4224. {
  4225. PCC_VENDORINFO pVendorInfo = pEndpointType->pVendorInfo;
  4226. if (pVendorInfo)
  4227. {
  4228. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.bit_mask |= vendor_present;
  4229. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.bit_mask = 0;
  4230. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.vendor.t35CountryCode = pVendorInfo->bCountryCode;
  4231. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.vendor.t35Extension = pVendorInfo->bExtension;
  4232. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.vendor.manufacturerCode = pVendorInfo->wManufacturerCode;
  4233. if (pVendorInfo->pProductNumber && pVendorInfo->pProductNumber->pOctetString &&
  4234. pVendorInfo->pProductNumber->wOctetStringLength)
  4235. {
  4236. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.bit_mask |= productId_present;
  4237. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.productId.length =
  4238. pVendorInfo->pProductNumber->wOctetStringLength;
  4239. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.productId.value,
  4240. pVendorInfo->pProductNumber->pOctetString,
  4241. pVendorInfo->pProductNumber->wOctetStringLength);
  4242. }
  4243. if (pVendorInfo->pVersionNumber && pVendorInfo->pVersionNumber->pOctetString &&
  4244. pVendorInfo->pVersionNumber->wOctetStringLength)
  4245. {
  4246. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.bit_mask |= versionId_present;
  4247. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.versionId.length =
  4248. pVendorInfo->pVersionNumber->wOctetStringLength;
  4249. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.vendor.versionId.value,
  4250. pVendorInfo->pVersionNumber->pOctetString,
  4251. pVendorInfo->pVersionNumber->wOctetStringLength);
  4252. }
  4253. }
  4254. if (pEndpointType->bIsTerminal)
  4255. {
  4256. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.bit_mask =
  4257. terminal_present;
  4258. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.terminal.bit_mask = 0;
  4259. }
  4260. if (pEndpointType->bIsGateway)
  4261. {
  4262. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.bit_mask =
  4263. gateway_present;
  4264. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.gateway.bit_mask = protocol_present;
  4265. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.gateway.protocol = &TempProtocol;
  4266. }
  4267. }
  4268. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.mc = 0;
  4269. UserInfo.h323_uu_pdu.h323_message_body.u.callProceeding.destinationInfo.undefinedNode = 0;
  4270. rc = Q931_Encode(pWorld,
  4271. (void *) &UserInfo,
  4272. H323_UserInformation_PDU,
  4273. ppEncodedBuf,
  4274. pdwEncodedLength);
  4275. if (ASN1_FAILED(rc))
  4276. {
  4277. ASSERT(FALSE);
  4278. return CS_SUBSYSTEM_FAILURE;
  4279. }
  4280. return CS_OK;
  4281. }
  4282. //-------------------------------------------------------------------------------------
  4283. //-------------------------------------------------------------------------------------
  4284. HRESULT
  4285. Q931FacilityEncodeASN(
  4286. PCC_NONSTANDARDDATA pNonStandardData,
  4287. CC_ADDR *AlternativeAddr,
  4288. BYTE bReason,
  4289. CC_CONFERENCEID *pConferenceID,
  4290. PCC_ALIASNAMES pAlternativeAliasList,
  4291. ASN1_CODER_INFO *pWorld,
  4292. BYTE **ppEncodedBuf,
  4293. DWORD *pdwEncodedLength)
  4294. {
  4295. int rc;
  4296. H323_UserInformation UserInfo;
  4297. *ppEncodedBuf = NULL;
  4298. *pdwEncodedLength = 0;
  4299. memset(&UserInfo, 0, sizeof(H323_UserInformation));
  4300. UserInfo.bit_mask = 0;
  4301. // make sure the user_data_present flag is turned off.
  4302. UserInfo.bit_mask &= (~user_data_present);
  4303. if (pNonStandardData)
  4304. {
  4305. UserInfo.h323_uu_pdu.bit_mask |= H323_UU_PDU_nnStndrdDt_present;
  4306. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice = h221NonStandard_chosen;
  4307. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode =
  4308. pNonStandardData->bCountryCode;
  4309. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension =
  4310. pNonStandardData->bExtension;
  4311. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode =
  4312. pNonStandardData->wManufacturerCode;
  4313. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length =
  4314. pNonStandardData->sData.wOctetStringLength;
  4315. UserInfo.h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value =
  4316. pNonStandardData->sData.pOctetString;
  4317. }
  4318. else
  4319. {
  4320. UserInfo.h323_uu_pdu.bit_mask &= (~H323_UU_PDU_nnStndrdDt_present);
  4321. }
  4322. UserInfo.h323_uu_pdu.h323_message_body.choice = facility_chosen;
  4323. UserInfo.h323_uu_pdu.h323_message_body.u.facility.protocolIdentifier = &ProtocolId1;
  4324. if (AlternativeAddr != NULL)
  4325. {
  4326. DWORD a = AlternativeAddr->Addr.IP_Binary.dwAddr;
  4327. UserInfo.h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.choice = ipAddress_chosen;
  4328. UserInfo.h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.length = 4;
  4329. UserInfo.h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.port =
  4330. AlternativeAddr->Addr.IP_Binary.wPort;
  4331. UserInfo.h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.value[0] =
  4332. ((BYTE *)&a)[3];
  4333. UserInfo.h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.value[1] =
  4334. ((BYTE *)&a)[2];
  4335. UserInfo.h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.value[2] =
  4336. ((BYTE *)&a)[1];
  4337. UserInfo.h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.value[3] =
  4338. ((BYTE *)&a)[0];
  4339. UserInfo.h323_uu_pdu.h323_message_body.u.facility.bit_mask |=
  4340. (alternativeAddress_present);
  4341. }
  4342. else
  4343. {
  4344. UserInfo.h323_uu_pdu.h323_message_body.u.facility.bit_mask &=
  4345. (~alternativeAddress_present);
  4346. }
  4347. if (pAlternativeAliasList)
  4348. {
  4349. CS_STATUS AliasResult = CS_OK;
  4350. AliasResult = AliasToSeqof((struct _seqof3 **)&(UserInfo.h323_uu_pdu.
  4351. h323_message_body.u.facility.alternativeAliasAddress), pAlternativeAliasList);
  4352. if (AliasResult != CS_OK)
  4353. {
  4354. return CS_NO_MEMORY;
  4355. }
  4356. UserInfo.h323_uu_pdu.h323_message_body.u.facility.bit_mask |=
  4357. (alternativeAliasAddress_present);
  4358. }
  4359. else
  4360. {
  4361. UserInfo.h323_uu_pdu.h323_message_body.u.facility.bit_mask &=
  4362. (~alternativeAliasAddress_present);
  4363. }
  4364. if (pConferenceID != NULL)
  4365. {
  4366. UserInfo.h323_uu_pdu.h323_message_body.u.facility.conferenceID.length =
  4367. sizeof(UserInfo.h323_uu_pdu.h323_message_body.u.facility.conferenceID.value);
  4368. memcpy(UserInfo.h323_uu_pdu.h323_message_body.u.facility.conferenceID.value,
  4369. pConferenceID->buffer,
  4370. UserInfo.h323_uu_pdu.h323_message_body.u.facility.conferenceID.length);
  4371. UserInfo.h323_uu_pdu.h323_message_body.u.facility.bit_mask |=
  4372. (conferenceID_present);
  4373. }
  4374. else
  4375. {
  4376. UserInfo.h323_uu_pdu.h323_message_body.u.facility.bit_mask &=
  4377. (~conferenceID_present);
  4378. }
  4379. switch (bReason)
  4380. {
  4381. case CC_REJECT_ROUTE_TO_GATEKEEPER:
  4382. UserInfo.h323_uu_pdu.h323_message_body.u.facility.reason.choice = routeCallToGatekeeper_chosen;
  4383. break;
  4384. case CC_REJECT_CALL_FORWARDED:
  4385. UserInfo.h323_uu_pdu.h323_message_body.u.facility.reason.choice = callForwarded_chosen;
  4386. break;
  4387. case CC_REJECT_ROUTE_TO_MC:
  4388. UserInfo.h323_uu_pdu.h323_message_body.u.facility.reason.choice = routeCallToMC_chosen;
  4389. break;
  4390. default:
  4391. UserInfo.h323_uu_pdu.h323_message_body.u.facility.reason.choice = RlsCmpltRsn_undfndRsn_chosen;
  4392. } // switch
  4393. rc = Q931_Encode(pWorld,
  4394. (void *) &UserInfo,
  4395. H323_UserInformation_PDU,
  4396. ppEncodedBuf,
  4397. pdwEncodedLength);
  4398. // Free the alias name structures from the UserInfo area.
  4399. FreeSeqof((struct _seqof3 *)UserInfo.h323_uu_pdu.h323_message_body.u.
  4400. facility.alternativeAliasAddress);
  4401. if (ASN1_FAILED(rc))
  4402. {
  4403. ASSERT(FALSE);
  4404. return CS_SUBSYSTEM_FAILURE;
  4405. }
  4406. return CS_OK;
  4407. }
  4408. //------------------------------------------------------------------------
  4409. //------------------------------------------------------------------------
  4410. BOOL
  4411. Q931ValidPduVersion(struct ObjectID_ *id)
  4412. {
  4413. // not sure what version checking to put here
  4414. #if 0
  4415. if ((id != NULL) && (id->value == 0) && (id->next != NULL) && (id->next->value <= 1))
  4416. {
  4417. return TRUE;
  4418. }
  4419. return FALSE;
  4420. #else
  4421. return TRUE;
  4422. #endif
  4423. }
  4424. //------------------------------------------------------------------------
  4425. //------------------------------------------------------------------------
  4426. HRESULT
  4427. Q931SetupParseASN(
  4428. ASN1_CODER_INFO *pWorld,
  4429. BYTE *pEncodedBuf,
  4430. DWORD dwEncodedLength,
  4431. Q931_SETUP_ASN *pParsedData)
  4432. {
  4433. int PDU = H323_UserInformation_PDU;
  4434. char *pDecodedBuf = NULL;
  4435. H323_UserInformation *pUserInfo;
  4436. struct ObjectID_ *id;
  4437. int Result;
  4438. if (pParsedData == NULL)
  4439. {
  4440. return CS_BAD_PARAM;
  4441. }
  4442. Result = Q931_Decode(pWorld,
  4443. (void **) &pDecodedBuf,
  4444. PDU,
  4445. pEncodedBuf,
  4446. dwEncodedLength);
  4447. if (ASN1_FAILED(Result) || (pDecodedBuf == NULL))
  4448. {
  4449. ASSERT(FALSE);
  4450. // trace and return an decoding error of some sort.
  4451. // Note: some values of Result should cause CS_SUBSYSTEM_FAILURE return.
  4452. return CS_BAD_PARAM;
  4453. }
  4454. // validate some basic things about the PDU...
  4455. pUserInfo = (H323_UserInformation *)pDecodedBuf;
  4456. // validate that this is a H323 PDU.
  4457. if (PDU != H323_UserInformation_PDU)
  4458. {
  4459. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4460. return CS_BAD_PARAM;
  4461. }
  4462. // validate that the PDU user-data uses ASN encoding.
  4463. if (((pUserInfo->bit_mask & user_data_present) != 0) &&
  4464. (pUserInfo->user_data.protocol_discriminator != USE_ASN1_ENCODING))
  4465. {
  4466. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4467. return CS_BAD_PARAM;
  4468. }
  4469. // validate that the PDU is H323 Setup information.
  4470. if (pUserInfo->h323_uu_pdu.h323_message_body.choice != setup_chosen)
  4471. {
  4472. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4473. return CS_BAD_PARAM;
  4474. }
  4475. id = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.protocolIdentifier;
  4476. if (!Q931ValidPduVersion(id))
  4477. {
  4478. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4479. return CS_INCOMPATIBLE_VERSION;
  4480. }
  4481. // make sure that the conference id is formed correctly.
  4482. if (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.conferenceID.length >
  4483. sizeof(pUserInfo->h323_uu_pdu.h323_message_body.u.setup.conferenceID.value))
  4484. {
  4485. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4486. return CS_BAD_PARAM;
  4487. }
  4488. #if 0
  4489. if (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.conferenceGoal.choice != create_chosen)
  4490. {
  4491. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4492. return CS_OPTION_NOT_IMPLEMENTED;
  4493. }
  4494. if (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.callType.choice != pointToPoint_chosen)
  4495. {
  4496. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4497. return CS_OPTION_NOT_IMPLEMENTED;
  4498. }
  4499. #endif
  4500. // parse the message contained in pUserInfo.
  4501. memset(pParsedData, 0, sizeof(Q931_SETUP_ASN));
  4502. pParsedData->SourceAddr.bMulticast = FALSE;
  4503. pParsedData->CallerAddr.bMulticast = FALSE;
  4504. pParsedData->CalleeDestAddr.bMulticast = FALSE;
  4505. pParsedData->CalleeAddr.bMulticast = FALSE;
  4506. // no validation of sourceInfo needed.
  4507. pParsedData->EndpointType.pVendorInfo = NULL;
  4508. if (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.bit_mask & (vendor_present))
  4509. {
  4510. pParsedData->EndpointType.pVendorInfo = &(pParsedData->VendorInfo);
  4511. pParsedData->VendorInfo.bCountryCode =
  4512. (BYTE)pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.vendor.t35CountryCode;
  4513. pParsedData->VendorInfo.bExtension =
  4514. (BYTE)pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.vendor.t35Extension;
  4515. pParsedData->VendorInfo.wManufacturerCode =
  4516. pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.vendor.manufacturerCode;
  4517. if (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.bit_mask & (productId_present))
  4518. {
  4519. pParsedData->VendorInfo.pProductNumber = Malloc(sizeof(CC_OCTETSTRING));
  4520. if (pParsedData->VendorInfo.pProductNumber == NULL)
  4521. {
  4522. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4523. return CS_NO_MEMORY;
  4524. }
  4525. pParsedData->VendorInfo.pProductNumber->wOctetStringLength = (WORD)
  4526. min(pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.productId.length,
  4527. CC_MAX_PRODUCT_LENGTH - 1);
  4528. memcpy(pParsedData->bufProductValue,
  4529. pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.productId.value,
  4530. pParsedData->VendorInfo.pProductNumber->wOctetStringLength);
  4531. pParsedData->bufProductValue[pParsedData->VendorInfo.pProductNumber->wOctetStringLength] = '\0';
  4532. pParsedData->VendorInfo.pProductNumber->pOctetString = pParsedData->bufProductValue;
  4533. }
  4534. if (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.bit_mask & (versionId_present))
  4535. {
  4536. pParsedData->VendorInfo.pVersionNumber = Malloc(sizeof(CC_OCTETSTRING));
  4537. if (pParsedData->VendorInfo.pVersionNumber == NULL)
  4538. {
  4539. Free(pParsedData->VendorInfo.pProductNumber);
  4540. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4541. return CS_NO_MEMORY;
  4542. }
  4543. pParsedData->VendorInfo.pVersionNumber->wOctetStringLength = (WORD)
  4544. min(pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.versionId.length,
  4545. CC_MAX_VERSION_LENGTH - 1);
  4546. memcpy(pParsedData->bufVersionValue,
  4547. pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.vendor.versionId.value,
  4548. pParsedData->VendorInfo.pVersionNumber->wOctetStringLength);
  4549. pParsedData->bufVersionValue[pParsedData->VendorInfo.pVersionNumber->wOctetStringLength] = '\0';
  4550. pParsedData->VendorInfo.pVersionNumber->pOctetString = pParsedData->bufVersionValue;
  4551. }
  4552. }
  4553. pParsedData->EndpointType.bIsTerminal = FALSE;
  4554. if (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.bit_mask & (terminal_present))
  4555. {
  4556. pParsedData->EndpointType.bIsTerminal = TRUE;
  4557. }
  4558. pParsedData->EndpointType.bIsGateway = FALSE;
  4559. if (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceInfo.bit_mask & (gateway_present))
  4560. {
  4561. pParsedData->EndpointType.bIsGateway = TRUE;
  4562. }
  4563. if ((pUserInfo->h323_uu_pdu.bit_mask & H323_UU_PDU_nnStndrdDt_present) != 0)
  4564. {
  4565. pParsedData->NonStandardDataPresent = TRUE;
  4566. if (pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice ==
  4567. h221NonStandard_chosen)
  4568. {
  4569. pParsedData->NonStandardData.bCountryCode =
  4570. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode);
  4571. pParsedData->NonStandardData.bExtension =
  4572. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension);
  4573. pParsedData->NonStandardData.wManufacturerCode =
  4574. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode;
  4575. }
  4576. pParsedData->NonStandardData.sData.wOctetStringLength = (WORD)
  4577. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length;
  4578. pParsedData->NonStandardData.sData.pOctetString =
  4579. (BYTE *)Malloc(pParsedData->NonStandardData.sData.wOctetStringLength);
  4580. if (pParsedData->NonStandardData.sData.pOctetString == NULL)
  4581. {
  4582. Free(pParsedData->VendorInfo.pProductNumber);
  4583. Free(pParsedData->VendorInfo.pVersionNumber);
  4584. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4585. return CS_NO_MEMORY;
  4586. }
  4587. memcpy(pParsedData->NonStandardData.sData.pOctetString,
  4588. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value,
  4589. pParsedData->NonStandardData.sData.wOctetStringLength);
  4590. }
  4591. else
  4592. {
  4593. pParsedData->NonStandardDataPresent = FALSE;
  4594. }
  4595. //RMO. ignore the h245 address.
  4596. {
  4597. CS_STATUS AliasResult = CS_OK;
  4598. // parse the sourceAddress aliases here...
  4599. AliasResult = SeqofToAlias(&(pParsedData->pCallerAliasList),
  4600. (struct _seqof3 *)pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceAddress);
  4601. if (AliasResult != CS_OK)
  4602. {
  4603. if (pParsedData->NonStandardData.sData.pOctetString != NULL)
  4604. Free(pParsedData->NonStandardData.sData.pOctetString);
  4605. Free(pParsedData->VendorInfo.pProductNumber);
  4606. Free(pParsedData->VendorInfo.pVersionNumber);
  4607. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4608. return CS_NO_MEMORY;
  4609. }
  4610. // parse the destinationAddress aliases here...
  4611. AliasResult = SeqofToAlias(&(pParsedData->pCalleeAliasList),
  4612. (struct _seqof3 *)pUserInfo->h323_uu_pdu.h323_message_body.u.setup.destinationAddress);
  4613. if (AliasResult != CS_OK)
  4614. {
  4615. Q931FreeAliasNames(pParsedData->pCallerAliasList);
  4616. if (pParsedData->NonStandardData.sData.pOctetString != NULL)
  4617. Free(pParsedData->NonStandardData.sData.pOctetString);
  4618. pParsedData->pCallerAliasList = NULL;
  4619. Free(pParsedData->VendorInfo.pProductNumber);
  4620. Free(pParsedData->VendorInfo.pVersionNumber);
  4621. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4622. return CS_NO_MEMORY;
  4623. }
  4624. // parse the destExtraCallInfo aliases here...
  4625. AliasResult = SeqofToAlias(&(pParsedData->pExtraAliasList),
  4626. (struct _seqof3 *)pUserInfo->h323_uu_pdu.h323_message_body.u.setup.destExtraCallInfo);
  4627. if (AliasResult != CS_OK)
  4628. {
  4629. Q931FreeAliasNames(pParsedData->pCalleeAliasList);
  4630. Q931FreeAliasNames(pParsedData->pCallerAliasList);
  4631. if (pParsedData->NonStandardData.sData.pOctetString != NULL)
  4632. Free(pParsedData->NonStandardData.sData.pOctetString);
  4633. pParsedData->pCallerAliasList = NULL;
  4634. Free(pParsedData->VendorInfo.pProductNumber);
  4635. Free(pParsedData->VendorInfo.pVersionNumber);
  4636. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4637. return CS_NO_MEMORY;
  4638. }
  4639. // parse the remoteExtensionAddress aliases here...
  4640. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.setup.bit_mask &
  4641. remoteExtensionAddress_present) != 0)
  4642. {
  4643. AliasResult = Q931AliasAddrToAliasItem(&(pParsedData->pExtensionAliasItem),
  4644. &(pUserInfo->h323_uu_pdu.h323_message_body.u.setup.remoteExtensionAddress));
  4645. if (AliasResult != CS_OK)
  4646. {
  4647. Q931FreeAliasNames(pParsedData->pExtraAliasList);
  4648. Q931FreeAliasNames(pParsedData->pCalleeAliasList);
  4649. Q931FreeAliasNames(pParsedData->pCallerAliasList);
  4650. pParsedData->pCallerAliasList = NULL;
  4651. if (pParsedData->NonStandardData.sData.pOctetString != NULL)
  4652. Free(pParsedData->NonStandardData.sData.pOctetString);
  4653. Free(pParsedData->VendorInfo.pProductNumber);
  4654. Free(pParsedData->VendorInfo.pVersionNumber);
  4655. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4656. return CS_NO_MEMORY;
  4657. }
  4658. }
  4659. }
  4660. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.setup.bit_mask &
  4661. destCallSignalAddress_present) != 0)
  4662. {
  4663. BYTE *a = (BYTE *)(&(pParsedData->CalleeDestAddr.Addr.IP_Binary.dwAddr));
  4664. pParsedData->CalleeDestAddr.nAddrType = CC_IP_BINARY;
  4665. pParsedData->CalleeDestAddr.Addr.IP_Binary.wPort =
  4666. pUserInfo->h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.port;
  4667. a[3] = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.value[0];
  4668. a[2] = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.value[1];
  4669. a[1] = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.value[2];
  4670. a[0] = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.destCallSignalAddress.u.ipAddress.ip.value[3];
  4671. pParsedData->CalleeDestAddrPresent = TRUE;
  4672. }
  4673. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.setup.bit_mask &
  4674. sourceCallSignalAddress_present) != 0)
  4675. {
  4676. BYTE *a = (BYTE *)(&(pParsedData->SourceAddr.Addr.IP_Binary.dwAddr));
  4677. pParsedData->SourceAddr.nAddrType = CC_IP_BINARY;
  4678. pParsedData->SourceAddr.Addr.IP_Binary.wPort =
  4679. pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.port;
  4680. a[3] = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.value[0];
  4681. a[2] = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.value[1];
  4682. a[1] = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.value[2];
  4683. a[0] = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.sourceCallSignalAddress.u.ipAddress.ip.value[3];
  4684. pParsedData->SourceAddrPresent = TRUE;
  4685. }
  4686. pParsedData->bCallerIsMC = pUserInfo->h323_uu_pdu.h323_message_body.u.setup.activeMC;
  4687. memcpy(pParsedData->ConferenceID.buffer,
  4688. pUserInfo->h323_uu_pdu.h323_message_body.u.setup.conferenceID.value,
  4689. pUserInfo->h323_uu_pdu.h323_message_body.u.setup.conferenceID.length);
  4690. switch (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.conferenceGoal.choice)
  4691. {
  4692. case invite_chosen:
  4693. pParsedData->wGoal = CSG_INVITE;
  4694. break;
  4695. case join_chosen:
  4696. pParsedData->wGoal = CSG_JOIN;
  4697. break;
  4698. default:
  4699. pParsedData->wGoal = CSG_CREATE;
  4700. } // switch
  4701. switch (pUserInfo->h323_uu_pdu.h323_message_body.u.setup.callType.choice)
  4702. {
  4703. case oneToN_chosen:
  4704. pParsedData->wCallType = CC_CALLTYPE_1_N;
  4705. break;
  4706. case nToOne_chosen:
  4707. pParsedData->wCallType = CC_CALLTYPE_N_1;
  4708. break;
  4709. case nToN_chosen:
  4710. pParsedData->wCallType = CC_CALLTYPE_N_N;
  4711. break;
  4712. default:
  4713. pParsedData->wCallType = CC_CALLTYPE_PT_PT;
  4714. } // switch
  4715. // Free the PDU data.
  4716. Result = freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4717. ASSERT(ASN1_SUCCEEDED(Result));
  4718. return CS_OK;
  4719. }
  4720. //------------------------------------------------------------------------
  4721. //------------------------------------------------------------------------
  4722. HRESULT
  4723. Q931ReleaseCompleteParseASN(
  4724. ASN1_CODER_INFO *pWorld,
  4725. BYTE *pEncodedBuf,
  4726. DWORD dwEncodedLength,
  4727. Q931_RELEASE_COMPLETE_ASN *pParsedData)
  4728. {
  4729. int PDU = H323_UserInformation_PDU;
  4730. char *pDecodedBuf = NULL;
  4731. H323_UserInformation *pUserInfo;
  4732. struct ObjectID_ *id;
  4733. int Result;
  4734. if (pParsedData == NULL)
  4735. {
  4736. return CS_BAD_PARAM;
  4737. }
  4738. Result = Q931_Decode(pWorld,
  4739. (void **) &pDecodedBuf,
  4740. PDU,
  4741. pEncodedBuf,
  4742. dwEncodedLength);
  4743. if (ASN1_FAILED(Result) || (pDecodedBuf == NULL))
  4744. {
  4745. ASSERT(FALSE);
  4746. // trace and return an decoding error of some sort.
  4747. // Note: some values of Result should cause CS_SUBSYSTEM_FAILURE return.
  4748. return CS_BAD_PARAM;
  4749. }
  4750. // validate some basic things about the PDU...
  4751. pUserInfo = (H323_UserInformation *)pDecodedBuf;
  4752. // validate that this is a H323 PDU.
  4753. if (PDU != H323_UserInformation_PDU)
  4754. {
  4755. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4756. return CS_BAD_PARAM;
  4757. }
  4758. // validate that the PDU user-data uses ASN encoding.
  4759. if (((pUserInfo->bit_mask & user_data_present) != 0) &&
  4760. (pUserInfo->user_data.protocol_discriminator != USE_ASN1_ENCODING))
  4761. {
  4762. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4763. return CS_BAD_PARAM;
  4764. }
  4765. // validate that the PDU is H323 Release Complete information.
  4766. if (pUserInfo->h323_uu_pdu.h323_message_body.choice != releaseComplete_chosen)
  4767. {
  4768. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4769. return CS_BAD_PARAM;
  4770. }
  4771. id = pUserInfo->h323_uu_pdu.h323_message_body.u.releaseComplete.protocolIdentifier;
  4772. if (!Q931ValidPduVersion(id))
  4773. {
  4774. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4775. return CS_INCOMPATIBLE_VERSION;
  4776. }
  4777. // parse the message contained in pUserInfo.
  4778. memset(pParsedData, 0, sizeof(Q931_RELEASE_COMPLETE_ASN));
  4779. if ((pUserInfo->h323_uu_pdu.bit_mask & H323_UU_PDU_nnStndrdDt_present) != 0)
  4780. {
  4781. pParsedData->NonStandardDataPresent = TRUE;
  4782. if (pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice ==
  4783. h221NonStandard_chosen)
  4784. {
  4785. pParsedData->NonStandardData.bCountryCode =
  4786. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode);
  4787. pParsedData->NonStandardData.bExtension =
  4788. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension);
  4789. pParsedData->NonStandardData.wManufacturerCode =
  4790. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode;
  4791. }
  4792. pParsedData->NonStandardData.sData.wOctetStringLength = (WORD)
  4793. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length;
  4794. pParsedData->NonStandardData.sData.pOctetString =
  4795. (BYTE *)Malloc(pParsedData->NonStandardData.sData.wOctetStringLength);
  4796. if (pParsedData->NonStandardData.sData.pOctetString == NULL)
  4797. {
  4798. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4799. return CS_NO_MEMORY;
  4800. }
  4801. memcpy(pParsedData->NonStandardData.sData.pOctetString,
  4802. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value,
  4803. pParsedData->NonStandardData.sData.wOctetStringLength); }
  4804. else
  4805. {
  4806. pParsedData->NonStandardDataPresent = FALSE;
  4807. }
  4808. if (pUserInfo->h323_uu_pdu.h323_message_body.u.releaseComplete.bit_mask & reason_present)
  4809. {
  4810. switch (pUserInfo->h323_uu_pdu.h323_message_body.u.releaseComplete.reason.choice)
  4811. {
  4812. case noBandwidth_chosen:
  4813. pParsedData->bReason = CC_REJECT_NO_BANDWIDTH;
  4814. break;
  4815. case gatekeeperResources_chosen:
  4816. pParsedData->bReason = CC_REJECT_GATEKEEPER_RESOURCES;
  4817. break;
  4818. case unreachableDestination_chosen:
  4819. pParsedData->bReason = CC_REJECT_UNREACHABLE_DESTINATION;
  4820. break;
  4821. case destinationRejection_chosen:
  4822. pParsedData->bReason = CC_REJECT_DESTINATION_REJECTION;
  4823. break;
  4824. case invalidRevision_chosen:
  4825. pParsedData->bReason = CC_REJECT_INVALID_REVISION;
  4826. break;
  4827. case noPermission_chosen:
  4828. pParsedData->bReason = CC_REJECT_NO_PERMISSION;
  4829. break;
  4830. case unreachableGatekeeper_chosen:
  4831. pParsedData->bReason = CC_REJECT_UNREACHABLE_GATEKEEPER;
  4832. break;
  4833. case gatewayResources_chosen:
  4834. pParsedData->bReason = CC_REJECT_GATEWAY_RESOURCES;
  4835. break;
  4836. case badFormatAddress_chosen:
  4837. pParsedData->bReason = CC_REJECT_BAD_FORMAT_ADDRESS;
  4838. break;
  4839. case adaptiveBusy_chosen:
  4840. pParsedData->bReason = CC_REJECT_ADAPTIVE_BUSY;
  4841. break;
  4842. case inConf_chosen:
  4843. pParsedData->bReason = CC_REJECT_IN_CONF;
  4844. break;
  4845. case facilityCallDeflection_chosen:
  4846. pParsedData->bReason = CC_REJECT_CALL_DEFLECTION;
  4847. break;
  4848. default:
  4849. pParsedData->bReason = CC_REJECT_UNDEFINED_REASON;
  4850. } // switch
  4851. }
  4852. else
  4853. {
  4854. pParsedData->bReason = CC_REJECT_UNDEFINED_REASON;
  4855. }
  4856. // Free the PDU data.
  4857. Result = freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4858. ASSERT(ASN1_SUCCEEDED(Result));
  4859. return CS_OK;
  4860. }
  4861. //------------------------------------------------------------------------
  4862. //------------------------------------------------------------------------
  4863. HRESULT
  4864. Q931ConnectParseASN(
  4865. ASN1_CODER_INFO *pWorld,
  4866. BYTE *pEncodedBuf,
  4867. DWORD dwEncodedLength,
  4868. Q931_CONNECT_ASN *pParsedData)
  4869. {
  4870. int PDU = H323_UserInformation_PDU;
  4871. char *pDecodedBuf = NULL;
  4872. H323_UserInformation *pUserInfo;
  4873. struct ObjectID_ *id;
  4874. int Result;
  4875. if (pParsedData == NULL)
  4876. {
  4877. return CS_BAD_PARAM;
  4878. }
  4879. Result = Q931_Decode(pWorld,
  4880. (void **) &pDecodedBuf,
  4881. PDU,
  4882. pEncodedBuf,
  4883. dwEncodedLength);
  4884. if (ASN1_FAILED(Result) || (pDecodedBuf == NULL))
  4885. {
  4886. ASSERT(FALSE);
  4887. // trace and return an decoding error of some sort.
  4888. // Note: some values of Result should cause CS_SUBSYSTEM_FAILURE return.
  4889. return CS_BAD_PARAM;
  4890. }
  4891. // validate some basic things about the PDU...
  4892. pUserInfo = (H323_UserInformation *)pDecodedBuf;
  4893. // validate that this is a H323 PDU.
  4894. if (PDU != H323_UserInformation_PDU)
  4895. {
  4896. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4897. return CS_BAD_PARAM;
  4898. }
  4899. // validate that the PDU user-data uses ASN encoding.
  4900. if (((pUserInfo->bit_mask & user_data_present) != 0) &&
  4901. (pUserInfo->user_data.protocol_discriminator != USE_ASN1_ENCODING))
  4902. {
  4903. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4904. return CS_BAD_PARAM;
  4905. }
  4906. // validate that the PDU is H323 Connect information.
  4907. if (pUserInfo->h323_uu_pdu.h323_message_body.choice != connect_chosen)
  4908. {
  4909. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4910. return CS_BAD_PARAM;
  4911. }
  4912. id = pUserInfo->h323_uu_pdu.h323_message_body.u.connect.protocolIdentifier;
  4913. if (!Q931ValidPduVersion(id))
  4914. {
  4915. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4916. return CS_INCOMPATIBLE_VERSION;
  4917. }
  4918. // make sure that the conference id is formed correctly.
  4919. if (pUserInfo->h323_uu_pdu.h323_message_body.u.connect.conferenceID.length >
  4920. sizeof(pUserInfo->h323_uu_pdu.h323_message_body.u.connect.conferenceID.value))
  4921. {
  4922. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4923. return CS_BAD_PARAM;
  4924. }
  4925. // parse the message contained in pUserInfo.
  4926. memset(pParsedData, 0, sizeof(Q931_CONNECT_ASN));
  4927. pParsedData->h245Addr.bMulticast = FALSE;
  4928. if ((pUserInfo->h323_uu_pdu.bit_mask & H323_UU_PDU_nnStndrdDt_present) != 0)
  4929. {
  4930. pParsedData->NonStandardDataPresent = TRUE;
  4931. if (pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice ==
  4932. h221NonStandard_chosen)
  4933. {
  4934. pParsedData->NonStandardData.bCountryCode =
  4935. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode);
  4936. pParsedData->NonStandardData.bExtension =
  4937. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension);
  4938. pParsedData->NonStandardData.wManufacturerCode =
  4939. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode;
  4940. }
  4941. pParsedData->NonStandardData.sData.wOctetStringLength = (WORD)
  4942. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length;
  4943. pParsedData->NonStandardData.sData.pOctetString =
  4944. (BYTE *)Malloc(pParsedData->NonStandardData.sData.wOctetStringLength);
  4945. if (pParsedData->NonStandardData.sData.pOctetString == NULL)
  4946. {
  4947. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4948. return CS_NO_MEMORY;
  4949. }
  4950. memcpy(pParsedData->NonStandardData.sData.pOctetString,
  4951. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value,
  4952. pParsedData->NonStandardData.sData.wOctetStringLength);
  4953. }
  4954. else
  4955. {
  4956. pParsedData->NonStandardDataPresent = FALSE;
  4957. }
  4958. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.connect.bit_mask &
  4959. Cnnct_UUIE_h245Address_present) != 0)
  4960. {
  4961. BYTE *a = (BYTE *)(&(pParsedData->h245Addr.Addr.IP_Binary.dwAddr));
  4962. pParsedData->h245Addr.nAddrType = CC_IP_BINARY;
  4963. pParsedData->h245Addr.Addr.IP_Binary.wPort =
  4964. pUserInfo->h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.port;
  4965. a[3] = pUserInfo->h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.value[0];
  4966. a[2] = pUserInfo->h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.value[1];
  4967. a[1] = pUserInfo->h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.value[2];
  4968. a[0] = pUserInfo->h323_uu_pdu.h323_message_body.u.connect.Cnnct_UUIE_h245Address.u.ipAddress.ip.value[3];
  4969. pParsedData->h245AddrPresent = TRUE;
  4970. }
  4971. else
  4972. {
  4973. pParsedData->h245AddrPresent = FALSE;
  4974. }
  4975. // no validation of destinationInfo needed.
  4976. pParsedData->EndpointType.pVendorInfo = NULL;
  4977. if (pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.bit_mask & (vendor_present))
  4978. {
  4979. pParsedData->EndpointType.pVendorInfo = &(pParsedData->VendorInfo);
  4980. pParsedData->VendorInfo.bCountryCode =
  4981. (BYTE)pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.vendor.t35CountryCode;
  4982. pParsedData->VendorInfo.bExtension =
  4983. (BYTE)pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.vendor.t35Extension;
  4984. pParsedData->VendorInfo.wManufacturerCode =
  4985. pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.vendor.manufacturerCode;
  4986. if (pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.bit_mask & (productId_present))
  4987. {
  4988. pParsedData->VendorInfo.pProductNumber = Malloc(sizeof(CC_OCTETSTRING));
  4989. if (pParsedData->VendorInfo.pProductNumber == NULL)
  4990. {
  4991. if (pParsedData->NonStandardData.sData.pOctetString != NULL)
  4992. Free(pParsedData->NonStandardData.sData.pOctetString);
  4993. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  4994. return CS_NO_MEMORY;
  4995. }
  4996. pParsedData->VendorInfo.pProductNumber->wOctetStringLength = (WORD)
  4997. min(pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.productId.length,
  4998. CC_MAX_PRODUCT_LENGTH - 1);
  4999. memcpy(pParsedData->bufProductValue,
  5000. pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.productId.value,
  5001. pParsedData->VendorInfo.pProductNumber->wOctetStringLength);
  5002. pParsedData->bufProductValue[pParsedData->VendorInfo.pProductNumber->wOctetStringLength] = '\0';
  5003. pParsedData->VendorInfo.pProductNumber->pOctetString = pParsedData->bufProductValue;
  5004. }
  5005. if (pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.bit_mask & (versionId_present))
  5006. {
  5007. pParsedData->VendorInfo.pVersionNumber = Malloc(sizeof(CC_OCTETSTRING));
  5008. if (pParsedData->VendorInfo.pVersionNumber == NULL)
  5009. {
  5010. if (pParsedData->NonStandardData.sData.pOctetString != NULL)
  5011. Free(pParsedData->NonStandardData.sData.pOctetString);
  5012. Free(pParsedData->VendorInfo.pProductNumber);
  5013. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5014. return CS_NO_MEMORY;
  5015. }
  5016. pParsedData->VendorInfo.pVersionNumber->wOctetStringLength = (WORD)
  5017. min(pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.versionId.length,
  5018. CC_MAX_VERSION_LENGTH - 1);
  5019. memcpy(pParsedData->bufVersionValue,
  5020. pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.vendor.versionId.value,
  5021. pParsedData->VendorInfo.pVersionNumber->wOctetStringLength);
  5022. pParsedData->bufVersionValue[pParsedData->VendorInfo.pVersionNumber->wOctetStringLength] = '\0';
  5023. pParsedData->VendorInfo.pVersionNumber->pOctetString = pParsedData->bufVersionValue;
  5024. }
  5025. }
  5026. pParsedData->EndpointType.bIsTerminal = FALSE;
  5027. if (pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.bit_mask & (terminal_present))
  5028. {
  5029. pParsedData->EndpointType.bIsTerminal = TRUE;
  5030. }
  5031. pParsedData->EndpointType.bIsGateway = FALSE;
  5032. if (pUserInfo->h323_uu_pdu.h323_message_body.u.connect.destinationInfo.bit_mask & (gateway_present))
  5033. {
  5034. pParsedData->EndpointType.bIsGateway = TRUE;
  5035. }
  5036. memcpy(pParsedData->ConferenceID.buffer,
  5037. pUserInfo->h323_uu_pdu.h323_message_body.u.connect.conferenceID.value,
  5038. pUserInfo->h323_uu_pdu.h323_message_body.u.connect.conferenceID.length);
  5039. // Free the PDU data.
  5040. Result = freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5041. ASSERT(ASN1_SUCCEEDED(Result));
  5042. return CS_OK;
  5043. }
  5044. //------------------------------------------------------------------------
  5045. //------------------------------------------------------------------------
  5046. HRESULT
  5047. Q931AlertingParseASN(
  5048. ASN1_CODER_INFO *pWorld,
  5049. BYTE *pEncodedBuf,
  5050. DWORD dwEncodedLength,
  5051. Q931_ALERTING_ASN *pParsedData)
  5052. {
  5053. int PDU = H323_UserInformation_PDU;
  5054. char *pDecodedBuf = NULL;
  5055. H323_UserInformation *pUserInfo;
  5056. struct ObjectID_ *id;
  5057. int Result;
  5058. if (pParsedData == NULL)
  5059. {
  5060. return CS_BAD_PARAM;
  5061. }
  5062. Result = Q931_Decode(pWorld,
  5063. (void **) &pDecodedBuf,
  5064. PDU,
  5065. pEncodedBuf,
  5066. dwEncodedLength);
  5067. if (ASN1_FAILED(Result) || (pDecodedBuf == NULL))
  5068. {
  5069. ASSERT(FALSE);
  5070. // trace and return an decoding error of some sort.
  5071. // Note: some values of Result should cause CS_SUBSYSTEM_FAILURE return.
  5072. return CS_BAD_PARAM;
  5073. }
  5074. // validate some basic things about the PDU...
  5075. pUserInfo = (H323_UserInformation *)pDecodedBuf;
  5076. // validate that this is a H323 PDU.
  5077. if (PDU != H323_UserInformation_PDU)
  5078. {
  5079. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5080. return CS_BAD_PARAM;
  5081. }
  5082. // validate that the PDU user-data uses ASN encoding.
  5083. if (((pUserInfo->bit_mask & user_data_present) != 0) &&
  5084. (pUserInfo->user_data.protocol_discriminator != USE_ASN1_ENCODING))
  5085. {
  5086. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5087. return CS_BAD_PARAM;
  5088. }
  5089. // validate that the PDU is H323 Alerting information.
  5090. if (pUserInfo->h323_uu_pdu.h323_message_body.choice != alerting_chosen)
  5091. {
  5092. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5093. return CS_BAD_PARAM;
  5094. }
  5095. id = pUserInfo->h323_uu_pdu.h323_message_body.u.alerting.protocolIdentifier;
  5096. if (!Q931ValidPduVersion(id))
  5097. {
  5098. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5099. return CS_INCOMPATIBLE_VERSION;
  5100. }
  5101. // parse the message contained in pUserInfo.
  5102. memset(pParsedData, 0, sizeof(Q931_ALERTING_ASN));
  5103. pParsedData->h245Addr.bMulticast = FALSE;
  5104. if ((pUserInfo->h323_uu_pdu.bit_mask & H323_UU_PDU_nnStndrdDt_present) != 0)
  5105. {
  5106. pParsedData->NonStandardDataPresent = TRUE;
  5107. if (pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice ==
  5108. h221NonStandard_chosen)
  5109. {
  5110. pParsedData->NonStandardData.bCountryCode =
  5111. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode);
  5112. pParsedData->NonStandardData.bExtension =
  5113. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension);
  5114. pParsedData->NonStandardData.wManufacturerCode =
  5115. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode;
  5116. }
  5117. pParsedData->NonStandardData.sData.wOctetStringLength = (WORD)
  5118. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length;
  5119. pParsedData->NonStandardData.sData.pOctetString =
  5120. (BYTE *)Malloc(pParsedData->NonStandardData.sData.wOctetStringLength);
  5121. if (pParsedData->NonStandardData.sData.pOctetString == NULL)
  5122. {
  5123. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5124. return CS_NO_MEMORY;
  5125. }
  5126. memcpy(pParsedData->NonStandardData.sData.pOctetString,
  5127. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value,
  5128. pParsedData->NonStandardData.sData.wOctetStringLength);
  5129. }
  5130. else
  5131. {
  5132. pParsedData->NonStandardDataPresent = FALSE;
  5133. }
  5134. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.alerting.bit_mask &
  5135. CPg_UUIE_h245Addrss_present) != 0)
  5136. {
  5137. BYTE *a = (BYTE *)(&(pParsedData->h245Addr.Addr.IP_Binary.dwAddr));
  5138. pParsedData->h245Addr.nAddrType = CC_IP_BINARY;
  5139. pParsedData->h245Addr.Addr.IP_Binary.wPort =
  5140. pUserInfo->h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.port;
  5141. a[3] = pUserInfo->h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[0];
  5142. a[2] = pUserInfo->h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[1];
  5143. a[1] = pUserInfo->h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[2];
  5144. a[0] = pUserInfo->h323_uu_pdu.h323_message_body.u.alerting.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[3];
  5145. }
  5146. //RMO. ignore the destinationInfo field.
  5147. // Free the PDU data.
  5148. Result = freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5149. ASSERT(ASN1_SUCCEEDED(Result));
  5150. return CS_OK;
  5151. }
  5152. //------------------------------------------------------------------------
  5153. //------------------------------------------------------------------------
  5154. HRESULT
  5155. Q931ProceedingParseASN(
  5156. ASN1_CODER_INFO *pWorld,
  5157. BYTE *pEncodedBuf,
  5158. DWORD dwEncodedLength,
  5159. Q931_CALL_PROCEEDING_ASN *pParsedData)
  5160. {
  5161. int PDU = H323_UserInformation_PDU;
  5162. char *pDecodedBuf = NULL;
  5163. H323_UserInformation *pUserInfo;
  5164. struct ObjectID_ *id;
  5165. int Result;
  5166. if (pParsedData == NULL)
  5167. {
  5168. return CS_BAD_PARAM;
  5169. }
  5170. Result = Q931_Decode(pWorld,
  5171. (void **) &pDecodedBuf,
  5172. PDU,
  5173. pEncodedBuf,
  5174. dwEncodedLength);
  5175. if (ASN1_FAILED(Result) || (pDecodedBuf == NULL))
  5176. {
  5177. ASSERT(FALSE);
  5178. // trace and return an decoding error of some sort.
  5179. // Note: some values of Result should cause CS_SUBSYSTEM_FAILURE return.
  5180. return CS_BAD_PARAM;
  5181. }
  5182. // validate some basic things about the PDU...
  5183. pUserInfo = (H323_UserInformation *)pDecodedBuf;
  5184. // validate that this is a H323 PDU.
  5185. if (PDU != H323_UserInformation_PDU)
  5186. {
  5187. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5188. return CS_BAD_PARAM;
  5189. }
  5190. // validate that the PDU user-data uses ASN encoding.
  5191. if (((pUserInfo->bit_mask & user_data_present) != 0) &&
  5192. (pUserInfo->user_data.protocol_discriminator != USE_ASN1_ENCODING))
  5193. {
  5194. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5195. return CS_BAD_PARAM;
  5196. }
  5197. // validate that the PDU is H323 Call Proceeding information.
  5198. if (pUserInfo->h323_uu_pdu.h323_message_body.choice != callProceeding_chosen)
  5199. {
  5200. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5201. return CS_BAD_PARAM;
  5202. }
  5203. id = pUserInfo->h323_uu_pdu.h323_message_body.u.callProceeding.protocolIdentifier;
  5204. if (!Q931ValidPduVersion(id))
  5205. {
  5206. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5207. return CS_INCOMPATIBLE_VERSION;
  5208. }
  5209. // parse the message contained in pUserInfo.
  5210. memset(pParsedData, 0, sizeof(Q931_CALL_PROCEEDING_ASN));
  5211. pParsedData->h245Addr.bMulticast = FALSE;
  5212. if ((pUserInfo->h323_uu_pdu.bit_mask & H323_UU_PDU_nnStndrdDt_present) != 0)
  5213. {
  5214. pParsedData->NonStandardDataPresent = TRUE;
  5215. if (pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice ==
  5216. h221NonStandard_chosen)
  5217. {
  5218. pParsedData->NonStandardData.bCountryCode =
  5219. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode);
  5220. pParsedData->NonStandardData.bExtension =
  5221. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension);
  5222. pParsedData->NonStandardData.wManufacturerCode =
  5223. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode;
  5224. }
  5225. pParsedData->NonStandardData.sData.wOctetStringLength = (WORD)
  5226. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length;
  5227. pParsedData->NonStandardData.sData.pOctetString =
  5228. (BYTE *)Malloc(pParsedData->NonStandardData.sData.wOctetStringLength);
  5229. if (pParsedData->NonStandardData.sData.pOctetString == NULL)
  5230. {
  5231. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5232. return CS_NO_MEMORY;
  5233. }
  5234. memcpy(pParsedData->NonStandardData.sData.pOctetString,
  5235. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value,
  5236. pParsedData->NonStandardData.sData.wOctetStringLength);
  5237. }
  5238. else
  5239. {
  5240. pParsedData->NonStandardDataPresent = FALSE;
  5241. }
  5242. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.callProceeding.bit_mask &
  5243. CPg_UUIE_h245Addrss_present) != 0)
  5244. {
  5245. BYTE *a = (BYTE *)(&(pParsedData->h245Addr.Addr.IP_Binary.dwAddr));
  5246. pParsedData->h245Addr.nAddrType = CC_IP_BINARY;
  5247. pParsedData->h245Addr.Addr.IP_Binary.wPort =
  5248. pUserInfo->h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.port;
  5249. a[3] = pUserInfo->h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[0];
  5250. a[2] = pUserInfo->h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[1];
  5251. a[1] = pUserInfo->h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[2];
  5252. a[0] = pUserInfo->h323_uu_pdu.h323_message_body.u.callProceeding.CPg_UUIE_h245Addrss.u.ipAddress.ip.value[3];
  5253. }
  5254. //RMO. ignore the destinationInfo field.
  5255. // Free the PDU data.
  5256. Result = freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5257. ASSERT(ASN1_SUCCEEDED(Result));
  5258. return CS_OK;
  5259. }
  5260. //------------------------------------------------------------------------
  5261. //------------------------------------------------------------------------
  5262. HRESULT
  5263. Q931FacilityParseASN(
  5264. ASN1_CODER_INFO *pWorld,
  5265. BYTE *pEncodedBuf,
  5266. DWORD dwEncodedLength,
  5267. Q931_FACILITY_ASN *pParsedData)
  5268. {
  5269. int PDU = H323_UserInformation_PDU;
  5270. char *pDecodedBuf = NULL;
  5271. H323_UserInformation *pUserInfo;
  5272. int Result;
  5273. if (pParsedData == NULL)
  5274. {
  5275. return CS_BAD_PARAM;
  5276. }
  5277. Result = Q931_Decode(pWorld,
  5278. (void **) &pDecodedBuf,
  5279. PDU,
  5280. pEncodedBuf,
  5281. dwEncodedLength);
  5282. if (ASN1_FAILED(Result) || (pDecodedBuf == NULL))
  5283. {
  5284. ASSERT(FALSE);
  5285. // trace and return an decoding error of some sort.
  5286. // Note: some values of Result should cause CS_SUBSYSTEM_FAILURE return.
  5287. return CS_BAD_PARAM;
  5288. }
  5289. // validate some basic things about the PDU...
  5290. pUserInfo = (H323_UserInformation *)pDecodedBuf;
  5291. // validate that this is a H323 PDU.
  5292. if (PDU != H323_UserInformation_PDU)
  5293. {
  5294. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5295. return CS_BAD_PARAM;
  5296. }
  5297. // validate that the PDU user-data uses ASN encoding.
  5298. if (((pUserInfo->bit_mask & user_data_present) != 0) &&
  5299. (pUserInfo->user_data.protocol_discriminator != USE_ASN1_ENCODING))
  5300. {
  5301. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5302. return CS_BAD_PARAM;
  5303. }
  5304. // validate that the PDU is H323 Facility information.
  5305. if (pUserInfo->h323_uu_pdu.h323_message_body.choice != facility_chosen)
  5306. {
  5307. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5308. return CS_BAD_PARAM;
  5309. }
  5310. {
  5311. struct ObjectID_ *id;
  5312. id = pUserInfo->h323_uu_pdu.h323_message_body.u.facility.protocolIdentifier;
  5313. if (!Q931ValidPduVersion(id))
  5314. {
  5315. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5316. return CS_INCOMPATIBLE_VERSION;
  5317. }
  5318. }
  5319. // if there is a conference id, make sure that it is formed correctly.
  5320. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.facility.bit_mask &
  5321. conferenceID_present) != 0)
  5322. {
  5323. if (pUserInfo->h323_uu_pdu.h323_message_body.u.facility.conferenceID.length >
  5324. sizeof(pUserInfo->h323_uu_pdu.h323_message_body.u.facility.conferenceID.value))
  5325. {
  5326. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5327. return CS_BAD_PARAM;
  5328. }
  5329. }
  5330. // parse the message contained in pUserInfo.
  5331. memset(pParsedData, 0, sizeof(Q931_FACILITY_ASN));
  5332. pParsedData->AlternativeAddr.bMulticast = FALSE;
  5333. if ((pUserInfo->h323_uu_pdu.bit_mask & H323_UU_PDU_nnStndrdDt_present) != 0)
  5334. {
  5335. pParsedData->NonStandardDataPresent = TRUE;
  5336. if (pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.choice ==
  5337. h221NonStandard_chosen)
  5338. {
  5339. pParsedData->NonStandardData.bCountryCode =
  5340. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35CountryCode);
  5341. pParsedData->NonStandardData.bExtension =
  5342. (BYTE)(pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.t35Extension);
  5343. pParsedData->NonStandardData.wManufacturerCode =
  5344. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.nonStandardIdentifier.u.h221NonStandard.manufacturerCode;
  5345. }
  5346. pParsedData->NonStandardData.sData.wOctetStringLength = (WORD)
  5347. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.length;
  5348. pParsedData->NonStandardData.sData.pOctetString =
  5349. (BYTE *)Malloc(pParsedData->NonStandardData.sData.wOctetStringLength);
  5350. if (pParsedData->NonStandardData.sData.pOctetString == NULL)
  5351. {
  5352. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5353. return CS_NO_MEMORY;
  5354. }
  5355. memcpy(pParsedData->NonStandardData.sData.pOctetString,
  5356. pUserInfo->h323_uu_pdu.H323_UU_PDU_nnStndrdDt.data.value,
  5357. pParsedData->NonStandardData.sData.wOctetStringLength);
  5358. }
  5359. else
  5360. {
  5361. pParsedData->NonStandardDataPresent = FALSE;
  5362. }
  5363. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.facility.bit_mask &
  5364. alternativeAddress_present) != 0)
  5365. {
  5366. BYTE *a = (BYTE *)(&(pParsedData->AlternativeAddr.Addr.IP_Binary.dwAddr));
  5367. pParsedData->AlternativeAddr.nAddrType = CC_IP_BINARY;
  5368. pParsedData->AlternativeAddr.Addr.IP_Binary.wPort =
  5369. pUserInfo->h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.port;
  5370. a[3] = pUserInfo->h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.value[0];
  5371. a[2] = pUserInfo->h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.value[1];
  5372. a[1] = pUserInfo->h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.value[2];
  5373. a[0] = pUserInfo->h323_uu_pdu.h323_message_body.u.facility.alternativeAddress.u.ipAddress.ip.value[3];
  5374. }
  5375. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.facility.bit_mask &
  5376. alternativeAliasAddress_present) != 0)
  5377. {
  5378. CS_STATUS AliasResult = CS_OK;
  5379. // parse the sourceAddress aliases here...
  5380. AliasResult = SeqofToAlias(&(pParsedData->pAlternativeAliasList),
  5381. (struct _seqof3 *)pUserInfo->h323_uu_pdu.h323_message_body.u.facility.alternativeAliasAddress);
  5382. if (AliasResult != CS_OK)
  5383. {
  5384. freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5385. return CS_NO_MEMORY;
  5386. }
  5387. }
  5388. if ((pUserInfo->h323_uu_pdu.h323_message_body.u.facility.bit_mask &
  5389. conferenceID_present) != 0)
  5390. {
  5391. memcpy(pParsedData->ConferenceID.buffer,
  5392. pUserInfo->h323_uu_pdu.h323_message_body.u.facility.conferenceID.value,
  5393. pUserInfo->h323_uu_pdu.h323_message_body.u.facility.conferenceID.length);
  5394. pParsedData->ConferenceIDPresent = TRUE;
  5395. }
  5396. switch (pUserInfo->h323_uu_pdu.h323_message_body.u.facility.reason.choice)
  5397. {
  5398. case routeCallToGatekeeper_chosen:
  5399. pParsedData->bReason = CC_REJECT_ROUTE_TO_GATEKEEPER;
  5400. break;
  5401. case callForwarded_chosen:
  5402. pParsedData->bReason = CC_REJECT_CALL_FORWARDED;
  5403. break;
  5404. case routeCallToMC_chosen:
  5405. pParsedData->bReason = CC_REJECT_ROUTE_TO_MC;
  5406. break;
  5407. default:
  5408. pParsedData->bReason = CC_REJECT_UNDEFINED_REASON;
  5409. } // switch
  5410. // Free the PDU data.
  5411. Result = freePDU(pWorld, PDU, pDecodedBuf, q931asn);
  5412. ASSERT(ASN1_SUCCEEDED(Result));
  5413. return CS_OK;
  5414. }
  5415. // THE FOLLOWING IS ADDED FOR TELES ASN.1 INTEGRATION
  5416. int Q931_InitModule(void)
  5417. {
  5418. Q931ASN_Module_Startup();
  5419. return (Q931ASN_Module != NULL) ? ASN1_SUCCESS : ASN1_ERR_MEMORY;
  5420. }
  5421. int Q931_TermModule(void)
  5422. {
  5423. Q931ASN_Module_Cleanup();
  5424. return ASN1_SUCCESS;
  5425. }
  5426. int Q931_InitWorld(ASN1_CODER_INFO *pWorld)
  5427. {
  5428. int rc;
  5429. ZeroMemory(pWorld, sizeof(*pWorld));
  5430. if (Q931ASN_Module == NULL)
  5431. {
  5432. return ASN1_ERR_BADARGS;
  5433. }
  5434. rc = ASN1_CreateEncoder(
  5435. Q931ASN_Module, // ptr to mdule
  5436. &(pWorld->pEncInfo), // ptr to encoder info
  5437. NULL, // buffer ptr
  5438. 0, // buffer size
  5439. NULL); // parent ptr
  5440. if (rc == ASN1_SUCCESS)
  5441. {
  5442. ASSERT(pWorld->pEncInfo != NULL);
  5443. rc = ASN1_CreateDecoder(
  5444. Q931ASN_Module, // ptr to mdule
  5445. &(pWorld->pDecInfo), // ptr to decoder info
  5446. NULL, // buffer ptr
  5447. 0, // buffer size
  5448. NULL); // parent ptr
  5449. ASSERT(pWorld->pDecInfo != NULL);
  5450. }
  5451. if (rc != ASN1_SUCCESS)
  5452. {
  5453. Q931_TermWorld(pWorld);
  5454. }
  5455. return rc;
  5456. }
  5457. int Q931_TermWorld(ASN1_CODER_INFO *pWorld)
  5458. {
  5459. if (Q931ASN_Module == NULL)
  5460. {
  5461. return ASN1_ERR_BADARGS;
  5462. }
  5463. ASN1_CloseEncoder(pWorld->pEncInfo);
  5464. ASN1_CloseDecoder(pWorld->pDecInfo);
  5465. ZeroMemory(pWorld, sizeof(*pWorld));
  5466. return ASN1_SUCCESS;
  5467. }
  5468. int Q931_Encode(ASN1_CODER_INFO *pWorld, void *pStruct, int nPDU, BYTE **ppEncoded, DWORD *pcbEncodedSize)
  5469. {
  5470. ASN1encoding_t pEncInfo = pWorld->pEncInfo;
  5471. int rc = ASN1_Encode(
  5472. pEncInfo, // ptr to encoder info
  5473. pStruct, // pdu data structure
  5474. nPDU, // pdu id
  5475. ASN1ENCODE_ALLOCATEBUFFER, // flags
  5476. NULL, // do not provide buffer
  5477. 0); // buffer size if provided
  5478. if (ASN1_SUCCEEDED(rc))
  5479. {
  5480. ASSERT(rc == ASN1_SUCCESS);
  5481. *pcbEncodedSize = pEncInfo->len; // len of encoded data in buffer
  5482. *ppEncoded = pEncInfo->buf; // buffer to encode into
  5483. }
  5484. else
  5485. {
  5486. ASSERT(FALSE);
  5487. *pcbEncodedSize = 0;
  5488. *ppEncoded = NULL;
  5489. }
  5490. return rc;
  5491. }
  5492. int Q931_Decode(ASN1_CODER_INFO *pWorld, void **ppStruct, int nPDU, BYTE *pEncoded, DWORD cbEncodedSize)
  5493. {
  5494. ASN1decoding_t pDecInfo = pWorld->pDecInfo;
  5495. int rc = ASN1_Decode(
  5496. pDecInfo, // ptr to encoder info
  5497. ppStruct, // pdu data structure
  5498. nPDU, // pdu id
  5499. ASN1DECODE_SETBUFFER, // flags
  5500. pEncoded, // do not provide buffer
  5501. cbEncodedSize); // buffer size if provided
  5502. if (ASN1_SUCCEEDED(rc))
  5503. {
  5504. ASSERT(rc == ASN1_SUCCESS);
  5505. }
  5506. else
  5507. {
  5508. ASSERT(FALSE);
  5509. *ppStruct = NULL;
  5510. }
  5511. return rc;
  5512. }