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.

1159 lines
29 KiB

  1. /*++
  2. Copyright (c) 1997 Microsoft Corporation
  3. Module Name:
  4. provider.c
  5. Abstract:
  6. TAPI Service Provider functions related to provider info.
  7. TSPI_providerConfig
  8. TSPI_providerEnumDevices
  9. TSPI_providerFreeDialogInstance
  10. TSPI_providerGenericDialogData
  11. TSPI_providerInit
  12. TSPI_providerInstall
  13. TSPI_providerRemove
  14. TSPI_providerShutdown
  15. TSPI_providerUIIdentify
  16. TUISPI_providerConfig
  17. TUISPI_providerInstall
  18. TUISPI_providerRemove
  19. Environment:
  20. User Mode - Win32
  21. --*/
  22. ///////////////////////////////////////////////////////////////////////////////
  23. // //
  24. // Include files //
  25. // //
  26. ///////////////////////////////////////////////////////////////////////////////
  27. #include "globals.h"
  28. #include "provider.h"
  29. #include "callback.h"
  30. #include "registry.h"
  31. #include "termcaps.h"
  32. #include "version.h"
  33. #include "line.h"
  34. #include "config.h"
  35. ///////////////////////////////////////////////////////////////////////////////
  36. // //
  37. // Global variables //
  38. // //
  39. ///////////////////////////////////////////////////////////////////////////////
  40. DWORD g_dwTSPIVersion = UNINITIALIZED;
  41. DWORD g_dwLineDeviceIDBase = UNINITIALIZED;
  42. DWORD g_dwPermanentProviderID = UNINITIALIZED;
  43. ASYNC_COMPLETION g_pfnCompletionProc = NULL;
  44. LINEEVENT g_pfnLineEventProc = NULL;
  45. HPROVIDER g_hProvider = (HPROVIDER)NULL;
  46. ///////////////////////////////////////////////////////////////////////////////
  47. // //
  48. // Public procedures //
  49. // //
  50. ///////////////////////////////////////////////////////////////////////////////
  51. #if defined(DBG) && defined(DEBUG_CRITICAL_SECTIONS)
  52. VOID
  53. H323LockProvider(
  54. )
  55. /*++
  56. Routine Description:
  57. Locks service provider.
  58. Arguments:
  59. None.
  60. Return Values:
  61. None.
  62. --*/
  63. {
  64. H323DBG((
  65. DEBUG_LEVEL_VERBOSE,
  66. "provider about to be locked.\n"
  67. ));
  68. // lock service provider
  69. EnterCriticalSection(&g_GlobalLock);
  70. H323DBG((
  71. DEBUG_LEVEL_VERBOSE,
  72. "provider locked.\n"
  73. ));
  74. }
  75. VOID
  76. H323UnlockProvider(
  77. )
  78. /*++
  79. Routine Description:
  80. Unlocks service provider.
  81. Arguments:
  82. None.
  83. Return Values:
  84. None.
  85. --*/
  86. {
  87. // unlock service provider
  88. LeaveCriticalSection(&g_GlobalLock);
  89. H323DBG((
  90. DEBUG_LEVEL_VERBOSE,
  91. "provider unlocked.\n"
  92. ));
  93. }
  94. #endif // DBG && DEBUG_CRITICAL_SECTIONS
  95. BOOL
  96. H323IsTSPAlreadyInstalled(
  97. )
  98. /*++
  99. Routine Description:
  100. Searchs registry for previous instance of H323.TSP.
  101. Arguments:
  102. None.
  103. Return Values:
  104. Returns true if TSP already installed.
  105. --*/
  106. {
  107. DWORD i;
  108. HKEY hKey;
  109. LONG lStatus;
  110. DWORD dwNumProviders = 0;
  111. DWORD dwDataSize = sizeof(DWORD);
  112. DWORD dwDataType = REG_DWORD;
  113. LPSTR pszProvidersKey = TAPI_REGKEY_PROVIDERS;
  114. LPSTR pszNumProvidersValue = TAPI_REGVAL_NUMPROVIDERS;
  115. CHAR szName[H323_MAXPATHNAMELEN+1];
  116. CHAR szPath[H323_MAXPATHNAMELEN+1];
  117. // attempt to open key
  118. lStatus = RegOpenKeyEx(
  119. HKEY_LOCAL_MACHINE,
  120. pszProvidersKey,
  121. 0,
  122. KEY_READ,
  123. &hKey
  124. );
  125. // validate status
  126. if (lStatus != NOERROR) {
  127. H323DBG((
  128. DEBUG_LEVEL_WARNING,
  129. "error 0x%08lx opening tapi providers key.\n",
  130. lStatus
  131. ));
  132. // done
  133. return FALSE;
  134. }
  135. // see if installed bit set
  136. lStatus = RegQueryValueEx(
  137. hKey,
  138. pszNumProvidersValue,
  139. 0,
  140. &dwDataType,
  141. (LPBYTE) &dwNumProviders,
  142. &dwDataSize
  143. );
  144. // validate status
  145. if (lStatus != NOERROR) {
  146. H323DBG((
  147. DEBUG_LEVEL_WARNING,
  148. "error 0x%08lx determining number of providers.\n",
  149. lStatus
  150. ));
  151. // release handle
  152. RegCloseKey(hKey);
  153. // done
  154. return FALSE;
  155. }
  156. // loop through each provider
  157. for (i = 0; i < dwNumProviders; i++) {
  158. // construct path to provider name
  159. wsprintf(szName, "ProviderFileName%d", i);
  160. // reinitialize size
  161. dwDataSize = sizeof(szPath);
  162. // query the next name
  163. lStatus = RegQueryValueEx(
  164. hKey,
  165. szName,
  166. 0,
  167. &dwDataType,
  168. szPath,
  169. &dwDataSize
  170. );
  171. // validate status
  172. if (lStatus == NOERROR) {
  173. // upper case
  174. _strupr(szPath);
  175. // compare path string to h323 provider
  176. if (strstr(szPath, H323_TSPDLL) != NULL) {
  177. // release handle
  178. RegCloseKey(hKey);
  179. // done
  180. return TRUE;
  181. }
  182. } else {
  183. H323DBG((
  184. DEBUG_LEVEL_WARNING,
  185. "error 0x%08lx loading %s.\n",
  186. lStatus,
  187. szName
  188. ));
  189. }
  190. }
  191. // release handle
  192. RegCloseKey(hKey);
  193. // done
  194. return FALSE;
  195. }
  196. ///////////////////////////////////////////////////////////////////////////////
  197. // //
  198. // TSPI procedures //
  199. // //
  200. ///////////////////////////////////////////////////////////////////////////////
  201. LONG
  202. TSPIAPI
  203. TSPI_providerCreateLineDevice(
  204. DWORD_PTR dwTempID,
  205. DWORD dwDeviceID
  206. )
  207. /*++
  208. Routine Description:
  209. This function is called by TAPI in response to receipt of a LINE_CREATE
  210. message from the service provider, which allows the dynamic creation of
  211. a new line device.
  212. Arguments:
  213. dwTempID - The temporary device identifier that the service provider
  214. passed to TAPI in the LINE_CREATE message.
  215. dwDeviceID - The device identifier that TAPI assigns to this device if
  216. this function succeeds.
  217. Return Values:
  218. Returns zero if the request is successful or a negative error number if
  219. an error has occurred. Possible return values are:
  220. LINEERR_BADDEVICEID - The specified line device ID is out of range.
  221. LINEERR_NOMEM - Unable to allocate or lock memory.
  222. LINEERR_OPERATIONFAILED - The specified operation failed for unknown
  223. reasons.
  224. --*/
  225. {
  226. PH323_LINE pLine = NULL;
  227. H323DBG((
  228. DEBUG_LEVEL_TRACE,
  229. "creating new device %d (hdLine=0x%08lx).\n",
  230. dwDeviceID,
  231. dwTempID
  232. ));
  233. // lock line device using temporary device id
  234. if (!H323GetLineFromIDAndLock(&pLine, (DWORD)dwTempID)) {
  235. H323DBG((
  236. DEBUG_LEVEL_ERROR,
  237. "invalid temp device id 0x%08lx.\n",
  238. dwTempID
  239. ));
  240. // failure
  241. return LINEERR_BADDEVICEID;
  242. }
  243. // initialize new line device
  244. H323InitializeLine(pLine, dwDeviceID);
  245. // unlock line
  246. H323UnlockLine(pLine);
  247. // success
  248. return NOERROR;
  249. }
  250. LONG
  251. TSPIAPI
  252. TSPI_providerEnumDevices(
  253. DWORD dwPermanentProviderID,
  254. PDWORD pdwNumLines,
  255. PDWORD pdwNumPhones,
  256. HPROVIDER hProvider,
  257. LINEEVENT pfnLineCreateProc,
  258. PHONEEVENT pfnPhoneCreateProc
  259. )
  260. /*++
  261. Routine Description:
  262. TAPI.DLL calls this function before TSPI_providerInit to determine the
  263. number of line and phone devices supported by the service provider.
  264. Arguments:
  265. dwPermanentProviderID - Specifies the permanent ID, unique within the
  266. service providers on this system, of the service provider being
  267. initialized.
  268. pdwNumLines - Specifies a far pointer to a DWORD-sized memory location
  269. into which the service provider must write the number of line devices
  270. it is configured to support. TAPI.DLL initializes the value to zero,
  271. so if the service provider fails to write a different value, the
  272. value 0 is assumed.
  273. pdwNumPhones - Specifies a far pointer to a DWORD-sized memory location
  274. into which the service provider must write the number of phone devices
  275. it is configured to support. TAPI.DLL initializes the value to zero,
  276. so if the service provider fails to write a different value, the
  277. value 0 is assumed.
  278. hProvider - Specifies an opaque DWORD-sized value which uniquely identifies
  279. this instance of this service provider during this execution of the
  280. Windows Telephony environment.
  281. pfnLineCreateProc - Specifies a far pointer to the LINEEVENT callback
  282. procedure supplied by TAPI.DLL. The service provider will use this
  283. function to send LINE_CREATE messages when a new line device needs to
  284. be created. This function should not be called to send a LINE_CREATE
  285. message until after the service provider has returned from the
  286. TSPI_providerInit procedure.
  287. pfnPhoneCreateProc - Specifies a far pointer to the PHONEEVENT callback
  288. procedure supplied by TAPI.DLL. The service provider will use this
  289. function to send PHONE_CREATE messages when a new phone device needs
  290. to be created. This function should not be called to send a
  291. PHONE_CREATE message until after the service provider has returned
  292. from the TSPI_providerInit procedure.
  293. Return Values:
  294. Returns zero if the request is successful or a negative error number if
  295. an error has occurred. Possible return values are:
  296. LINEERR_NOMEM - Unable to allocate or lock memory.
  297. LINEERR_OPERATIONFAILED - The specified operation failed for unknown
  298. reasons.
  299. --*/
  300. {
  301. WSADATA wsaData;
  302. WORD wVersionRequested = H323_WINSOCKVERSION;
  303. UNREFERENCED_PARAMETER(pdwNumPhones); // no phone support
  304. UNREFERENCED_PARAMETER(pfnPhoneCreateProc); // no dynamic phones
  305. UNREFERENCED_PARAMETER(dwPermanentProviderID); // legacy parameter
  306. // initialize winsock stack
  307. WSAStartup(wVersionRequested, &wsaData);
  308. // lock provider
  309. H323LockProvider();
  310. // save provider handle
  311. g_hProvider = hProvider;
  312. // save line create tapi callback
  313. g_pfnLineEventProc = pfnLineCreateProc;
  314. // install defaults
  315. H323SetDefaultConfig();
  316. // load registry parameters
  317. H323GetConfigFromRegistry();
  318. // initialize line table
  319. if (!H323AllocLineTable(&g_pLineTable)) {
  320. // shutdown
  321. WSACleanup();
  322. // unlock provider
  323. H323UnlockProvider();
  324. // could not create line table
  325. return LINEERR_OPERATIONFAILED;
  326. }
  327. H323DBG((
  328. DEBUG_LEVEL_VERBOSE,
  329. "service provider supports %d line(s).\n",
  330. g_pLineTable->dwNumInUse
  331. ));
  332. // report number of interfaces
  333. *pdwNumLines = g_pLineTable->dwNumInUse;
  334. // unlock provider
  335. H323UnlockProvider();
  336. // success
  337. return NOERROR;
  338. }
  339. LONG
  340. TSPIAPI
  341. TSPI_providerInit(
  342. DWORD dwTSPIVersion,
  343. DWORD dwPermanentProviderID,
  344. DWORD dwLineDeviceIDBase,
  345. DWORD dwPhoneDeviceIDBase,
  346. DWORD_PTR dwNumLines,
  347. DWORD_PTR dwNumPhones,
  348. ASYNC_COMPLETION pfnCompletionProc,
  349. LPDWORD pdwTSPIOptions
  350. )
  351. /*++
  352. Routine Description:
  353. Initializes the service provider, also giving it parameters required for
  354. subsequent operation.
  355. This function is guaranteed to be called before any of the other functions
  356. prefixed with TSPI_line or TSPI_phone except TSPI_lineNegotiateTSPIVersion.
  357. It is strictly paired with a subsequent call to TSPI_providerShutdown. It
  358. is the caller's reponsibility to ensure proper pairing.
  359. Note that a service provider should perform as many consistency checks as
  360. is practical at the time TSPI_providerInit is called to ensure that it is
  361. ready to run. Some consistency or installation errors, however, may not be
  362. detectable until the operation is attempted. The error LINEERR_NODRIVER can
  363. be used to report such non-specific errors at the time they are detected.
  364. There is no directly corresponding function at the TAPI level. At that
  365. level, multiple different usage instances can be outstanding, with an
  366. "application handle" returned to identify the instance in subsequent
  367. operations. At the TSPI level, the interface architecture supports only a
  368. single usage instance for each distinct service provider.
  369. A new parameter, lpdwTSPIOptions, is added to this function. This parameter
  370. allows the service provider to return bits indicating optional behaviors
  371. desired of TAPI. TAPI sets the options DWORD to 0 before calling
  372. TSPI_providerInit, so if the service provider doesn't want any of these
  373. options, it can just leave the DWORD set to 0.
  374. At this time, only one bit is defined to be returned through this pointer:
  375. LINETSPIOPTION_NONREENTRANT. The service provider sets this bit if it is
  376. not designed for fully pre-emptive, multithreaded, multitasking,
  377. multiprocessor operation (e.g., updating of global data protected by
  378. mutexes). When this bit is set, TAPI will only make one call at a time to
  379. the service provider; it will not call any other entry point, nor that
  380. entry point again, until the service provider returns from the original
  381. function call. Without this bit set, TAPI may call into multiple service
  382. provider entry points, including multiple times to the same entry point,
  383. simultaneously (actually simultaneously in a multiprocessor system). Note:
  384. TAPI will not serialize access to TSPI functions that display a dialog
  385. (TUISPI_lineConfigDialog, TUISPI_lineConfigDialogEdit,
  386. TUISPI_phoneConfigDialog, TUISPI_providerConfig, TUISPI_providerInstall,
  387. TUISPI_providerRemove) so that they do not block other TSPI functions
  388. from being called; the service provider must include internal protection
  389. on these functions.
  390. Arguments:
  391. dwTSPIVersion - Specifies the version of the TSPI definition under which
  392. this function must operate. The caller may use
  393. TSPI_lineNegotiateTSPIVersion with the special dwDeviceID
  394. INITIALIZE_NEGOTIATION to negotiate a version that is guaranteed to be
  395. acceptible to the service provider.
  396. dwPermanentProviderID - Specifies the permanent ID, unique within the
  397. service providers on this system, of the service provider being
  398. initialized.
  399. dwLineDeviceIDBase - Specifies the lowest device ID for the line devices
  400. supported by this service provider.
  401. dwPhoneDeviceIDBase - Specifies the lowest device ID for the phone devices
  402. supported by this service provider.
  403. dwNumLines - Specifies how many line devices this service provider
  404. supports.
  405. dwNumPhones - Specifies how many line devices this service provider
  406. supports.
  407. pfnCompletionProc - Specifies the procedure the service provider calls to
  408. report completion of all asynchronously operating procedures on line
  409. and phone devices.
  410. pdwTSPIOptions - A pointer to a DWORD-sized memory location, into which
  411. the service provider may write a value specifying LINETSPIOPTIONS_
  412. values.
  413. Return Values:
  414. Returns zero if the function is successful, or a negative error number if
  415. an error has occurred. Possible return values are as follows:
  416. LINEERR_INCOMPATIBLEAPIVERSION - The application requested an API
  417. version or version range that is either incompatible or cannot be
  418. supported by the Telephony API implementation and/or corresponding
  419. service provider.
  420. LINEERR_NOMEM - Unable to allocate or lock memory.
  421. LINEERR_OPERATIONFAILED - The specified operation failed for unknown
  422. reasons.
  423. LINEERR_RESOURCEUNAVAIL - Insufficient resources to complete the
  424. operation.
  425. --*/
  426. {
  427. UNREFERENCED_PARAMETER(dwNumLines); // legacy parameter
  428. UNREFERENCED_PARAMETER(dwNumPhones); // legacy parameter
  429. UNREFERENCED_PARAMETER(dwPhoneDeviceIDBase); // no phone support
  430. UNREFERENCED_PARAMETER(pdwTSPIOptions); // already thread-safe
  431. H323DBG((
  432. DEBUG_LEVEL_TRACE,
  433. "initializing service provider.\n"
  434. ));
  435. // make sure this is a version we support
  436. if (!H323ValidateTSPIVersion(dwTSPIVersion)) {
  437. // incompatible api version
  438. return LINEERR_INCOMPATIBLEAPIVERSION;
  439. }
  440. // lock provider
  441. H323LockProvider();
  442. // initialize caps
  443. InitializeTermCaps();
  444. // initialize line table using device id base
  445. if (!H323InitializeLineTable(g_pLineTable, dwLineDeviceIDBase)) {
  446. // unlock provider
  447. H323UnlockProvider();
  448. // could not update lines
  449. return LINEERR_OPERATIONFAILED;
  450. }
  451. // start callback thread
  452. if (!H323StartCallbackThread()) {
  453. // unlock provider
  454. H323UnlockProvider();
  455. // could not start thread
  456. return LINEERR_OPERATIONFAILED;
  457. }
  458. // save global service provider info
  459. g_dwTSPIVersion = dwTSPIVersion;
  460. g_pfnCompletionProc = pfnCompletionProc;
  461. g_dwLineDeviceIDBase = dwLineDeviceIDBase;
  462. g_dwPermanentProviderID = dwPermanentProviderID;
  463. // unlock provider
  464. H323UnlockProvider();
  465. // success
  466. return NOERROR;
  467. }
  468. LONG
  469. TSPIAPI
  470. TSPI_providerShutdown(
  471. DWORD dwTSPIVersion,
  472. DWORD dwPermanentProviderID
  473. )
  474. /*++
  475. Routine Description:
  476. Shuts down the service provider. The service provider should terminate
  477. any activities it has in progress and release any resources it has
  478. allocated.
  479. Arguments:
  480. dwTSPIVersion - Specifies the version of the TSPI definition under which
  481. this function must operate. The caller may use
  482. TSPI_lineNegotiateTSPIVersion or TSPI_phoneNegotiateTSPIVersion with
  483. the special dwDeviceID INITIALIZE_NEGOTIATION to negotiate a version
  484. that is guaranteed to be acceptible to the service provider.
  485. dwPermanentProviderID - Specifies the permanent ID, unique within the
  486. service providers on this system, of the service provider being
  487. shut down.
  488. Return Values:
  489. Returns zero if the function is successful, or a negative error number
  490. if an error has occurred. Possible return values are as follows:
  491. LINEERR_INCOMPATIBLEAPIVERSION - The application requested an API
  492. version or version range that is either incompatible or cannot be
  493. supported by the Telephony API implementation and/or corresponding
  494. service provider.
  495. LINEERR_NOMEM - Unable to allocate or lock memory.
  496. LINEERR_OPERATIONFAILED - The specified operation failed for unknown
  497. reasons.
  498. --*/
  499. {
  500. UNREFERENCED_PARAMETER(dwPermanentProviderID); // legacy parameter
  501. // make sure this is a version we support
  502. if (!H323ValidateTSPIVersion(dwTSPIVersion)) {
  503. // failure
  504. return LINEERR_INCOMPATIBLEAPIVERSION;
  505. }
  506. // lock provider
  507. H323LockProvider();
  508. // close open line devices
  509. if( g_pLineTable ) {
  510. if (!H323CloseLineTable(g_pLineTable)) {
  511. // unlock provider
  512. H323UnlockProvider();
  513. // failure
  514. return LINEERR_OPERATIONFAILED;
  515. }
  516. }
  517. // stop callback thread last
  518. if (!H323StopCallbackThread()) {
  519. // unlock provider
  520. H323UnlockProvider();
  521. // could not stop thread
  522. return LINEERR_OPERATIONFAILED;
  523. }
  524. // release memory for line devices
  525. if (!H323FreeLineTable(g_pLineTable)) {
  526. // unlock provider
  527. H323UnlockProvider();
  528. // failure
  529. return LINEERR_OPERATIONFAILED;
  530. }
  531. // shutdown
  532. WSACleanup();
  533. // re-initialize
  534. g_pLineTable = NULL;
  535. // unlock provider
  536. H323UnlockProvider();
  537. // success
  538. return NOERROR;
  539. }
  540. LONG
  541. TSPIAPI
  542. TSPI_providerInstall(
  543. HWND hwndOwner,
  544. DWORD dwPermanentProviderID
  545. )
  546. /*++
  547. Routine Description:
  548. The TSPI_providerInstall function is obsolete. TAPI version 1.4
  549. or earlier service providers can implement this TSPI function.
  550. TAPI version 2.0 or later TSPs implement TUISPI_providerInstall.
  551. Arguments:
  552. hwndOwner - The handle of the parent window in which the function
  553. can create any dialog box windows that are required during
  554. installation.
  555. dwPermanentProviderID - The service provider's permanent provider
  556. identifier.
  557. Return Values:
  558. Always returns NOERROR.
  559. --*/
  560. {
  561. UNREFERENCED_PARAMETER(hwndOwner);
  562. UNREFERENCED_PARAMETER(dwPermanentProviderID);
  563. // success
  564. return NOERROR;
  565. }
  566. LONG
  567. TSPIAPI
  568. TSPI_providerRemove(
  569. HWND hwndOwner,
  570. DWORD dwPermanentProviderID
  571. )
  572. /*++
  573. Routine Description:
  574. The TSPI_providerRemove function is obsolete. TAPI version 1.4 or
  575. earlier service providers can implement this TSPI function. TAPI
  576. version 2.0 or later TSPs implement TUISPI_providerRemove.
  577. Arguments:
  578. hwndOwner - The handle of the parent window in which the function
  579. can create any dialog box windows that are required during
  580. installation.
  581. dwPermanentProviderID - The service provider's permanent provider
  582. identifier.
  583. Return Values:
  584. Always returns NOERROR.
  585. --*/
  586. {
  587. UNREFERENCED_PARAMETER(hwndOwner);
  588. UNREFERENCED_PARAMETER(dwPermanentProviderID);
  589. // success
  590. return NOERROR;
  591. }
  592. LONG
  593. TSPIAPI
  594. TSPI_providerUIIdentify(
  595. LPWSTR pwszUIDLLName
  596. )
  597. /*++
  598. Routine Description:
  599. The TSPI_providerUIIdentify function extracts from the service
  600. provider the fully qualified path to load the service provider's
  601. UI DLL component.
  602. Implementation is mandatory if the service provider implements
  603. any UI DLL functions.
  604. Arguments:
  605. pwszUIDLLName - Pointer to a block of memory at least MAX_PATH
  606. in length, into which the service provider must copy a NULL-
  607. terminated string specifying the fully-qualified path for the
  608. DLL containing the service provider functions which must execute
  609. in the process of the calling application.
  610. Return Values:
  611. Always returns NOERROR.
  612. --*/
  613. {
  614. // copy name of our dll as ui dll
  615. lstrcpyW(pwszUIDLLName,H323_UIDLL);
  616. // success
  617. return NOERROR;
  618. }
  619. LONG
  620. TSPIAPI
  621. TUISPI_providerInstall(
  622. TUISPIDLLCALLBACK pfnUIDLLCallback,
  623. HWND hwndOwner,
  624. DWORD dwPermanentProviderID
  625. )
  626. /*++
  627. Routine Description:
  628. Implementation of the TUISPI_providerInstall function is the
  629. service provider's opportunity to install any additional
  630. "pieces" of the provider into the right directories (or at
  631. least verifying that they're there) and set up registry entries
  632. the provider needs.
  633. Arguments:
  634. pfnUIDLLCallback - Pointer to a function the UI DLL can call to
  635. communicate with the service provider DLL to obtain information
  636. needed to display the dialog box.
  637. hwndOwner - The handle of the parent window in which the function
  638. can create any dialog box windows that are required during
  639. installation.
  640. dwPermanentProviderID - The service provider's permanent provider
  641. identifier.
  642. Return Values:
  643. Returns zero if the function is successful, or a negative error number
  644. if an error has occurred. Possible return values are as follows:
  645. LINEERR_NOMEM - Unable to allocate or lock memory.
  646. LINEERR_NOMULTIPLEINSTANCE - A telephony service provider which
  647. does not support multiple instances is listed more than once
  648. in the [Providers] section in the registry. The application
  649. LINEERR_OPERATIONFAILED - The specified operation failed for unknown
  650. reasons.
  651. --*/
  652. {
  653. HKEY hKey;
  654. HKEY hKeyTSP;
  655. LONG lStatus;
  656. LPSTR pszKey;
  657. UNREFERENCED_PARAMETER(pfnUIDLLCallback);
  658. UNREFERENCED_PARAMETER(hwndOwner);
  659. UNREFERENCED_PARAMETER(dwPermanentProviderID);
  660. // check for previous instance
  661. if (H323IsTSPAlreadyInstalled()) {
  662. // cannot be installed twice
  663. return LINEERR_NOMULTIPLEINSTANCE;
  664. }
  665. // set key to h323
  666. pszKey = H323_REGKEY_ROOT;
  667. // attempt to open key
  668. lStatus = RegOpenKeyEx(
  669. HKEY_LOCAL_MACHINE,
  670. pszKey,
  671. 0,
  672. KEY_READ,
  673. &hKey
  674. );
  675. // validate status
  676. if (lStatus == NOERROR) {
  677. H323DBG((
  678. DEBUG_LEVEL_TRACE,
  679. "successfully installed H.323 provider.\n"
  680. ));
  681. // release handle
  682. RegCloseKey(hKey);
  683. // success
  684. return NOERROR;
  685. }
  686. // set key to windows
  687. pszKey = WINDOWS_REGKEY_ROOT;
  688. // attempt to open key
  689. lStatus = RegOpenKeyEx(
  690. HKEY_LOCAL_MACHINE,
  691. pszKey,
  692. 0,
  693. KEY_WRITE,
  694. &hKey
  695. );
  696. // validate status
  697. if (lStatus != NOERROR) {
  698. H323DBG((
  699. DEBUG_LEVEL_ERROR,
  700. "error 0x%08lx opening windows registry key.\n",
  701. lStatus
  702. ));
  703. // operation failed
  704. return LINEERR_OPERATIONFAILED;
  705. }
  706. // attempt to create key
  707. lStatus = RegCreateKey(
  708. hKey,
  709. H323_SUBKEY,
  710. &hKeyTSP
  711. );
  712. // validate status
  713. if (lStatus != NOERROR) {
  714. H323DBG((
  715. DEBUG_LEVEL_ERROR,
  716. "error 0x%08lx creating tsp registry key.\n",
  717. lStatus
  718. ));
  719. // release handle
  720. RegCloseKey(hKey);
  721. // operation failed
  722. return LINEERR_OPERATIONFAILED;
  723. }
  724. H323DBG((
  725. DEBUG_LEVEL_TRACE,
  726. "successfully installed H.323 provider.\n"
  727. ));
  728. // release handle
  729. RegCloseKey(hKeyTSP);
  730. // release handle
  731. RegCloseKey(hKey);
  732. // success
  733. return NOERROR;
  734. }
  735. LONG
  736. TSPIAPI
  737. TUISPI_providerRemove(
  738. TUISPIDLLCALLBACK pfnUIDLLCallback,
  739. HWND hwndOwner,
  740. DWORD dwPermanentProviderID
  741. )
  742. /*++
  743. Routine Description:
  744. The TUISPI_providerRemove function asks the user to confirm
  745. elimination of the service provider.
  746. It is the responsibility of the service provider to remove any
  747. registry entries that the service provider added at addProvider
  748. time, as well as any other modules and files that are no longer
  749. needed.
  750. Arguments:
  751. pfnUIDLLCallback - Pointer to a function the UI DLL can call to
  752. communicate with the service provider DLL to obtain information
  753. needed to display the dialog box.
  754. hwndOwner - The handle of the parent window in which the function
  755. can create any dialog box windows that are required during
  756. removal.
  757. dwPermanentProviderID - The service provider's permanent provider
  758. identifier.
  759. Return Values:
  760. Returns zero if the function is successful, or a negative error number
  761. if an error has occurred. Possible return values are as follows:
  762. LINEERR_NOMEM - Unable to allocate or lock memory.
  763. LINEERR_OPERATIONFAILED - The specified operation failed for unknown
  764. reasons.
  765. --*/
  766. {
  767. HKEY hKey;
  768. LONG lStatus;
  769. LPSTR pszKey;
  770. UNREFERENCED_PARAMETER(pfnUIDLLCallback);
  771. UNREFERENCED_PARAMETER(hwndOwner);
  772. UNREFERENCED_PARAMETER(dwPermanentProviderID);
  773. // set key to h323
  774. pszKey = H323_REGKEY_ROOT;
  775. // attempt to open key
  776. lStatus = RegOpenKeyEx(
  777. HKEY_LOCAL_MACHINE,
  778. pszKey,
  779. 0,
  780. KEY_READ,
  781. &hKey
  782. );
  783. // validate status
  784. if (lStatus != NOERROR) {
  785. H323DBG((
  786. DEBUG_LEVEL_TRACE,
  787. "successfully removed H.323 provider.\n"
  788. ));
  789. // success
  790. return NOERROR;
  791. }
  792. // release handle
  793. RegCloseKey(hKey);
  794. // set key to windows
  795. pszKey = WINDOWS_REGKEY_ROOT;
  796. // attempt to open key
  797. lStatus = RegOpenKeyEx(
  798. HKEY_LOCAL_MACHINE,
  799. pszKey,
  800. 0,
  801. KEY_WRITE,
  802. &hKey
  803. );
  804. // validate status
  805. if (lStatus != NOERROR) {
  806. H323DBG((
  807. DEBUG_LEVEL_ERROR,
  808. "error 0x%08lx opening windows registry key.\n",
  809. lStatus
  810. ));
  811. // operation failed
  812. return LINEERR_OPERATIONFAILED;
  813. }
  814. // attempt to delete key
  815. lStatus = RegDeleteKey(
  816. hKey,
  817. H323_SUBKEY
  818. );
  819. // validate status
  820. if (lStatus != NOERROR) {
  821. H323DBG((
  822. DEBUG_LEVEL_ERROR,
  823. "error 0x%08lx deleting tsp registry key.\n",
  824. lStatus
  825. ));
  826. // release handle
  827. RegCloseKey(hKey);
  828. // operation failed
  829. return LINEERR_OPERATIONFAILED;
  830. }
  831. H323DBG((
  832. DEBUG_LEVEL_TRACE,
  833. "successfully removed H.323 provider.\n"
  834. ));
  835. // release handle
  836. RegCloseKey(hKey);
  837. // success
  838. return NOERROR;
  839. }
  840.