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.

2498 lines
66 KiB

  1. /*++
  2. Copyright (c) 1999 Microsoft Corporation
  3. Module Name:
  4. q931pdu.cpp
  5. Abstract:
  6. Encode/decode/transport routines for Q931/H450 messages.
  7. Author:
  8. Nikhil Bobde (NikhilB)
  9. Revision History:
  10. --*/
  11. #include "globals.h"
  12. #include "q931obj.h"
  13. #include "line.h"
  14. #include "q931pdu.h"
  15. #include "ras.h"
  16. //PARSE ROUTINES
  17. //------------------------------------------------------------------------------
  18. // Parse and return a single octet encoded value, See Q931 section 4.5.1.
  19. //
  20. // Parameters:
  21. // pbBuffer Pointer to a descriptor of the buffer
  22. // containing the length and a pointer
  23. // to the raw bytes of the input stream.
  24. // bIdent Pointer to space for field identifier
  25. // Value Pointer to space for field value
  26. //------------------------------------------------------------------------------
  27. HRESULT
  28. ParseSingleOctetType1(
  29. PBUFFERDESCR pBuf,
  30. BYTE * bIdent,
  31. BYTE * Value
  32. )
  33. {
  34. // There has to be at least 1 byte in the stream to be
  35. // able to parse the single octet value
  36. if (pBuf->dwLength < 1)
  37. {
  38. return E_INVALIDARG;
  39. }
  40. // low bits (0, 1, 2, 3) of the byte are the value
  41. *Value = (BYTE)(*pBuf->pbBuffer & TYPE1VALUEMASK);
  42. // higher bits (4, 5, 6) are the identifier. bit 7 is always 1,
  43. // and is not returned as part of the id.
  44. *bIdent = (BYTE)((*pBuf->pbBuffer & 0x70) >> 4);
  45. pBuf->pbBuffer++;
  46. pBuf->dwLength--;
  47. return S_OK;
  48. }
  49. //------------------------------------------------------------------------------
  50. // Parse and return a single octet encoded value, See Q931 section 4.5.1.
  51. // This octet has no value, only an identifier.
  52. //
  53. // Parameters:
  54. // pbBuffer Pointer to a descriptor of the buffer containing the
  55. // length and a pointer to the raw bytes of the input stream.
  56. // bIdent Pointer to space for field identifier
  57. //------------------------------------------------------------------------------
  58. HRESULT
  59. ParseSingleOctetType2(
  60. PBUFFERDESCR pBuf,
  61. BYTE * bIdent
  62. )
  63. {
  64. // There has to be at least 1 byte in the stream to be
  65. // able to parse the single octet value
  66. if (pBuf->dwLength < 1)
  67. {
  68. return E_INVALIDARG;
  69. }
  70. // low 7 bits of the byte are the identifier
  71. *bIdent = (BYTE)(*pBuf->pbBuffer & 0x7f);
  72. pBuf->pbBuffer++;
  73. pBuf->dwLength--;
  74. return S_OK;
  75. }
  76. //------------------------------------------------------------------------------
  77. // Parse and return a variable length Q931 field see Q931 section 4.5.1.
  78. //
  79. // Parameters :
  80. // pbBuffer Pointer to a descriptor of the buffer
  81. // containing the length and a pointer
  82. // to the raw bytes of the input stream.
  83. // bIdent Pointer to space for field identifier
  84. // dwLength Pointer to space for the length
  85. // pbContents Pointer to space for the bytes of the field
  86. //------------------------------------------------------------------------------
  87. HRESULT
  88. ParseVariableOctet(
  89. PBUFFERDESCR pBuf,
  90. BYTE * dwLength,
  91. BYTE * pbContents
  92. )
  93. {
  94. // There has to be at least 2 bytes in order just to get
  95. // the length and the identifier
  96. // able to parse the single octet value
  97. if (pBuf->dwLength < 2)
  98. {
  99. return E_INVALIDARG;
  100. }
  101. //Increment the ident byte
  102. pBuf->pbBuffer++;
  103. pBuf->dwLength--;
  104. // The next byte is the length
  105. *dwLength = *pBuf->pbBuffer;
  106. pBuf->pbBuffer++;
  107. pBuf->dwLength--;
  108. if (pBuf->dwLength < *dwLength)
  109. {
  110. return E_INVALIDARG;
  111. }
  112. CopyMemory( pbContents, pBuf->pbBuffer, *dwLength );
  113. pBuf->pbBuffer += *dwLength;
  114. pBuf->dwLength -= *dwLength;
  115. return S_OK;
  116. }
  117. //------------------------------------------------------------------------------
  118. // Parse and return a variable length Q931 field see Q931 section 4.5.1.
  119. //------------------------------------------------------------------------------
  120. HRESULT
  121. ParseVariableASN(
  122. PBUFFERDESCR pBuf,
  123. BYTE *bIdent,
  124. BYTE *ProtocolDiscriminator,
  125. PUSERUSERIE pUserUserIE
  126. )
  127. {
  128. pUserUserIE -> wUserInfoLen = 0;
  129. // There has to be at least 4 bytes for the IE identifier,
  130. // the contents length, and the protocol discriminator (1 + 2 + 1).
  131. if (pBuf->dwLength < 4)
  132. {
  133. return E_INVALIDARG;
  134. }
  135. // low 7 bits of the first byte are the identifier
  136. *bIdent= (BYTE)(*pBuf->pbBuffer & 0x7f);
  137. pBuf->pbBuffer++;
  138. pBuf->dwLength--;
  139. // The next 2 bytes are the length
  140. pUserUserIE -> wUserInfoLen = *(pBuf->pbBuffer);
  141. pBuf->pbBuffer++;
  142. pUserUserIE -> wUserInfoLen =
  143. (WORD)(((pUserUserIE -> wUserInfoLen) << 8) + *pBuf->pbBuffer);
  144. pBuf->pbBuffer++;
  145. pBuf->dwLength -= 2;
  146. if (pBuf->dwLength < pUserUserIE -> wUserInfoLen )
  147. {
  148. return E_INVALIDARG;
  149. }
  150. // The next byte is the protocol discriminator.
  151. *ProtocolDiscriminator = *pBuf->pbBuffer;
  152. pBuf->pbBuffer++;
  153. pBuf->dwLength--;
  154. if( pUserUserIE -> wUserInfoLen > 0 )
  155. {
  156. pUserUserIE -> wUserInfoLen--;
  157. }
  158. CopyMemory( pUserUserIE -> pbUserInfo,
  159. pBuf->pbBuffer,
  160. pUserUserIE -> wUserInfoLen );
  161. pBuf->pbBuffer += pUserUserIE -> wUserInfoLen;
  162. pBuf->dwLength -= pUserUserIE -> wUserInfoLen;
  163. return S_OK;
  164. }
  165. //------------------------------------------------------------------------------
  166. // Get the identifier of the next field from the buffer and
  167. // return it. The buffer pointer is not incremented, To
  168. // parse the field and extract its values, the above functions
  169. // should be used. See Q931 table 4-3 for the encodings of the
  170. // identifiers.
  171. //
  172. // Parameters:
  173. // pbBuffer Pointer to the buffer space
  174. //------------------------------------------------------------------------------
  175. BYTE
  176. GetNextIdent(
  177. void *pbBuffer
  178. )
  179. {
  180. FIELDIDENTTYPE bIdent;
  181. // Extract the first byte from the buffer
  182. bIdent= (*(FIELDIDENTTYPE *)pbBuffer);
  183. // This value can be returned as the identifier as long
  184. // as it is not a single Octet - Type 1 element.
  185. // Those items must have the value removed from them
  186. // before they can be returned.
  187. if ((bIdent & 0x80) && ((bIdent & TYPE1IDENTMASK) != 0xA0))
  188. {
  189. return (BYTE)(bIdent & TYPE1IDENTMASK);
  190. }
  191. return bIdent;
  192. }
  193. //------------------------------------------------------------------------------
  194. // Parse and return a protocol discriminator. See Q931 section 4.2.
  195. // The octet pointed to by **pbBuffer is the protocol Discriminator.
  196. //
  197. // Parameters:
  198. // pbBuffer Pointer to a descriptor of the buffer
  199. // containing the length and a pointer
  200. // to the raw bytes of the input stream.
  201. // Discrim Pointer to space for discriminator
  202. //------------------------------------------------------------------------------
  203. HRESULT
  204. ParseProtocolDiscriminator(
  205. PBUFFERDESCR pBuf,
  206. PDTYPE *Discrim)
  207. {
  208. // There has to be at least enough bytes left in the
  209. // string for the operation
  210. if (pBuf->dwLength < sizeof(PDTYPE))
  211. {
  212. return E_INVALIDARG;
  213. }
  214. *Discrim = *(PDTYPE *)pBuf->pbBuffer;
  215. if (*Discrim != Q931PDVALUE)
  216. {
  217. return E_INVALIDARG;
  218. }
  219. pBuf->pbBuffer += sizeof(PDTYPE);
  220. pBuf->dwLength -= sizeof(PDTYPE);
  221. return S_OK;
  222. }
  223. //------------------------------------------------------------------------------
  224. // Parse and return a variable length Q931 call reference see
  225. // Q931 section 4.3.
  226. //
  227. // Parameters:
  228. // pbBuffer Pointer to a descriptor of the buffer
  229. // containing the length and a pointer
  230. // to the raw bytes of the input stream.
  231. // dwLength Pointer to space for the length
  232. // pbContents Pointer to space for the bytes of the field
  233. //------------------------------------------------------------------------------
  234. HRESULT
  235. ParseCallReference(
  236. PBUFFERDESCR pBuf,
  237. CRTYPE * wCallRef
  238. )
  239. {
  240. register int indexI;
  241. BYTE dwLength;
  242. // There has to be at least enough bytes left in the
  243. // string for the length byte
  244. if( pBuf->dwLength < 1 )
  245. {
  246. return E_INVALIDARG;
  247. }
  248. // low 4 bits of the first byte are the length.
  249. // the rest of the bits are zeroes.
  250. dwLength = (BYTE)(*pBuf->pbBuffer & 0x0f);
  251. if( dwLength != sizeof(WORD) )
  252. {
  253. return E_INVALIDARG;
  254. }
  255. pBuf->pbBuffer++;
  256. pBuf->dwLength--;
  257. // There has to be at least enough bytes left in the
  258. // string for the operation
  259. if (pBuf->dwLength < dwLength)
  260. {
  261. return E_INVALIDARG;
  262. }
  263. *wCallRef = 0; // length can be 0, so initialize here first...
  264. for (indexI = 0; indexI < dwLength; indexI++)
  265. {
  266. if (indexI < sizeof(CRTYPE))
  267. {
  268. // Copy the bytes out of the rest of the buffer
  269. *wCallRef = (WORD)((*wCallRef << 8) +
  270. *pBuf->pbBuffer);
  271. }
  272. pBuf->pbBuffer++;
  273. pBuf->dwLength--;
  274. }
  275. // note: the high order bit of the value represents callee relationship.
  276. return S_OK;
  277. }
  278. //------------------------------------------------------------------------------
  279. // Parse and return a message type. See Q931 section 4.4.
  280. // The octet pointed to by **pbBuffer is the message type.
  281. //
  282. // Parameters:
  283. // pbBuffer Pointer to a descriptor of the buffer
  284. // containing the length and a pointer
  285. // to the raw bytes of the input stream.
  286. // MessageType Pointer to space for message type
  287. //------------------------------------------------------------------------------
  288. HRESULT
  289. ParseMessageType(
  290. PBUFFERDESCR pBuf,
  291. MESSAGEIDTYPE * MessageType
  292. )
  293. {
  294. // There has to be at least enough bytes left in the
  295. // string for the operation
  296. if (pBuf->dwLength < sizeof(MESSAGEIDTYPE))
  297. {
  298. return E_INVALIDARG;
  299. }
  300. *MessageType = (BYTE)(*((MESSAGEIDTYPE *)pBuf->pbBuffer) & MESSAGETYPEMASK);
  301. if( ISVALIDQ931MESSAGE(*MessageType) == FALSE )
  302. {
  303. return E_INVALIDARG;
  304. }
  305. pBuf->pbBuffer += sizeof(MESSAGEIDTYPE);
  306. pBuf->dwLength -= sizeof(MESSAGEIDTYPE);
  307. return S_OK;
  308. }
  309. //------------------------------------------------------------------------------
  310. // Parse an optional facility ie field
  311. //
  312. // Parameters:
  313. // pbBuffer Pointer to a descriptor of the buffer
  314. // containing the length and a pointer
  315. // to the raw bytes of the input stream.
  316. // pFieldStruct Pointer to space for parsed facility
  317. // information.
  318. //------------------------------------------------------------------------------
  319. HRESULT
  320. ParseFacility(
  321. PBUFFERDESCR pBuf,
  322. PFACILITYIE pFieldStruct
  323. )
  324. {
  325. HRESULT hr;
  326. memset( (PVOID)pFieldStruct, 0, sizeof(FACILITYIE));
  327. pFieldStruct->fPresent = FALSE;
  328. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  329. &pFieldStruct->pbContents[0]);
  330. if( FAILED(hr) )
  331. {
  332. return hr;
  333. }
  334. if (pFieldStruct->dwLength > 0)
  335. {
  336. pFieldStruct->fPresent = TRUE;
  337. }
  338. return S_OK;
  339. }
  340. //------------------------------------------------------------------------------
  341. // Parse an optional bearer capability field
  342. //
  343. // Parameters:
  344. // pbBuffer Pointer to a descriptor of the buffer
  345. // containing the length and a pointer
  346. // to the raw bytes of the input stream.
  347. // pFieldStruct Pointer to space for parsed bearer capability
  348. // information.
  349. //------------------------------------------------------------------------------
  350. HRESULT
  351. ParseBearerCapability(
  352. PBUFFERDESCR pBuf,
  353. PBEARERCAPIE pFieldStruct)
  354. {
  355. HRESULT hr;
  356. memset( (PVOID)pFieldStruct, 0, sizeof(BEARERCAPIE));
  357. pFieldStruct->fPresent = FALSE;
  358. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  359. &pFieldStruct->pbContents[0]);
  360. if( FAILED(hr) )
  361. {
  362. return hr;
  363. }
  364. if (pFieldStruct->dwLength > 0)
  365. {
  366. pFieldStruct->fPresent = TRUE;
  367. }
  368. return S_OK;
  369. }
  370. //------------------------------------------------------------------------------
  371. // Parse an optional cause field
  372. //
  373. // Parameters:
  374. // pbBuffer Pointer to a descriptor of the buffer
  375. // containing the length and a pointer
  376. // to the raw bytes of the input stream.
  377. // pFieldStruct Pointer to space for parsed cause
  378. // information.
  379. //------------------------------------------------------------------------------
  380. HRESULT
  381. ParseCause(
  382. PBUFFERDESCR pBuf,
  383. PCAUSEIE pFieldStruct)
  384. {
  385. HRESULT hr;
  386. memset( (PVOID)pFieldStruct, 0, sizeof(CAUSEIE));
  387. pFieldStruct->fPresent = FALSE;
  388. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  389. &pFieldStruct->pbContents[0]);
  390. if( FAILED(hr) )
  391. {
  392. return hr;
  393. }
  394. if (pFieldStruct->dwLength > 0)
  395. {
  396. pFieldStruct->fPresent = TRUE;
  397. }
  398. return S_OK;
  399. }
  400. //------------------------------------------------------------------------------
  401. // Parse an optional call state field
  402. //
  403. // Parameters:
  404. // pbBuffer Pointer to a descriptor of the buffer
  405. // containing the length and a pointer
  406. // to the raw bytes of the input stream.
  407. // pFieldStruct Pointer to space for parsed call state
  408. // information.
  409. //------------------------------------------------------------------------------
  410. HRESULT
  411. ParseCallState(
  412. PBUFFERDESCR pBuf,
  413. PCALLSTATEIE pFieldStruct)
  414. {
  415. memset( (PVOID)pFieldStruct, 0, sizeof(CALLSTATEIE));
  416. pFieldStruct->fPresent = FALSE;
  417. HRESULT hr;
  418. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  419. &pFieldStruct->pbContents[0]);
  420. if( FAILED(hr) )
  421. {
  422. return hr;
  423. }
  424. if (pFieldStruct->dwLength > 0)
  425. {
  426. pFieldStruct->fPresent = TRUE;
  427. }
  428. return S_OK;
  429. }
  430. //------------------------------------------------------------------------------
  431. // Parse an optional channel identification field
  432. //
  433. // Parameters:
  434. // pbBuffer Pointer to a descriptor of the buffer
  435. // containing the length and a pointer
  436. // to the raw bytes of the input stream.
  437. // pFieldStruct Pointer to space for parsed channel identity
  438. // information.
  439. //------------------------------------------------------------------------------
  440. HRESULT
  441. ParseChannelIdentification(
  442. PBUFFERDESCR pBuf,
  443. PCHANIDENTIE pFieldStruct)
  444. {
  445. memset( (PVOID)pFieldStruct, 0, sizeof(CHANIDENTIE));
  446. pFieldStruct->fPresent = FALSE;
  447. HRESULT hr;
  448. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  449. &pFieldStruct->pbContents[0]);
  450. if( FAILED(hr) )
  451. {
  452. return hr;
  453. }
  454. if (pFieldStruct->dwLength > 0)
  455. {
  456. pFieldStruct->fPresent = TRUE;
  457. }
  458. return S_OK;
  459. }
  460. //------------------------------------------------------------------------------
  461. // Parse an optional progress indication field
  462. //
  463. // Parameters:
  464. // pbBuffer Pointer to a descriptor of the buffer
  465. // containing the length and a pointer
  466. // to the raw bytes of the input stream.
  467. // pFieldStruct Pointer to space for parsed progress
  468. // information.
  469. //------------------------------------------------------------------------------
  470. HRESULT
  471. ParseProgress(
  472. PBUFFERDESCR pBuf,
  473. PPROGRESSIE pFieldStruct)
  474. {
  475. memset( (PVOID)pFieldStruct, 0, sizeof(PROGRESSIE));
  476. pFieldStruct->fPresent = FALSE;
  477. HRESULT hr;
  478. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  479. &pFieldStruct->pbContents[0]);
  480. if( FAILED(hr) )
  481. {
  482. return hr;
  483. }
  484. if (pFieldStruct->dwLength > 0)
  485. {
  486. pFieldStruct->fPresent = TRUE;
  487. }
  488. return S_OK;
  489. }
  490. //------------------------------------------------------------------------------
  491. // Parse an optional network specific facilities field
  492. //
  493. // Parameters:
  494. // pbBuffer Pointer to a descriptor of the buffer
  495. // containing the length and a pointer
  496. // to the raw bytes of the input stream.
  497. // pFieldStruct Pointer to space for parsed network facitlities
  498. // information.
  499. //------------------------------------------------------------------------------
  500. HRESULT
  501. ParseNetworkSpec(
  502. PBUFFERDESCR pBuf,
  503. PNETWORKIE pFieldStruct)
  504. {
  505. memset( (PVOID)pFieldStruct, 0, sizeof(NETWORKIE));
  506. pFieldStruct->fPresent = FALSE;
  507. HRESULT hr;
  508. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  509. &pFieldStruct->pbContents[0]);
  510. if( FAILED(hr) )
  511. {
  512. return hr;
  513. }
  514. if (pFieldStruct->dwLength > 0)
  515. {
  516. pFieldStruct->fPresent = TRUE;
  517. }
  518. return S_OK;
  519. }
  520. //------------------------------------------------------------------------------
  521. // Parse an optional notification indicator field
  522. //
  523. // Parameters:
  524. // pbBuffer Pointer to a descriptor of the buffer
  525. // containing the length and a pointer
  526. // to the raw bytes of the input stream.
  527. // pFieldStruct Pointer to space for parse notification indicator
  528. // information.
  529. //------------------------------------------------------------------------------
  530. HRESULT
  531. ParseNotificationIndicator(
  532. PBUFFERDESCR pBuf,
  533. PNOTIFICATIONINDIE pFieldStruct)
  534. {
  535. memset( (PVOID)pFieldStruct, 0, sizeof(NOTIFICATIONINDIE));
  536. pFieldStruct->fPresent = FALSE;
  537. if (GetNextIdent(pBuf->pbBuffer) == IDENT_NOTIFICATION)
  538. {
  539. HRESULT hr;
  540. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  541. &pFieldStruct->pbContents[0]);
  542. if( FAILED(hr) )
  543. {
  544. return hr;
  545. }
  546. if (pFieldStruct->dwLength > 0)
  547. {
  548. pFieldStruct->fPresent = TRUE;
  549. }
  550. }
  551. return S_OK;
  552. }
  553. //------------------------------------------------------------------------------
  554. // Parse an optional display field
  555. //
  556. // Parameters:
  557. // pbBuffer Pointer to a descriptor of the buffer
  558. // containing the length and a pointer
  559. // to the raw bytes of the input stream.
  560. // pFieldStruct Pointer to space for parsed display
  561. // information.
  562. //------------------------------------------------------------------------------
  563. HRESULT
  564. ParseDisplay(
  565. PBUFFERDESCR pBuf,
  566. PDISPLAYIE pFieldStruct)
  567. {
  568. HRESULT hr;
  569. memset( (PVOID)pFieldStruct, 0, sizeof(DISPLAYIE));
  570. pFieldStruct->fPresent = FALSE;
  571. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  572. &pFieldStruct->pbContents[0]);
  573. if( FAILED(hr) )
  574. {
  575. return hr;
  576. }
  577. if (pFieldStruct->dwLength > 0)
  578. {
  579. pFieldStruct->fPresent = TRUE;
  580. }
  581. return S_OK;
  582. }
  583. HRESULT
  584. ParseDate(
  585. PBUFFERDESCR pBuf,
  586. PDATEIE pFieldStruct)
  587. {
  588. HRESULT hr;
  589. memset( (PVOID)pFieldStruct, 0, sizeof(DATEIE));
  590. pFieldStruct->fPresent = FALSE;
  591. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  592. &pFieldStruct->pbContents[0]);
  593. if( FAILED(hr) )
  594. {
  595. return hr;
  596. }
  597. if (pFieldStruct->dwLength > 0)
  598. {
  599. pFieldStruct->fPresent = TRUE;
  600. }
  601. return S_OK;
  602. }
  603. //------------------------------------------------------------------------------
  604. // Parse an optional keypad field
  605. //
  606. // Parameters:
  607. // pbBuffer Pointer to a descriptor of the buffer
  608. // containing the length and a pointer
  609. // to the raw bytes of the input stream.
  610. // pFieldStruct Pointer to space for parsed keypad
  611. // information.
  612. //------------------------------------------------------------------------------
  613. HRESULT
  614. ParseKeypad(
  615. PBUFFERDESCR pBuf,
  616. PKEYPADIE pFieldStruct)
  617. {
  618. HRESULT hr;
  619. memset( (PVOID)pFieldStruct, 0, sizeof(KEYPADIE));
  620. pFieldStruct->fPresent = FALSE;
  621. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  622. &pFieldStruct->pbContents[0]);
  623. if( FAILED(hr) )
  624. {
  625. return hr;
  626. }
  627. if (pFieldStruct->dwLength > 0)
  628. {
  629. pFieldStruct->fPresent = TRUE;
  630. }
  631. return S_OK;
  632. }
  633. //------------------------------------------------------------------------------
  634. // Parse an optional signal field
  635. //
  636. // Parameters:
  637. // pbBuffer Pointer to a descriptor of the buffer
  638. // containing the length and a pointer
  639. // to the raw bytes of the input stream.
  640. // pFieldStruct Pointer to space for parsed signal
  641. // information.
  642. //------------------------------------------------------------------------------
  643. HRESULT
  644. ParseSignal(
  645. PBUFFERDESCR pBuf,
  646. PSIGNALIE pFieldStruct)
  647. {
  648. HRESULT hr;
  649. memset( (PVOID)pFieldStruct, 0, sizeof(SIGNALIE));
  650. pFieldStruct->fPresent = FALSE;
  651. hr = ParseVariableOctet(pBuf,
  652. &pFieldStruct->dwLength, &pFieldStruct->pbContents[0]);
  653. if( FAILED(hr) )
  654. {
  655. return hr;
  656. }
  657. if (pFieldStruct->dwLength > 0)
  658. {
  659. pFieldStruct->fPresent = TRUE;
  660. }
  661. return S_OK;
  662. }
  663. //------------------------------------------------------------------------------
  664. // Parse an optional information rate field
  665. //
  666. // Parameters:
  667. // pbBuffer Pointer to a descriptor of the buffer
  668. // containing the length and a pointer
  669. // to the raw bytes of the input stream.
  670. // pFieldStruct Pointer to space for parsed information rate
  671. // information.
  672. //------------------------------------------------------------------------------
  673. HRESULT
  674. ParseInformationRate(
  675. PBUFFERDESCR pBuf,
  676. PINFORATEIE pFieldStruct)
  677. {
  678. HRESULT hr;
  679. memset( (PVOID)pFieldStruct, 0, sizeof(INFORATEIE));
  680. pFieldStruct->fPresent = FALSE;
  681. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  682. &pFieldStruct->pbContents[0]);
  683. if( FAILED(hr) )
  684. {
  685. return hr;
  686. }
  687. if (pFieldStruct->dwLength > 0)
  688. {
  689. pFieldStruct->fPresent = TRUE;
  690. }
  691. return S_OK;
  692. }
  693. //------------------------------------------------------------------------------
  694. // Parse an optional calling party number field
  695. //
  696. // Parameters:
  697. // pbBuffer Pointer to a descriptor of the buffer
  698. // containing the length and a pointer
  699. // to the raw bytes of the input stream.
  700. // pFieldStruct Pointer to space for parsed
  701. // information.
  702. //------------------------------------------------------------------------------
  703. HRESULT
  704. ParseCallingPartyNumber(
  705. PBUFFERDESCR pBuf,
  706. PCALLINGNUMBERIE pFieldStruct)
  707. {
  708. HRESULT hr;
  709. memset( (PVOID)pFieldStruct, 0, sizeof(CALLINGNUMBERIE));
  710. pFieldStruct->fPresent = FALSE;
  711. hr = ParseVariableOctet(pBuf,
  712. &pFieldStruct->dwLength, &pFieldStruct->pbContents[0]);
  713. if( FAILED(hr) )
  714. {
  715. return hr;
  716. }
  717. if (pFieldStruct->dwLength > 0)
  718. {
  719. pFieldStruct->fPresent = TRUE;
  720. }
  721. return S_OK;
  722. }
  723. //------------------------------------------------------------------------------
  724. // Parse an optional calling party subaddress field
  725. //
  726. // Parameters:
  727. // pbBuffer Pointer to a descriptor of the buffer
  728. // containing the length and a pointer
  729. // to the raw bytes of the input stream.
  730. // pFieldStruct Pointer to space for parsed
  731. // information.
  732. //------------------------------------------------------------------------------
  733. HRESULT
  734. ParseCallingPartySubaddress(
  735. PBUFFERDESCR pBuf,
  736. PCALLINGSUBADDRIE pFieldStruct)
  737. {
  738. HRESULT hr;
  739. memset( (PVOID)pFieldStruct, 0, sizeof(CALLINGSUBADDRIE));
  740. pFieldStruct->fPresent = FALSE;
  741. hr = ParseVariableOctet(pBuf,
  742. &pFieldStruct->dwLength, &pFieldStruct->pbContents[0]);
  743. if( FAILED(hr) )
  744. {
  745. return hr;
  746. }
  747. if (pFieldStruct->dwLength > 0)
  748. {
  749. pFieldStruct->fPresent = TRUE;
  750. }
  751. return S_OK;
  752. }
  753. //------------------------------------------------------------------------------
  754. // Parse an optional called party number field
  755. //
  756. // Parameters:
  757. // pbBuffer Pointer to a descriptor of the buffer
  758. // containing the length and a pointer
  759. // to the raw bytes of the input stream.
  760. // pFieldStruct Pointer to space for parsed
  761. // information.
  762. //------------------------------------------------------------------------------
  763. HRESULT
  764. ParseCalledPartyNumber(
  765. PBUFFERDESCR pBuf,
  766. PCALLEDNUMBERIE pFieldStruct
  767. )
  768. {
  769. memset( (PVOID)pFieldStruct, 0, sizeof(PCALLEDNUMBERIE));
  770. pFieldStruct->fPresent = FALSE;
  771. if (GetNextIdent(pBuf->pbBuffer) == IDENT_CALLEDNUMBER)
  772. {
  773. BYTE RemainingLength = 0;
  774. // Need 3 bytes for the ident (1), length (1),
  775. // and type + plan (1) fields.
  776. if (pBuf->dwLength < 3)
  777. {
  778. return E_INVALIDARG;
  779. }
  780. // skip the ie identifier...
  781. pBuf->pbBuffer++;
  782. pBuf->dwLength--;
  783. // Get the length of the contents following the length field.
  784. RemainingLength = *pBuf->pbBuffer;
  785. pBuf->pbBuffer++;
  786. pBuf->dwLength--;
  787. // make sure we have at least that much length left...
  788. if (pBuf->dwLength < RemainingLength)
  789. {
  790. return E_INVALIDARG;
  791. }
  792. // Get the type + plan fields.
  793. if (*(pBuf->pbBuffer) & 0x80)
  794. {
  795. pFieldStruct->NumberType =
  796. (BYTE)(*pBuf->pbBuffer & 0xf0);
  797. pFieldStruct->NumberingPlan =
  798. (BYTE)(*pBuf->pbBuffer & 0x0f);
  799. pBuf->pbBuffer++;
  800. pBuf->dwLength--;
  801. RemainingLength--;
  802. }
  803. pFieldStruct->PartyNumberLength = RemainingLength;
  804. pFieldStruct->fPresent = TRUE;
  805. CopyMemory( pFieldStruct->PartyNumbers, pBuf->pbBuffer, RemainingLength );
  806. pBuf->pbBuffer += RemainingLength;
  807. pBuf->dwLength -= RemainingLength;
  808. }
  809. return S_OK;
  810. }
  811. //------------------------------------------------------------------------------
  812. // Parse an optional called party subaddress field
  813. //
  814. // Parameters:
  815. // pbBuffer Pointer to a descriptor of the buffer
  816. // containing the length and a pointer
  817. // to the raw bytes of the input stream.
  818. // pFieldStruct Pointer to space for parsed
  819. // information.
  820. //------------------------------------------------------------------------------
  821. HRESULT
  822. ParseCalledPartySubaddress(
  823. PBUFFERDESCR pBuf,
  824. PCALLEDSUBADDRIE pFieldStruct
  825. )
  826. {
  827. HRESULT hr;
  828. memset( (PVOID)pFieldStruct, 0, sizeof(CALLEDSUBADDRIE));
  829. pFieldStruct->fPresent = FALSE;
  830. hr = ParseVariableOctet(pBuf,
  831. &pFieldStruct->dwLength, &pFieldStruct->pbContents[0]);
  832. if( FAILED(hr) )
  833. {
  834. return hr;
  835. }
  836. if (pFieldStruct->dwLength > 0)
  837. {
  838. pFieldStruct->fPresent = TRUE;
  839. }
  840. return S_OK;
  841. }
  842. //------------------------------------------------------------------------------
  843. // Parse an optional redirecting number field
  844. //
  845. // Parameters:
  846. // pbBuffer Pointer to a descriptor of the buffer
  847. // containing the length and a pointer
  848. // to the raw bytes of the input stream.
  849. // pFieldStruct Pointer to space for parsed
  850. // information.
  851. //------------------------------------------------------------------------------
  852. HRESULT
  853. ParseRedirectingNumber(
  854. PBUFFERDESCR pBuf,
  855. PREDIRECTINGIE pFieldStruct
  856. )
  857. {
  858. HRESULT hr;
  859. memset( (PVOID)pFieldStruct, 0, sizeof(REDIRECTINGIE));
  860. pFieldStruct->fPresent = FALSE;
  861. hr = ParseVariableOctet(pBuf,
  862. &pFieldStruct->dwLength, &pFieldStruct->pbContents[0]);
  863. if( FAILED(hr) )
  864. {
  865. return hr;
  866. }
  867. if (pFieldStruct->dwLength > 0)
  868. {
  869. pFieldStruct->fPresent = TRUE;
  870. }
  871. return S_OK;
  872. }
  873. //------------------------------------------------------------------------------
  874. // Parse an optional lower layer compatibility field
  875. //
  876. // Parameters:
  877. // pbBuffer Pointer to a descriptor of the buffer
  878. // containing the length and a pointer
  879. // to the raw bytes of the input stream.
  880. // pFieldStruct Pointer to space for parsed
  881. // information.
  882. //------------------------------------------------------------------------------
  883. HRESULT
  884. ParseLowLayerCompatibility(
  885. PBUFFERDESCR pBuf,
  886. PLLCOMPATIBILITYIE pFieldStruct
  887. )
  888. {
  889. HRESULT hr;
  890. memset( (PVOID)pFieldStruct, 0, sizeof(LLCOMPATIBILITYIE));
  891. pFieldStruct->fPresent = FALSE;
  892. hr = ParseVariableOctet(pBuf,
  893. &pFieldStruct->dwLength, &pFieldStruct->pbContents[0]);
  894. if( FAILED(hr) )
  895. {
  896. return hr;
  897. }
  898. if (pFieldStruct->dwLength > 0)
  899. {
  900. pFieldStruct->fPresent = TRUE;
  901. }
  902. return S_OK;
  903. }
  904. //------------------------------------------------------------------------------
  905. // Parse an optional higher layer compatibility field
  906. //
  907. // Parameters:
  908. // pbBuffer Pointer to a descriptor of the buffer
  909. // containing the length and a pointer
  910. // to the raw bytes of the input stream.
  911. // pFieldStruct Pointer to space for parsed
  912. // information.
  913. //------------------------------------------------------------------------------
  914. HRESULT
  915. ParseHighLayerCompatibility(
  916. PBUFFERDESCR pBuf,
  917. PHLCOMPATIBILITYIE pFieldStruct
  918. )
  919. {
  920. HRESULT hr;
  921. memset( (PVOID)pFieldStruct, 0, sizeof(HLCOMPATIBILITYIE));
  922. pFieldStruct->fPresent = FALSE;
  923. hr = ParseVariableOctet(pBuf, &pFieldStruct->dwLength,
  924. &pFieldStruct->pbContents[0]);
  925. if( FAILED(hr) )
  926. {
  927. return hr;
  928. }
  929. if (pFieldStruct->dwLength > 0)
  930. {
  931. pFieldStruct->fPresent = TRUE;
  932. }
  933. return S_OK;
  934. }
  935. HRESULT
  936. ParseUserToUser(
  937. PBUFFERDESCR pBuf,
  938. PUSERUSERIE pFieldStruct
  939. )
  940. {
  941. BYTE bIdent;
  942. HRESULT hr;
  943. ZeroMemory( (PVOID)pFieldStruct, sizeof(USERUSERIE));
  944. pFieldStruct->fPresent = FALSE;
  945. hr = ParseVariableASN( pBuf,
  946. &bIdent,
  947. &(pFieldStruct->ProtocolDiscriminator),
  948. pFieldStruct
  949. );
  950. if( FAILED(hr) )
  951. {
  952. return hr;
  953. }
  954. if (pFieldStruct->wUserInfoLen > 0)
  955. {
  956. pFieldStruct->fPresent = TRUE;
  957. }
  958. return S_OK;
  959. }
  960. HRESULT
  961. ParseQ931Field(
  962. PBUFFERDESCR pBuf,
  963. PQ931MESSAGE pMessage
  964. )
  965. {
  966. FIELDIDENTTYPE bIdent;
  967. bIdent = GetNextIdent(pBuf->pbBuffer);
  968. switch (bIdent)
  969. {
  970. /*case IDENT_REVCHARGE:
  971. case IDENT_TRANSITNET:
  972. case IDENT_RESTART:
  973. case IDENT_MORE:
  974. case IDENT_REPEAT:
  975. case IDENT_SEGMENTED:
  976. case IDENT_SHIFT:
  977. case IDENT_CALLIDENT:
  978. case IDENT_CLOSEDUG:
  979. case IDENT_SENDINGCOMPLETE:
  980. case IDENT_PACKETSIZE:
  981. case IDENT_CONGESTION:
  982. case IDENT_NETWORKSPEC:
  983. case IDENT_PLWINDOWSIZE:
  984. case IDENT_TRANSITDELAY:
  985. case IDENT_PLBINARYPARAMS:
  986. case IDENT_ENDTOENDDELAY:
  987. return E_INVALIDARG;*/
  988. case IDENT_FACILITY:
  989. return ParseFacility( pBuf, &pMessage->Facility );
  990. case IDENT_BEARERCAP:
  991. return ParseBearerCapability( pBuf, &pMessage->BearerCapability );
  992. case IDENT_CAUSE:
  993. return ParseCause(pBuf, &pMessage->Cause);
  994. case IDENT_CALLSTATE:
  995. return ParseCallState(pBuf, &pMessage->CallState);
  996. case IDENT_CHANNELIDENT:
  997. return ParseChannelIdentification( pBuf,
  998. &pMessage->ChannelIdentification );
  999. case IDENT_PROGRESS:
  1000. return ParseProgress( pBuf, &pMessage->ProgressIndicator );
  1001. case IDENT_NOTIFICATION:
  1002. return ParseNotificationIndicator( pBuf,
  1003. &pMessage->NotificationIndicator );
  1004. case IDENT_DISPLAY:
  1005. return ParseDisplay( pBuf, &pMessage->Display );
  1006. case IDENT_DATE:
  1007. return ParseDate( pBuf, &pMessage->Date );
  1008. case IDENT_KEYPAD:
  1009. return ParseKeypad( pBuf, &pMessage->Keypad );
  1010. case IDENT_SIGNAL:
  1011. return ParseSignal(pBuf, &pMessage->Signal);
  1012. case IDENT_INFORMATIONRATE:
  1013. return ParseInformationRate( pBuf, &pMessage->InformationRate );
  1014. case IDENT_CALLINGNUMBER:
  1015. return ParseCallingPartyNumber( pBuf, &pMessage->CallingPartyNumber );
  1016. case IDENT_CALLINGSUBADDR:
  1017. return ParseCallingPartySubaddress(pBuf,
  1018. &pMessage->CallingPartySubaddress);
  1019. case IDENT_CALLEDNUMBER:
  1020. return ParseCalledPartyNumber(pBuf, &pMessage->CalledPartyNumber);
  1021. case IDENT_CALLEDSUBADDR:
  1022. return ParseCalledPartySubaddress( pBuf,
  1023. &pMessage->CalledPartySubaddress );
  1024. case IDENT_REDIRECTING:
  1025. return ParseRedirectingNumber( pBuf, &pMessage->RedirectingNumber );
  1026. case IDENT_LLCOMPATIBILITY:
  1027. return ParseLowLayerCompatibility( pBuf,
  1028. &pMessage->LowLayerCompatibility );
  1029. case IDENT_HLCOMPATIBILITY:
  1030. return ParseHighLayerCompatibility( pBuf,
  1031. &pMessage->HighLayerCompatibility );
  1032. case IDENT_USERUSER:
  1033. return ParseUserToUser(pBuf, &pMessage->UserToUser);
  1034. default:
  1035. //Increment the ident byte
  1036. pBuf->pbBuffer++;
  1037. pBuf->dwLength--;
  1038. return S_OK;
  1039. }
  1040. }
  1041. //------------------------------------------------------------------------------
  1042. // Write a Q931 message type. See Q931 section 4.4.
  1043. //------------------------------------------------------------------------------
  1044. void
  1045. WriteMessageType(
  1046. PBUFFERDESCR pBuf,
  1047. MESSAGEIDTYPE * MessageType,
  1048. DWORD* pdwPDULen
  1049. )
  1050. {
  1051. (*pdwPDULen) += sizeof(MESSAGEIDTYPE);
  1052. _ASSERTE( pBuf->dwLength > *pdwPDULen );
  1053. *(MESSAGEIDTYPE *)(pBuf->pbBuffer) =
  1054. (BYTE)(*MessageType & MESSAGETYPEMASK);
  1055. pBuf->pbBuffer += sizeof(MESSAGEIDTYPE);
  1056. }
  1057. void
  1058. WriteVariableOctet(
  1059. PBUFFERDESCR pBuf,
  1060. BYTE bIdent,
  1061. BYTE dwLength,
  1062. BYTE *pbContents,
  1063. DWORD* pdwPDULen
  1064. )
  1065. {
  1066. if( pbContents == NULL )
  1067. {
  1068. dwLength = 0;
  1069. }
  1070. // space for the length and the identifier bytes and octet array
  1071. (*pdwPDULen) += (2 + dwLength);
  1072. _ASSERTE( pBuf->dwLength > *pdwPDULen );
  1073. // the id byte, then the length byte
  1074. // low 7 bits of the first byte are the identifier
  1075. *pBuf->pbBuffer = (BYTE)(bIdent & 0x7f);
  1076. pBuf->pbBuffer++;
  1077. *pBuf->pbBuffer = dwLength;
  1078. pBuf->pbBuffer++;
  1079. CopyMemory( (PVOID)pBuf->pbBuffer, (PVOID)pbContents, dwLength );
  1080. pBuf->pbBuffer += dwLength;
  1081. }
  1082. void
  1083. WriteUserInformation(
  1084. PBUFFERDESCR pBuf,
  1085. BYTE bIdent,
  1086. WORD wUserInfoLen,
  1087. BYTE * pbUserInfo,
  1088. DWORD * pdwPDULen
  1089. )
  1090. {
  1091. WORD ContentsLength = (WORD)(wUserInfoLen + 1);
  1092. // There has to be at least 4 bytes for the IE identifier,
  1093. // the contents length, and the protocol discriminator (1 + 2 + 1).
  1094. (*pdwPDULen) += (4 + wUserInfoLen);
  1095. _ASSERTE( pBuf->dwLength > *pdwPDULen );
  1096. // low 7 bits of the first byte are the identifier
  1097. *pBuf->pbBuffer = (BYTE)(bIdent & 0x7f);
  1098. pBuf->pbBuffer++;
  1099. // write the contents length bytes.
  1100. *pBuf->pbBuffer = (BYTE)(ContentsLength >> 8);
  1101. pBuf->pbBuffer++;
  1102. *pBuf->pbBuffer = (BYTE)ContentsLength;
  1103. pBuf->pbBuffer++;
  1104. // write the protocol discriminator byte.
  1105. *(pBuf->pbBuffer) = Q931_PROTOCOL_X209;
  1106. pBuf->pbBuffer++;
  1107. CopyMemory( (PVOID)pBuf->pbBuffer,
  1108. (PVOID)pbUserInfo,
  1109. wUserInfoLen);
  1110. pBuf->pbBuffer += wUserInfoLen;
  1111. }
  1112. HRESULT
  1113. WritePartyNumber(
  1114. PBUFFERDESCR pBuf,
  1115. BYTE bIdent,
  1116. BYTE NumberType,
  1117. BYTE NumberingPlan,
  1118. BYTE bPartyNumberLength,
  1119. BYTE *pbPartyNumbers,
  1120. DWORD * pdwPDULen )
  1121. {
  1122. if (pbPartyNumbers == NULL)
  1123. {
  1124. bPartyNumberLength = 1;
  1125. }
  1126. // space for the ident (1), length (1), and type + plan (1) fields.
  1127. (*pdwPDULen) += (2 + bPartyNumberLength);
  1128. _ASSERTE( pBuf->dwLength > *pdwPDULen );
  1129. // low 7 bits of byte 1 are the ie identifier
  1130. *pBuf->pbBuffer = (BYTE)(bIdent & 0x7f);
  1131. pBuf->pbBuffer++;
  1132. // byte 2 is the ie contents length following the length field.
  1133. *pBuf->pbBuffer = (BYTE)(bPartyNumberLength);
  1134. pBuf->pbBuffer++;
  1135. // byte 3 is the type and plan field.
  1136. *pBuf->pbBuffer = (BYTE)(NumberType | NumberingPlan);
  1137. pBuf->pbBuffer++;
  1138. if( pbPartyNumbers != NULL )
  1139. {
  1140. CopyMemory( (PVOID)pBuf->pbBuffer,
  1141. (PVOID)pbPartyNumbers,
  1142. bPartyNumberLength-1 );
  1143. }
  1144. pBuf->pbBuffer += (bPartyNumberLength-1);
  1145. return S_OK;
  1146. }
  1147. //
  1148. //ASN Parsing functions
  1149. //
  1150. BOOL
  1151. ParseVendorInfo(
  1152. OUT PH323_VENDORINFO pDestVendorInfo,
  1153. IN VendorIdentifier* pVendor
  1154. )
  1155. {
  1156. memset( (PVOID)pDestVendorInfo, 0, sizeof(H323_VENDORINFO) );
  1157. pDestVendorInfo ->bCountryCode = (BYTE)pVendor->vendor.t35CountryCode;
  1158. pDestVendorInfo ->bExtension = (BYTE)pVendor->vendor.t35Extension;
  1159. pDestVendorInfo ->wManufacturerCode = pVendor->vendor.manufacturerCode;
  1160. if( pVendor->bit_mask & (productId_present) )
  1161. {
  1162. pDestVendorInfo ->pProductNumber = new H323_OCTETSTRING;
  1163. if( pDestVendorInfo ->pProductNumber == NULL )
  1164. {
  1165. goto cleanup;
  1166. }
  1167. pDestVendorInfo ->pProductNumber->wOctetStringLength =
  1168. (WORD)min(pVendor->productId.length, H323_MAX_PRODUCT_LENGTH - 1);
  1169. pDestVendorInfo ->pProductNumber->pOctetString = (BYTE*)
  1170. new char[pDestVendorInfo ->pProductNumber->wOctetStringLength + 1];
  1171. if( pDestVendorInfo ->pProductNumber->pOctetString == NULL )
  1172. {
  1173. goto cleanup;
  1174. }
  1175. CopyMemory( (PVOID)pDestVendorInfo ->pProductNumber->pOctetString,
  1176. (PVOID)pVendor->productId.value,
  1177. pDestVendorInfo -> pProductNumber->wOctetStringLength );
  1178. pDestVendorInfo ->pProductNumber->pOctetString[
  1179. pDestVendorInfo ->pProductNumber->wOctetStringLength] = '\0';
  1180. }
  1181. if( pVendor->bit_mask & versionId_present )
  1182. {
  1183. pDestVendorInfo ->pVersionNumber = new H323_OCTETSTRING;
  1184. if( pDestVendorInfo ->pVersionNumber == NULL )
  1185. {
  1186. goto cleanup;
  1187. }
  1188. pDestVendorInfo ->pVersionNumber->wOctetStringLength =
  1189. (WORD)min(pVendor->versionId.length, H323_MAX_VERSION_LENGTH - 1);
  1190. pDestVendorInfo ->pVersionNumber->pOctetString = (BYTE*)
  1191. new char[pDestVendorInfo ->pVersionNumber->wOctetStringLength+1];
  1192. if( pDestVendorInfo ->pVersionNumber->pOctetString == NULL )
  1193. {
  1194. goto cleanup;
  1195. }
  1196. CopyMemory( (PVOID)pDestVendorInfo ->pVersionNumber->pOctetString,
  1197. (PVOID)pVendor->versionId.value,
  1198. pDestVendorInfo ->pVersionNumber->wOctetStringLength);
  1199. pDestVendorInfo ->pVersionNumber->pOctetString[
  1200. pDestVendorInfo ->pVersionNumber->wOctetStringLength] = '\0';
  1201. }
  1202. return TRUE;
  1203. cleanup:
  1204. FreeVendorInfo( pDestVendorInfo );
  1205. return FALSE;
  1206. }
  1207. BOOL
  1208. ParseNonStandardData(
  1209. OUT H323NonStandardData * dstNonStdData,
  1210. IN H225NonStandardParameter * srcNonStdData
  1211. )
  1212. {
  1213. H221NonStandard & h221NonStdData =
  1214. srcNonStdData ->nonStandardIdentifier.u.h221NonStandard;
  1215. if( srcNonStdData ->nonStandardIdentifier.choice ==
  1216. H225NonStandardIdentifier_h221NonStandard_chosen )
  1217. {
  1218. dstNonStdData ->bCountryCode = (BYTE)(h221NonStdData.t35CountryCode);
  1219. dstNonStdData ->bExtension = (BYTE)(h221NonStdData.t35Extension);
  1220. dstNonStdData ->wManufacturerCode = h221NonStdData.manufacturerCode;
  1221. }
  1222. dstNonStdData->sData.wOctetStringLength = (WORD)srcNonStdData->data.length;
  1223. dstNonStdData ->sData.pOctetString =
  1224. (BYTE *)new char[dstNonStdData ->sData.wOctetStringLength];
  1225. if( dstNonStdData -> sData.pOctetString == NULL )
  1226. {
  1227. return FALSE;
  1228. }
  1229. CopyMemory( (PVOID)dstNonStdData ->sData.pOctetString,
  1230. (PVOID)srcNonStdData ->data.value,
  1231. dstNonStdData ->sData.wOctetStringLength );
  1232. return TRUE;
  1233. }
  1234. BOOL
  1235. AliasAddrToAliasNames(
  1236. OUT PH323_ALIASNAMES *ppTarget,
  1237. IN Setup_UUIE_sourceAddress *pSource
  1238. )
  1239. {
  1240. Setup_UUIE_sourceAddress *CurrentNode = NULL;
  1241. WORD wCount = 0;
  1242. int indexI = 0;
  1243. HRESULT hr;
  1244. *ppTarget = NULL;
  1245. for( CurrentNode = pSource; CurrentNode; CurrentNode = CurrentNode->next )
  1246. {
  1247. wCount++;
  1248. }
  1249. if( wCount == 0 )
  1250. {
  1251. return TRUE;
  1252. }
  1253. *ppTarget = new H323_ALIASNAMES;
  1254. if (*ppTarget == NULL)
  1255. {
  1256. return FALSE;
  1257. }
  1258. ZeroMemory( *ppTarget, sizeof(H323_ALIASNAMES) );
  1259. (*ppTarget)->pItems = new H323_ALIASITEM[wCount];
  1260. if( (*ppTarget)->pItems == NULL )
  1261. {
  1262. goto cleanup;
  1263. }
  1264. for( CurrentNode = pSource; CurrentNode; CurrentNode = CurrentNode->next )
  1265. {
  1266. hr = AliasAddrToAliasItem( &((*ppTarget)->pItems[indexI]),
  1267. &(CurrentNode->value));
  1268. if( hr == E_OUTOFMEMORY )
  1269. {
  1270. WORD indexJ;
  1271. //Free everything that has been allocated so far...
  1272. for (indexJ = 0; indexJ < indexI; indexJ++)
  1273. {
  1274. delete (*ppTarget)->pItems[indexJ].pData;
  1275. }
  1276. goto cleanup;
  1277. }
  1278. else if( SUCCEEDED(hr) )
  1279. {
  1280. indexI++;
  1281. }
  1282. }
  1283. // any aliases?
  1284. if (indexI > 0)
  1285. {
  1286. // save number of aliases
  1287. (*ppTarget)->wCount = (WORD)indexI;
  1288. }
  1289. else
  1290. {
  1291. //free everything
  1292. delete (*ppTarget)->pItems;
  1293. delete (*ppTarget);
  1294. *ppTarget = NULL;
  1295. return FALSE;
  1296. }
  1297. return TRUE;
  1298. cleanup:
  1299. if( *ppTarget )
  1300. {
  1301. if( (*ppTarget)->pItems )
  1302. {
  1303. delete (*ppTarget)->pItems;
  1304. }
  1305. delete( *ppTarget );
  1306. *ppTarget = NULL;
  1307. }
  1308. return FALSE;
  1309. }
  1310. HRESULT
  1311. AliasAddrToAliasItem(
  1312. OUT PH323_ALIASITEM pAliasItem,
  1313. IN AliasAddress * pAliasAddr
  1314. )
  1315. {
  1316. WORD indexI;
  1317. if( pAliasItem == NULL )
  1318. {
  1319. return E_FAIL;
  1320. }
  1321. memset( (PVOID)pAliasItem, 0, sizeof(H323_ALIASITEM) );
  1322. switch( pAliasAddr->choice )
  1323. {
  1324. case h323_ID_chosen:
  1325. pAliasItem->wType = h323_ID_chosen;
  1326. if ((pAliasAddr->u.h323_ID.length != 0) &&
  1327. (pAliasAddr->u.h323_ID.value != NULL))
  1328. {
  1329. pAliasItem->wDataLength = (WORD)pAliasAddr->u.h323_ID.length;
  1330. pAliasItem->pData =
  1331. (LPWSTR)new char[(pAliasItem->wDataLength+1) * sizeof(WCHAR)];
  1332. if (pAliasItem->pData == NULL)
  1333. {
  1334. return E_OUTOFMEMORY;
  1335. }
  1336. CopyMemory( (PVOID)pAliasItem->pData,
  1337. (PVOID)pAliasAddr->u.h323_ID.value,
  1338. pAliasItem->wDataLength * sizeof(WCHAR) );
  1339. pAliasItem->pData[pAliasItem->wDataLength] = L'\0';
  1340. }
  1341. break;
  1342. case e164_chosen:
  1343. pAliasItem->wType = e164_chosen;
  1344. pAliasItem->wDataLength = (WORD)strlen(pAliasAddr->u.e164);
  1345. pAliasItem->pData =
  1346. (LPWSTR)new char[(pAliasItem->wDataLength + 1) * sizeof(WCHAR)];
  1347. if( pAliasItem->pData == NULL )
  1348. {
  1349. return E_OUTOFMEMORY;
  1350. }
  1351. //converting from byte to UNICODE
  1352. for (indexI = 0; indexI < pAliasItem->wDataLength; indexI++)
  1353. {
  1354. pAliasItem->pData[indexI] = (WCHAR)pAliasAddr->u.e164[indexI];
  1355. }
  1356. pAliasItem->pData[pAliasItem->wDataLength] = '\0';
  1357. break;
  1358. default:
  1359. return E_INVALIDARG;
  1360. } // switch
  1361. return S_OK;
  1362. }
  1363. void FreeFacilityASN(
  1364. IN Q931_FACILITY_ASN* pFacilityASN
  1365. )
  1366. {
  1367. //free non standard data
  1368. if( pFacilityASN->fNonStandardDataPresent != NULL )
  1369. {
  1370. delete pFacilityASN->nonStandardData.sData.pOctetString;
  1371. pFacilityASN->nonStandardData.sData.pOctetString =NULL;
  1372. }
  1373. if( pFacilityASN->pAlternativeAliasList != NULL )
  1374. {
  1375. FreeAliasNames(pFacilityASN->pAlternativeAliasList );
  1376. pFacilityASN->pAlternativeAliasList = NULL;
  1377. }
  1378. }
  1379. void FreeAlertingASN(
  1380. IN Q931_ALERTING_ASN* pAlertingASN
  1381. )
  1382. {
  1383. FreeProceedingASN( (Q931_CALL_PROCEEDING_ASN*)pAlertingASN );
  1384. }
  1385. void FreeProceedingASN(
  1386. IN Q931_CALL_PROCEEDING_ASN* pProceedingASN
  1387. )
  1388. {
  1389. //free non standard data
  1390. if( pProceedingASN->fNonStandardDataPresent == TRUE )
  1391. {
  1392. delete pProceedingASN->nonStandardData.sData.pOctetString;
  1393. pProceedingASN->nonStandardData.sData.pOctetString = NULL;
  1394. }
  1395. if( pProceedingASN->fFastStartPresent &&pProceedingASN->pFastStart )
  1396. {
  1397. FreeFastStart( pProceedingASN->pFastStart );
  1398. }
  1399. }
  1400. void FreeSetupASN(
  1401. IN Q931_SETUP_ASN* pSetupASN
  1402. )
  1403. {
  1404. if( pSetupASN == NULL )
  1405. {
  1406. return;
  1407. }
  1408. if( pSetupASN->pExtensionAliasItem != NULL )
  1409. {
  1410. if( pSetupASN->pExtensionAliasItem -> pData != NULL )
  1411. {
  1412. delete pSetupASN->pExtensionAliasItem -> pData;
  1413. }
  1414. delete pSetupASN->pExtensionAliasItem;
  1415. }
  1416. if( pSetupASN->pExtraAliasList != NULL )
  1417. {
  1418. FreeAliasNames(pSetupASN->pExtraAliasList);
  1419. pSetupASN->pExtraAliasList = NULL;
  1420. }
  1421. if( pSetupASN->pCalleeAliasList != NULL )
  1422. {
  1423. FreeAliasNames(pSetupASN->pCalleeAliasList);
  1424. pSetupASN->pCalleeAliasList = NULL;
  1425. }
  1426. if( pSetupASN->pCallerAliasList != NULL )
  1427. {
  1428. FreeAliasNames(pSetupASN->pCallerAliasList);
  1429. pSetupASN->pCallerAliasList = NULL;
  1430. }
  1431. if( pSetupASN->fNonStandardDataPresent == TRUE )
  1432. {
  1433. delete pSetupASN->nonStandardData.sData.pOctetString;
  1434. }
  1435. if( pSetupASN->EndpointType.pVendorInfo != NULL )
  1436. {
  1437. FreeVendorInfo( pSetupASN->EndpointType.pVendorInfo );
  1438. }
  1439. if( pSetupASN->fFastStartPresent == TRUE )
  1440. {
  1441. if( pSetupASN->pFastStart != NULL )
  1442. {
  1443. FreeFastStart( pSetupASN->pFastStart );
  1444. }
  1445. }
  1446. }
  1447. void FreeConnectASN(
  1448. IN Q931_CONNECT_ASN *pConnectASN
  1449. )
  1450. {
  1451. if( pConnectASN != NULL )
  1452. {
  1453. // Cleanup any dynamically allocated fields within SetupASN
  1454. if (pConnectASN->nonStandardData.sData.pOctetString)
  1455. {
  1456. delete pConnectASN->nonStandardData.sData.pOctetString;
  1457. pConnectASN->nonStandardData.sData.pOctetString = NULL;
  1458. }
  1459. if( pConnectASN->EndpointType.pVendorInfo != NULL )
  1460. {
  1461. FreeVendorInfo( pConnectASN->EndpointType.pVendorInfo );
  1462. }
  1463. if( pConnectASN->fFastStartPresent == TRUE )
  1464. {
  1465. if( pConnectASN->pFastStart != NULL )
  1466. {
  1467. FreeFastStart( pConnectASN->pFastStart );
  1468. }
  1469. }
  1470. }
  1471. }
  1472. void
  1473. FreeFastStart(
  1474. IN PH323_FASTSTART pFastStart
  1475. )
  1476. {
  1477. PH323_FASTSTART pTempFastStart;
  1478. while( pFastStart )
  1479. {
  1480. pTempFastStart = pFastStart -> next;
  1481. if(pFastStart -> value)
  1482. {
  1483. delete pFastStart -> value;
  1484. }
  1485. delete pFastStart;
  1486. pFastStart = pTempFastStart;
  1487. }
  1488. }
  1489. //FastStart is a plain linked list because it is exactly the same struct
  1490. //as defined by ASN.1. This allows to pass on the m_pFastStart member to
  1491. //the ASN encoder directly without any conversons
  1492. PH323_FASTSTART
  1493. CopyFastStart(
  1494. IN PSetup_UUIE_fastStart pSrcFastStart
  1495. )
  1496. {
  1497. PH323_FASTSTART pCurr, pHead = NULL, pTail = NULL;
  1498. H323DBG(( DEBUG_LEVEL_TRACE, "CopyFastStart entered." ));
  1499. while( pSrcFastStart )
  1500. {
  1501. pCurr = new H323_FASTSTART;
  1502. if( pCurr == NULL )
  1503. {
  1504. FreeFastStart( pHead );
  1505. return NULL;
  1506. }
  1507. pCurr -> next = NULL;
  1508. if( pHead == NULL )
  1509. {
  1510. pHead = pCurr;
  1511. }
  1512. else
  1513. {
  1514. pTail -> next = pCurr;
  1515. }
  1516. pTail = pCurr;
  1517. pCurr -> length = pSrcFastStart -> value.length;
  1518. pCurr -> value = (BYTE*)new char[pCurr -> length];
  1519. if( pCurr -> value == NULL )
  1520. {
  1521. FreeFastStart( pHead );
  1522. return NULL;
  1523. }
  1524. CopyMemory( (PVOID)pCurr -> value,
  1525. (PVOID)pSrcFastStart -> value.value,
  1526. pCurr -> length );
  1527. pSrcFastStart = pSrcFastStart->next;
  1528. }
  1529. H323DBG(( DEBUG_LEVEL_TRACE, "CopyFastStart exited." ));
  1530. return pHead;
  1531. }
  1532. void
  1533. FreeVendorInfo(
  1534. IN PH323_VENDORINFO pVendorInfo
  1535. )
  1536. {
  1537. H323DBG(( DEBUG_LEVEL_TRACE, "FreeVendorInfo entered." ));
  1538. if( pVendorInfo != NULL )
  1539. {
  1540. if( pVendorInfo ->pProductNumber != NULL )
  1541. {
  1542. if( pVendorInfo ->pProductNumber->pOctetString != NULL )
  1543. {
  1544. delete pVendorInfo ->pProductNumber->pOctetString;
  1545. }
  1546. delete pVendorInfo ->pProductNumber;
  1547. }
  1548. if( pVendorInfo ->pVersionNumber != NULL )
  1549. {
  1550. if( pVendorInfo ->pVersionNumber->pOctetString != NULL )
  1551. {
  1552. delete pVendorInfo ->pVersionNumber->pOctetString;
  1553. }
  1554. delete pVendorInfo ->pVersionNumber;
  1555. }
  1556. memset( (PVOID) pVendorInfo, 0, sizeof(H323_VENDORINFO) );
  1557. }
  1558. H323DBG(( DEBUG_LEVEL_TRACE, "FreeVendorInfo exited." ));
  1559. }
  1560. void
  1561. FreeAliasNames(
  1562. IN PH323_ALIASNAMES pSource
  1563. )
  1564. {
  1565. H323DBG(( DEBUG_LEVEL_TRACE, "FreeAliasNames entered." ));
  1566. if( pSource != NULL )
  1567. {
  1568. if( pSource->wCount != 0 )
  1569. {
  1570. // Free everything that has been allocated so far...
  1571. int indexI;
  1572. for( indexI = 0; indexI < pSource->wCount; indexI++ )
  1573. {
  1574. if( pSource->pItems[indexI].pPrefix != NULL )
  1575. {
  1576. H323DBG(( DEBUG_LEVEL_TRACE, "delete prefix:%d.", indexI ));
  1577. delete pSource->pItems[indexI].pPrefix;
  1578. }
  1579. if( pSource->pItems[indexI].pData != NULL )
  1580. {
  1581. H323DBG(( DEBUG_LEVEL_TRACE, "delete pdata:%d.", indexI ));
  1582. delete pSource->pItems[indexI].pData;
  1583. }
  1584. }
  1585. if( pSource->pItems != NULL )
  1586. {
  1587. H323DBG(( DEBUG_LEVEL_TRACE, "delete pitems." ));
  1588. delete pSource->pItems;
  1589. }
  1590. }
  1591. H323DBG(( DEBUG_LEVEL_TRACE, "outta loop." ));
  1592. delete pSource;
  1593. }
  1594. H323DBG(( DEBUG_LEVEL_TRACE, "FreeAliasNames exited." ));
  1595. }
  1596. void
  1597. FreeAliasItems(
  1598. IN PH323_ALIASNAMES pSource
  1599. )
  1600. {
  1601. H323DBG(( DEBUG_LEVEL_TRACE, "FreeAliasItems entered." ));
  1602. if( pSource != NULL )
  1603. {
  1604. if( pSource->wCount != 0 )
  1605. {
  1606. // Free everything that has been allocated so far...
  1607. int indexI;
  1608. for( indexI = 0; indexI < pSource->wCount; indexI++ )
  1609. {
  1610. if( pSource->pItems[indexI].pPrefix )
  1611. {
  1612. delete pSource->pItems[indexI].pPrefix;
  1613. }
  1614. if( pSource->pItems[indexI].pData )
  1615. {
  1616. delete pSource->pItems[indexI].pData;
  1617. }
  1618. }
  1619. if( pSource->pItems != NULL )
  1620. {
  1621. delete pSource->pItems;
  1622. pSource->pItems = NULL;
  1623. }
  1624. pSource->wCount = 0;
  1625. }
  1626. }
  1627. H323DBG(( DEBUG_LEVEL_TRACE, "FreeAliasItems exited." ));
  1628. }
  1629. void
  1630. SetupTPKTHeader(
  1631. OUT BYTE * pbTpktHeader,
  1632. IN DWORD dwLength
  1633. )
  1634. {
  1635. dwLength += TPKT_HEADER_SIZE;
  1636. // TPKT requires that the packet size fit in two bytes.
  1637. _ASSERTE( dwLength < (1L << 16));
  1638. pbTpktHeader[0] = TPKT_VERSION;
  1639. pbTpktHeader[1] = 0;
  1640. pbTpktHeader[2] = (BYTE)(dwLength >> 8);
  1641. pbTpktHeader[3] = (BYTE)dwLength;
  1642. }
  1643. int
  1644. GetTpktLength(
  1645. IN char * pTpktHeader
  1646. )
  1647. {
  1648. BYTE * pbTempPtr = (BYTE*)pTpktHeader;
  1649. return (pbTempPtr[2] << 8) + pbTempPtr[3];
  1650. }
  1651. BOOL
  1652. AddAliasItem(
  1653. IN OUT PH323_ALIASNAMES pAliasNames,
  1654. IN BYTE* pbAliasName,
  1655. IN DWORD dwAliasSize,
  1656. IN WORD wType
  1657. )
  1658. {
  1659. H323DBG(( DEBUG_LEVEL_TRACE, "AddAliasItem entered." ));
  1660. PH323_ALIASITEM pAliasItem;
  1661. PH323_ALIASITEM tempPtr = pAliasNames -> pItems;
  1662. pAliasNames -> pItems = (PH323_ALIASITEM)realloc( pAliasNames -> pItems,
  1663. sizeof(H323_ALIASITEM) * (pAliasNames->wCount+1) );
  1664. if( pAliasNames -> pItems == NULL )
  1665. {
  1666. //restore the old pointer in case enough memory was not available to
  1667. //expand the memory block
  1668. pAliasNames -> pItems = tempPtr;
  1669. return FALSE;
  1670. }
  1671. pAliasItem = &(pAliasNames -> pItems[pAliasNames->wCount]);
  1672. pAliasItem->pData = (WCHAR*)new char[dwAliasSize];
  1673. if( pAliasItem ->pData == NULL )
  1674. {
  1675. return FALSE;
  1676. }
  1677. pAliasNames->wCount++;
  1678. // transfer memory
  1679. CopyMemory((PVOID)pAliasItem ->pData,
  1680. pbAliasName,
  1681. dwAliasSize );
  1682. // complete alias
  1683. pAliasItem ->wType = wType;
  1684. pAliasItem ->wPrefixLength = 0;
  1685. pAliasItem ->pPrefix = NULL;
  1686. pAliasItem ->wDataLength = (WORD)wcslen(pAliasItem -> pData);
  1687. _ASSERTE( ((pAliasItem->wDataLength+1)*2) == (WORD)dwAliasSize );
  1688. H323DBG(( DEBUG_LEVEL_TRACE, "AddAliasItem exited." ));
  1689. return TRUE;
  1690. }
  1691. void
  1692. FreeAddressAliases(
  1693. IN PSetup_UUIE_destinationAddress pAddr
  1694. )
  1695. {
  1696. PSetup_UUIE_destinationAddress pTempAddr;
  1697. while( pAddr )
  1698. {
  1699. pTempAddr = pAddr -> next;
  1700. if( pAddr ->value.choice == h323_ID_chosen )
  1701. {
  1702. if( pAddr -> value.u.h323_ID.value )
  1703. {
  1704. delete pAddr -> value.u.h323_ID.value;
  1705. }
  1706. }
  1707. delete pAddr;
  1708. pAddr = pTempAddr;
  1709. }
  1710. }
  1711. void CopyTransportAddress(
  1712. OUT TransportAddress& transportAddress,
  1713. IN PH323_ADDR pCalleeAddr
  1714. )
  1715. {
  1716. DWORD dwAddr = pCalleeAddr->Addr.IP_Binary.dwAddr;
  1717. transportAddress.choice = ipAddress_chosen;
  1718. transportAddress.u.ipAddress.ip.length = 4;
  1719. transportAddress.u.ipAddress.port
  1720. = pCalleeAddr->Addr.IP_Binary.wPort;
  1721. *(DWORD*)transportAddress.u.ipAddress.ip.value =
  1722. htonl( pCalleeAddr->Addr.IP_Binary.dwAddr );
  1723. //ReverseAddressAndCopy( transportAddress.u.ipAddress.ip.value, dwAddr);
  1724. }
  1725. void
  1726. AddressReverseAndCopy(
  1727. OUT DWORD * pdwAddr,
  1728. IN BYTE * addrValue
  1729. )
  1730. {
  1731. BYTE *addr = (BYTE *)(pdwAddr);
  1732. addr[3] = addrValue[0];
  1733. addr[2] = addrValue[1];
  1734. addr[1] = addrValue[2];
  1735. addr[0] = addrValue[3];
  1736. }
  1737. Setup_UUIE_sourceAddress *
  1738. SetMsgAddressAlias(
  1739. IN PH323_ALIASNAMES pAliasNames
  1740. )
  1741. {
  1742. PH323_ALIASITEM pAliasItem;
  1743. Setup_UUIE_sourceAddress *addressAlias, *currHead = NULL;
  1744. WORD wCount;
  1745. int indexI;
  1746. for( wCount=0; wCount < pAliasNames->wCount; wCount++ )
  1747. {
  1748. addressAlias = new Setup_UUIE_sourceAddress;
  1749. if( addressAlias == NULL )
  1750. {
  1751. goto cleanup;
  1752. }
  1753. ZeroMemory( (PVOID)addressAlias, sizeof(Setup_UUIE_sourceAddress) );
  1754. addressAlias -> next = currHead;
  1755. currHead = addressAlias;
  1756. pAliasItem = &(pAliasNames->pItems[wCount]);
  1757. // then do the required memory copying.
  1758. if( pAliasItem -> wType == h323_ID_chosen )
  1759. {
  1760. addressAlias ->value.choice = h323_ID_chosen;
  1761. addressAlias ->value.u.h323_ID.length = pAliasItem -> wDataLength;
  1762. _ASSERTE( pAliasItem -> wDataLength );
  1763. addressAlias->value.u.h323_ID.value =
  1764. new WCHAR[pAliasItem -> wDataLength];
  1765. if( addressAlias->value.u.h323_ID.value == NULL )
  1766. {
  1767. goto cleanup;
  1768. }
  1769. CopyMemory((PVOID)addressAlias->value.u.h323_ID.value,
  1770. (PVOID)pAliasItem->pData,
  1771. pAliasItem -> wDataLength * sizeof(WCHAR) );
  1772. }
  1773. else if( pAliasItem -> wType == e164_chosen )
  1774. {
  1775. addressAlias ->value.choice = e164_chosen;
  1776. for( indexI =0; indexI < pAliasItem->wDataLength; indexI++ )
  1777. {
  1778. addressAlias->value.u.e164[indexI] = (BYTE)pAliasItem->pData[indexI];
  1779. }
  1780. addressAlias->value.u.e164[ pAliasItem->wDataLength ] = '\0';
  1781. }
  1782. else
  1783. {
  1784. continue;
  1785. }
  1786. }
  1787. return currHead;
  1788. cleanup:
  1789. FreeAddressAliases( (PSetup_UUIE_destinationAddress)currHead );
  1790. return NULL;
  1791. }
  1792. /*BOOL
  1793. SetSetupMsgAddressAliasWithPrefix(
  1794. PH323_ALIASITEM pCallerAlias,
  1795. Setup_UUIE_sourceAddress *addressAlias
  1796. )
  1797. {
  1798. UINT indexI;
  1799. addressAlias -> next = NULL;
  1800. UINT uPrefixLength = pCallerAlias -> wPrefixLength;
  1801. UINT uDataLength = pCallerAlias -> wDataLength;
  1802. if(pCallerAlias->wType == h323_ID_chosen)
  1803. {
  1804. addressAlias->value.choice = h323_ID_chosen;
  1805. addressAlias->value.u.h323_ID.length =
  1806. (WORD)(uPrefixLength + uDataLength);
  1807. if(!addressAlias->value.u.h323_ID.length)
  1808. {
  1809. addressAlias->value.u.h323_ID.value = NULL;
  1810. //no data to copy
  1811. return TRUE;
  1812. }
  1813. addressAlias->value.u.h323_ID.value =
  1814. (WCHAR*)new char[(uPrefixLength + uDataLength) * sizeof(WCHAR)];
  1815. if( addressAlias->value.u.h323_ID.value == NULL )
  1816. {
  1817. return FALSE;
  1818. }
  1819. addressAlias->value.u.h323_ID.length = (WORD)(uDataLength+uPrefixLength);
  1820. if( uPrefixLength != 0 )
  1821. {
  1822. CopyMemory((PVOID)addressAlias->value.u.h323_ID.value,
  1823. (PVOID)pCallerAlias->pPrefix,
  1824. uPrefixLength * sizeof(WCHAR) );
  1825. }
  1826. if( uDataLength != 0 )
  1827. {
  1828. CopyMemory((PVOID)&addressAlias->value.u.h323_ID.value[uPrefixLength],
  1829. (PVOID)pCallerAlias->pData,
  1830. uDataLength * sizeof(WCHAR) );
  1831. }
  1832. }
  1833. else if(pCallerAlias->wType == e164_chosen )
  1834. {
  1835. addressAlias->value.choice = e164_chosen;
  1836. for (indexI = 0; indexI < uPrefixLength; ++indexI)
  1837. {
  1838. addressAlias->value.u.e164[indexI] = (BYTE)(pCallerAlias->pPrefix[indexI]);
  1839. }
  1840. for (indexI = 0; indexI < uDataLength; ++indexI)
  1841. {
  1842. addressAlias->value.u.e164[uPrefixLength + indexI] = (BYTE)(pCallerAlias->pData[indexI]);
  1843. }
  1844. for (indexI = uDataLength + uPrefixLength; indexI < sizeof(addressAlias->value.u.e164); ++indexI)
  1845. {
  1846. addressAlias->value.u.e164[indexI] = 0;
  1847. }
  1848. }
  1849. else
  1850. {
  1851. //un identified alias type
  1852. return FALSE;
  1853. }
  1854. return TRUE;
  1855. }*/
  1856. void
  1857. CopyVendorInfo(
  1858. OUT VendorIdentifier* vendor
  1859. )
  1860. {
  1861. H323_VENDORINFO* pVendorInfo = g_pH323Line -> GetVendorInfo();
  1862. vendor->bit_mask = 0;
  1863. vendor->vendor.t35CountryCode = pVendorInfo ->bCountryCode;
  1864. vendor->vendor.t35Extension = pVendorInfo ->bExtension;
  1865. vendor->vendor.manufacturerCode = pVendorInfo ->wManufacturerCode;
  1866. if (pVendorInfo ->pProductNumber && pVendorInfo ->pProductNumber->pOctetString &&
  1867. pVendorInfo ->pProductNumber->wOctetStringLength)
  1868. {
  1869. vendor->bit_mask |= productId_present;
  1870. vendor->productId.length =
  1871. pVendorInfo ->pProductNumber->wOctetStringLength;
  1872. CopyMemory( (PVOID)&vendor->productId.value,
  1873. (PVOID)pVendorInfo ->pProductNumber->pOctetString,
  1874. pVendorInfo ->pProductNumber->wOctetStringLength);
  1875. }
  1876. if (pVendorInfo ->pVersionNumber && pVendorInfo ->pVersionNumber->pOctetString &&
  1877. pVendorInfo ->pVersionNumber->wOctetStringLength)
  1878. {
  1879. vendor->bit_mask |= versionId_present;
  1880. vendor->versionId.length =
  1881. pVendorInfo ->pVersionNumber->wOctetStringLength;
  1882. CopyMemory( (PVOID)&vendor->versionId.value,
  1883. (PVOID)pVendorInfo ->pVersionNumber->pOctetString,
  1884. pVendorInfo ->pVersionNumber->wOctetStringLength);
  1885. }
  1886. }
  1887. // check to see if entry is in list
  1888. BOOL
  1889. IsInList(
  1890. IN LIST_ENTRY * List,
  1891. IN LIST_ENTRY * Entry
  1892. )
  1893. {
  1894. LIST_ENTRY * Pos;
  1895. for( Pos = List -> Flink; Pos != List; Pos = Pos -> Flink )
  1896. {
  1897. if( Pos == Entry )
  1898. {
  1899. return TRUE;
  1900. }
  1901. }
  1902. return FALSE;
  1903. }
  1904. void WriteProtocolDiscriminator(
  1905. PBUFFERDESCR pBuf,
  1906. DWORD * dwPDULen
  1907. )
  1908. {
  1909. // space for the length byte
  1910. (*dwPDULen)++;
  1911. _ASSERTE( pBuf->dwLength > *dwPDULen );
  1912. *(PDTYPE *)pBuf->pbBuffer = Q931PDVALUE;
  1913. pBuf->pbBuffer += sizeof(PDTYPE);
  1914. }
  1915. //------------------------------------------------------------------------------
  1916. // Write a variable length Q931 call reference. See Q931 section 4.3.
  1917. //------------------------------------------------------------------------------
  1918. void
  1919. WriteCallReference(
  1920. PBUFFERDESCR pBuf,
  1921. WORD * pwCallReference,
  1922. DWORD * pdwPDULen
  1923. )
  1924. {
  1925. int indexI;
  1926. // space for the length byte
  1927. (*pdwPDULen) += 1+ sizeof(WORD);
  1928. _ASSERTE( pBuf->dwLength > *pdwPDULen );
  1929. // the length byte
  1930. *pBuf->pbBuffer = (BYTE)sizeof(WORD);
  1931. pBuf->pbBuffer++;
  1932. for (indexI = 0; indexI < sizeof(WORD); indexI++)
  1933. {
  1934. // Copy the value bytes to the buffer
  1935. *pBuf->pbBuffer =
  1936. (BYTE)(((*pwCallReference) >> ((sizeof(WORD) - 1 -indexI) * 8)) & 0xff);
  1937. pBuf->pbBuffer++;
  1938. }
  1939. }
  1940. void
  1941. FreeCallForwardParams(
  1942. IN PCALLFORWARDPARAMS pCallForwardParams
  1943. )
  1944. {
  1945. LPFORWARDADDRESS pForwardedAddress, pTemp;
  1946. if( pCallForwardParams != NULL )
  1947. {
  1948. if( pCallForwardParams->divertedToAlias.pData != NULL )
  1949. {
  1950. delete pCallForwardParams->divertedToAlias.pData;
  1951. }
  1952. pForwardedAddress = pCallForwardParams->pForwardedAddresses;
  1953. while( pForwardedAddress )
  1954. {
  1955. pTemp = pForwardedAddress->next;
  1956. FreeForwardAddress( pForwardedAddress );
  1957. pForwardedAddress = pTemp;
  1958. }
  1959. delete pCallForwardParams;
  1960. }
  1961. }
  1962. void
  1963. FreeForwardAddress(
  1964. IN LPFORWARDADDRESS pForwardAddress
  1965. )
  1966. {
  1967. if( pForwardAddress != NULL )
  1968. {
  1969. if( pForwardAddress->callerAlias.pData != NULL )
  1970. {
  1971. delete pForwardAddress->callerAlias.pData;
  1972. }
  1973. if( pForwardAddress->divertedToAlias.pData != NULL )
  1974. {
  1975. delete pForwardAddress->divertedToAlias.pData;
  1976. }
  1977. delete pForwardAddress;
  1978. }
  1979. }
  1980. //Replaces first alias item in the alias list with the alias address passed.
  1981. BOOL
  1982. MapAliasItem(
  1983. IN PH323_ALIASNAMES pCalleeAliasNames,
  1984. IN AliasAddress* pAliasAddress )
  1985. {
  1986. int iIndex;
  1987. _ASSERTE( pCalleeAliasNames && pCalleeAliasNames->pItems );
  1988. if( pCalleeAliasNames != NULL )
  1989. {
  1990. switch( pAliasAddress->choice )
  1991. {
  1992. case e164_chosen:
  1993. pCalleeAliasNames->pItems[0].wType = pAliasAddress->choice;
  1994. if( pCalleeAliasNames->pItems[0].pData != NULL )
  1995. {
  1996. delete pCalleeAliasNames->pItems[0].pData;
  1997. }
  1998. pCalleeAliasNames->pItems[0].wDataLength =
  1999. (WORD)strlen( pAliasAddress->u.e164 );
  2000. pCalleeAliasNames->pItems[0].pData =
  2001. new WCHAR[pCalleeAliasNames->pItems[0].wDataLength];
  2002. if( pCalleeAliasNames->pItems[0].pData == NULL )
  2003. {
  2004. return FALSE;
  2005. }
  2006. for( iIndex=0; iIndex < pCalleeAliasNames->pItems[0].wDataLength;
  2007. iIndex++ )
  2008. {
  2009. pCalleeAliasNames->pItems[0].pData[iIndex] =
  2010. pAliasAddress->u.e164[iIndex];
  2011. }
  2012. break;
  2013. case h323_ID_chosen:
  2014. pCalleeAliasNames->pItems[0].wType = pAliasAddress->choice;
  2015. if( pCalleeAliasNames->pItems[0].pData != NULL )
  2016. {
  2017. delete pCalleeAliasNames->pItems[0].pData;
  2018. }
  2019. pCalleeAliasNames->pItems[0].wDataLength =
  2020. (WORD)pAliasAddress->u.h323_ID.length;
  2021. pCalleeAliasNames->pItems[0].pData =
  2022. new WCHAR[pCalleeAliasNames->pItems[0].wDataLength];
  2023. if( pCalleeAliasNames->pItems[0].pData == NULL )
  2024. {
  2025. return FALSE;
  2026. }
  2027. CopyMemory( (PVOID)pCalleeAliasNames->pItems[0].pData,
  2028. (PVOID)pAliasAddress->u.h323_ID.value,
  2029. pCalleeAliasNames->pItems[0].wDataLength );
  2030. break;
  2031. }
  2032. }
  2033. return TRUE;
  2034. }
  2035. //
  2036. //creates a new alias list and copies the first alias item from the given list.
  2037. //
  2038. PH323_ALIASNAMES
  2039. DuplicateAliasName(
  2040. PH323_ALIASNAMES pSrcAliasNames
  2041. )
  2042. {
  2043. PH323_ALIASNAMES pDestAliasNames = new H323_ALIASNAMES;
  2044. if( pDestAliasNames == NULL )
  2045. {
  2046. return NULL;
  2047. }
  2048. ZeroMemory( pDestAliasNames, sizeof(H323_ALIASNAMES) );
  2049. if( !AddAliasItem(
  2050. pDestAliasNames,
  2051. pSrcAliasNames->pItems[0].pData,
  2052. pSrcAliasNames->pItems[0].wType ) )
  2053. {
  2054. delete pDestAliasNames;
  2055. return NULL;
  2056. }
  2057. return pDestAliasNames;
  2058. }