Leaked source code of windows server 2003
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.

1519 lines
33 KiB

  1. /*++
  2. Copyright (c) 1998-99 Microsoft Corporation
  3. Module Name:
  4. store.c
  5. Abstract:
  6. Revision History:
  7. --*/
  8. #include <windows.h>
  9. #ifndef OS_WINCE
  10. #include <stdio.h>
  11. #endif // OS_WINCE
  12. #include <stdlib.h>
  13. #ifndef OS_WINCE
  14. #include <reglic.h>
  15. #endif
  16. #ifdef OS_WINCE
  17. #include "ceconfig.h"
  18. #endif
  19. #include "store.h"
  20. #define MAX_LEN 256
  21. #define BASE_STORE TEXT("Software\\Microsoft\\MSLicensing\\")
  22. #define STORE TEXT("Store")
  23. #define COMMON_STORE TEXT("Software\\Microsoft\\MSLicensing\\Store")
  24. #define MAX_SIZE_LICENSESTORE 2048
  25. #define MAX_NUM_LICENSESTORE 20
  26. #define MAX_LICENSESTORE_NAME 25
  27. #ifdef OS_WINCE
  28. typedef HANDLE STORE_HANDLE;
  29. #ifdef OS_WINCE
  30. //If gbFlushHKLM true, RegFlushKey is called in CCC::CC_OnDisconnected
  31. //Since the penalty for RegFlushKey is high on CE, we dont do it immediately
  32. BOOL gbFlushHKLM = FALSE;
  33. #endif
  34. //
  35. // WriteLiceneToStore() and ReadLicenseFromStore is only used by WINCE
  36. //
  37. DWORD
  38. CALL_TYPE
  39. WriteLicenseToStore(
  40. IN STORE_HANDLE hStore,
  41. IN BYTE FAR * pbLicense,
  42. IN DWORD cbLicense
  43. )
  44. /*++
  45. --*/
  46. {
  47. DWORD dwStatus = ERROR_SUCCESS;
  48. DWORD dwIndex;
  49. TCHAR szValueName[MAX_LICENSESTORE_NAME];
  50. DWORD dwCount;
  51. dwIndex = 0;
  52. while( cbLicense > 0 )
  53. {
  54. if( dwIndex > 0 )
  55. {
  56. wsprintf(
  57. szValueName,
  58. TEXT("ClientLicense%03d"),
  59. dwIndex
  60. );
  61. }
  62. else
  63. {
  64. lstrcpy(
  65. szValueName,
  66. TEXT("ClientLicense")
  67. );
  68. }
  69. dwIndex++;
  70. // must have a reason for this
  71. RegDeleteValue(
  72. (HKEY)hStore,
  73. szValueName
  74. );
  75. dwCount = (cbLicense > MAX_SIZE_LICENSESTORE) ? MAX_SIZE_LICENSESTORE : cbLicense;
  76. dwStatus = RegSetValueEx(
  77. (HKEY)hStore,
  78. szValueName,
  79. 0,
  80. REG_BINARY,
  81. pbLicense,
  82. dwCount
  83. );
  84. if( ERROR_SUCCESS != dwStatus )
  85. {
  86. break;
  87. }
  88. cbLicense -= dwCount;
  89. pbLicense += dwCount;
  90. }
  91. if( ERROR_SUCCESS == dwStatus )
  92. {
  93. //
  94. // Delete next store
  95. wsprintf(
  96. szValueName,
  97. TEXT("ClientLicense%03d"),
  98. dwIndex
  99. );
  100. RegDeleteValue(
  101. (HKEY)hStore,
  102. szValueName
  103. );
  104. #ifdef OS_WINCE
  105. gbFlushHKLM = TRUE;
  106. #endif
  107. }
  108. #ifdef OS_WINCE
  109. else
  110. {
  111. DWORD cbValName;
  112. cbValName = MAX_LICENSESTORE_NAME;
  113. while ( (ERROR_SUCCESS == RegEnumValue(
  114. (HKEY)hStore,
  115. 0,
  116. szValueName,
  117. &cbValName,
  118. NULL,
  119. NULL,
  120. NULL,
  121. NULL
  122. ) ) &&
  123. (cbValName < MAX_LICENSESTORE_NAME)
  124. )
  125. {
  126. RegDeleteValue(
  127. (HKEY) hStore,
  128. szValueName
  129. );
  130. cbValName = MAX_LICENSESTORE_NAME;
  131. }
  132. }
  133. #endif
  134. return dwStatus;
  135. }
  136. DWORD
  137. CALL_TYPE
  138. ReadLicenseFromStore(
  139. IN STORE_HANDLE hStore,
  140. IN BYTE FAR * pbLicense,
  141. IN DWORD FAR * pcbLicense
  142. )
  143. /*++
  144. --*/
  145. {
  146. DWORD dwStatus;
  147. DWORD dwIndex;
  148. TCHAR szValueName[MAX_LICENSESTORE_NAME];
  149. BYTE FAR * pbReadStart;
  150. DWORD cbReadSize;
  151. LONG dwSize;
  152. dwIndex = 0;
  153. dwSize = (LONG)*pcbLicense;
  154. *pcbLicense = 0;
  155. pbReadStart = pbLicense;
  156. for(;;)
  157. {
  158. if( pbLicense != NULL )
  159. {
  160. if( dwSize < 0 )
  161. {
  162. // don't continue on reading,
  163. // size of buffer is too small, should
  164. // query size first.
  165. dwStatus = ERROR_INSUFFICIENT_BUFFER;
  166. break;
  167. }
  168. }
  169. else if( dwIndex >= MAX_NUM_LICENSESTORE )
  170. {
  171. // License is way to big, treat it as error
  172. dwStatus = LSSTAT_ERROR;
  173. break;
  174. }
  175. if( dwIndex > 0 )
  176. {
  177. wsprintf(
  178. szValueName,
  179. TEXT("ClientLicense%03d"),
  180. dwIndex
  181. );
  182. }
  183. else
  184. {
  185. lstrcpy(
  186. szValueName,
  187. TEXT("ClientLicense")
  188. );
  189. }
  190. dwIndex++;
  191. cbReadSize = ( pbLicense ) ? dwSize : 0;
  192. dwStatus = RegQueryValueEx(
  193. (HKEY)hStore,
  194. szValueName,
  195. NULL,
  196. NULL,
  197. ( pbLicense ) ? pbReadStart : NULL,
  198. &cbReadSize
  199. );
  200. if( ERROR_SUCCESS != dwStatus )
  201. {
  202. if( dwIndex != 0 )
  203. {
  204. //
  205. // Ignore error if can't read from next store
  206. //
  207. dwStatus = ERROR_SUCCESS;
  208. }
  209. break;
  210. }
  211. (*pcbLicense) += cbReadSize;
  212. if( pbLicense )
  213. {
  214. pbReadStart += cbReadSize;
  215. dwSize -= cbReadSize;
  216. }
  217. }
  218. return dwStatus;
  219. }
  220. #endif // OS_WINCE
  221. LS_STATUS
  222. CALL_TYPE
  223. LSOpenLicenseStore(
  224. OUT HANDLE *phStore, //The handle of the store
  225. IN LPCTSTR szStoreName, //Optional store Name
  226. IN BOOL fReadOnly //whether to open read-only
  227. )
  228. {
  229. LS_STATUS lsResult = LSSTAT_ERROR;
  230. LPTSTR szKey = NULL;
  231. HKEY hKey;
  232. DWORD dwDisposition = 0, dwRetCode;
  233. if (phStore==NULL)
  234. return LSSTAT_INVALID_HANDLE;
  235. //If any store name is provided, try opening the store
  236. if(szStoreName)
  237. {
  238. if( NULL == (szKey = (LPTSTR)malloc( 2*( lstrlen(BASE_STORE) + lstrlen(szStoreName) + 1 ) ) ) )
  239. {
  240. lsResult = LSSTAT_OUT_OF_MEMORY;
  241. goto ErrorReturn;
  242. }
  243. lstrcpy(szKey, BASE_STORE);
  244. lstrcat(szKey, szStoreName);
  245. }
  246. //Open standard store
  247. else
  248. {
  249. szKey = COMMON_STORE;
  250. }
  251. //
  252. // try and open the key. If we cannot open the key, then create the key
  253. //
  254. dwRetCode = RegOpenKeyEx( HKEY_LOCAL_MACHINE,
  255. szKey,
  256. 0,
  257. fReadOnly ? KEY_READ : KEY_READ | KEY_WRITE,
  258. &hKey );
  259. if( ERROR_SUCCESS != dwRetCode )
  260. {
  261. HKEY hKeyBase;
  262. dwRetCode = RegCreateKeyEx( HKEY_LOCAL_MACHINE,
  263. #ifndef OS_WINCE
  264. BASE_STORE,
  265. #else
  266. szKey,
  267. #endif
  268. 0,
  269. TEXT("License Store"),
  270. REG_OPTION_NON_VOLATILE,
  271. KEY_READ | KEY_WRITE,
  272. NULL,
  273. &hKeyBase,
  274. &dwDisposition );
  275. if (ERROR_SUCCESS == dwRetCode)
  276. {
  277. #ifndef OS_WINCE
  278. // Set the proper ACL on the key; ignore errors
  279. SetupMSLicensingKey();
  280. #endif
  281. dwRetCode = RegCreateKeyEx( hKeyBase,
  282. (szStoreName != NULL) ? szStoreName : STORE,
  283. 0,
  284. TEXT("License Store"),
  285. REG_OPTION_NON_VOLATILE,
  286. KEY_ALL_ACCESS,
  287. NULL,
  288. &hKey,
  289. &dwDisposition );
  290. RegCloseKey(hKeyBase);
  291. }
  292. }
  293. if( ERROR_SUCCESS == dwRetCode )
  294. {
  295. *phStore = ( HANDLE )hKey;
  296. lsResult = LSSTAT_SUCCESS;
  297. }
  298. else
  299. {
  300. *phStore = NULL;
  301. }
  302. CommonReturn:
  303. if (szKey)
  304. {
  305. // We only allocate memory for szKey if szStoreName wasn't NULL
  306. if (szStoreName)
  307. free(szKey);
  308. }
  309. return lsResult;
  310. ErrorReturn:
  311. *phStore = NULL;
  312. goto CommonReturn;
  313. }
  314. //Closes an open store
  315. LS_STATUS
  316. CALL_TYPE
  317. LSCloseLicenseStore(
  318. IN HANDLE hStore //Handle of the store to be closed!
  319. )
  320. {
  321. LS_STATUS lsResult = LSSTAT_ERROR;
  322. HKEY hKey = NULL;
  323. if(hStore==NULL)
  324. return lsResult;
  325. hKey = (HKEY)hStore;
  326. if(hKey)
  327. {
  328. RegCloseKey(hKey);
  329. hKey = NULL;
  330. lsResult = LSSTAT_SUCCESS;
  331. }
  332. return lsResult;
  333. }
  334. /*
  335. Here we do not check any value. We do not even check if a license with same attributes present
  336. or not. This is to make the store functionality simpler. We assume, the higher level protocol
  337. will take care of that
  338. */
  339. //Add or updates/replaces license against a given LSINDEX in an open store
  340. //pointed by hStore
  341. LS_STATUS
  342. CALL_TYPE
  343. LSAddLicenseToStore(
  344. IN HANDLE hStore, //Handle of a open store
  345. IN DWORD dwFlags,//Flags either add or replace
  346. IN PLSINDEX plsiName, //Index against which License is added
  347. IN BYTE FAR * pbLicenseInfo, //License info to be added
  348. IN DWORD cbLicenseInfo // size of the License info blob
  349. )
  350. {
  351. LS_STATUS lsResult = LSSTAT_ERROR;
  352. HANDLE hLicense = NULL;
  353. HKEY hTempKey = NULL;
  354. DWORD dwRetCode;
  355. if( (hStore == NULL) ||
  356. (plsiName == NULL) ||
  357. (plsiName->pbScope == NULL) ||
  358. (plsiName->pbCompany == NULL) ||
  359. (plsiName->pbProductID == NULL) ||
  360. (pbLicenseInfo == NULL) ||
  361. (cbLicenseInfo == 0) )
  362. return LSSTAT_INVALID_HANDLE;
  363. lsResult = LSOpenLicenseHandle(hStore, FALSE, plsiName, &hLicense);
  364. switch(lsResult)
  365. {
  366. case LSSTAT_SUCCESS:
  367. if(dwFlags == LS_REPLACE_LICENSE_OK)
  368. {
  369. #ifndef OS_WINCE
  370. RegDeleteValue((HKEY)hLicense, TEXT("ClientLicense"));
  371. //Set the License Info value
  372. if( ERROR_SUCCESS != RegSetValueEx(
  373. (HKEY)hLicense,
  374. TEXT("ClientLicense"),
  375. 0,
  376. REG_BINARY,
  377. pbLicenseInfo,
  378. cbLicenseInfo
  379. ) )
  380. {
  381. lsResult = LSSTAT_ERROR;
  382. goto ErrorReturn;
  383. }
  384. #else
  385. if( ERROR_SUCCESS != WriteLicenseToStore(
  386. (STORE_HANDLE)hLicense,
  387. pbLicenseInfo,
  388. cbLicenseInfo ) )
  389. {
  390. lsResult = LSSTAT_ERROR;
  391. goto ErrorReturn;
  392. }
  393. #endif
  394. }
  395. else
  396. {
  397. lsResult = LSSTAT_LICENSE_EXISTS;
  398. goto ErrorReturn;
  399. }
  400. break;
  401. case LSSTAT_LICENSE_NOT_FOUND:
  402. {
  403. DWORD dwIndex, dwDisposition = 0;
  404. TCHAR szAddKey[MAX_LEN];
  405. for(dwIndex = 0; ; dwIndex ++)
  406. {
  407. // Open iterative license names until we fail to
  408. // determine a free spot
  409. wsprintf(szAddKey, TEXT("LICENSE%03d"), dwIndex);
  410. #ifdef OS_WINCE
  411. if( ERROR_SUCCESS != RegOpenKeyEx((HKEY)hStore, szAddKey, 0, 0, &hTempKey) )
  412. #else // !OS_WINCE
  413. if( ERROR_SUCCESS != RegOpenKeyEx((HKEY)hStore, szAddKey, 0, KEY_READ | KEY_WRITE, &hTempKey) )
  414. #endif // OS_WINCE
  415. break;
  416. else if(hTempKey)
  417. {
  418. RegCloseKey(hTempKey);
  419. hTempKey = NULL;
  420. }
  421. }
  422. //
  423. // try and open the key. If we cannot open the key, then create the key
  424. //
  425. dwRetCode = RegOpenKeyEx( ( HKEY )hStore,
  426. szAddKey,
  427. 0,
  428. KEY_READ | KEY_WRITE,
  429. &hTempKey );
  430. if( ERROR_SUCCESS != dwRetCode )
  431. {
  432. dwRetCode = RegCreateKeyEx( ( HKEY )hStore,
  433. szAddKey,
  434. 0,
  435. NULL,
  436. REG_OPTION_NON_VOLATILE,
  437. KEY_READ | KEY_WRITE,
  438. NULL,
  439. &hTempKey,
  440. &dwDisposition );
  441. }
  442. else
  443. {
  444. //
  445. // Indicate that we have opened an existing key successfully
  446. //
  447. dwDisposition = REG_OPENED_EXISTING_KEY;
  448. }
  449. if( ERROR_SUCCESS == dwRetCode )
  450. {
  451. if(dwDisposition == REG_CREATED_NEW_KEY)
  452. {
  453. //Set the Scope Value in binary format
  454. if( ERROR_SUCCESS != RegSetValueEx(
  455. hTempKey,
  456. TEXT("LicenseScope"),
  457. 0,
  458. REG_BINARY,
  459. plsiName->pbScope,
  460. plsiName->cbScope
  461. ) )
  462. {
  463. lsResult = LSSTAT_ERROR;
  464. goto ErrorReturn;
  465. }
  466. //Set Company Name Value
  467. if( ERROR_SUCCESS != RegSetValueEx(
  468. hTempKey,
  469. TEXT("CompanyName"),
  470. 0,
  471. REG_BINARY,
  472. plsiName->pbCompany,
  473. plsiName->cbCompany
  474. ) )
  475. {
  476. lsResult = LSSTAT_ERROR;
  477. goto ErrorReturn;
  478. }
  479. //Set Product Info
  480. if( ERROR_SUCCESS != RegSetValueEx(
  481. hTempKey,
  482. TEXT("ProductID"),
  483. 0,
  484. REG_BINARY,
  485. plsiName->pbProductID,
  486. plsiName->cbProductID
  487. ) )
  488. {
  489. lsResult = LSSTAT_ERROR;
  490. goto ErrorReturn;
  491. }
  492. #ifndef OS_WINCE
  493. //Set the License Info value
  494. if( ERROR_SUCCESS != RegSetValueEx(
  495. hTempKey,
  496. TEXT("ClientLicense"),
  497. 0,
  498. REG_BINARY,
  499. pbLicenseInfo,
  500. cbLicenseInfo
  501. ) )
  502. {
  503. lsResult = LSSTAT_ERROR;
  504. goto ErrorReturn;
  505. }
  506. #else
  507. if( ERROR_SUCCESS != WriteLicenseToStore(
  508. (STORE_HANDLE)hTempKey,
  509. pbLicenseInfo,
  510. cbLicenseInfo ) )
  511. {
  512. lsResult = LSSTAT_ERROR;
  513. goto ErrorReturn;
  514. }
  515. #endif
  516. }
  517. else // so ERROR_SUCCESS != RegCreateKeyEx
  518. {
  519. lsResult = LSSTAT_ERROR;
  520. goto ErrorReturn;
  521. }
  522. }
  523. else
  524. {
  525. lsResult = LSSTAT_ERROR;
  526. goto ErrorReturn;
  527. }
  528. lsResult = LSSTAT_SUCCESS;
  529. }
  530. break;
  531. default:
  532. goto ErrorReturn;
  533. }
  534. CommonReturn:
  535. if(hLicense)
  536. {
  537. LSCloseLicenseHandle(hLicense, 0);
  538. hLicense = NULL;
  539. }
  540. if(hTempKey)
  541. {
  542. RegCloseKey(hTempKey);
  543. hTempKey = NULL;
  544. }
  545. return lsResult;
  546. ErrorReturn:
  547. goto CommonReturn;
  548. }
  549. LS_STATUS
  550. CALL_TYPE
  551. LSDeleteLicenseFromStore(
  552. IN HANDLE hStore, //Handle of a open store
  553. IN PLSINDEX plsiName //Index of the license to be deleted
  554. )
  555. {
  556. LS_STATUS lsResult = LSSTAT_ERROR;
  557. TCHAR szKeyName[MAX_LEN];
  558. DWORD dwKeyNameLen = MAX_LEN;
  559. DWORD dwSubKeys = 0;
  560. DWORD dwIndex = 0;
  561. DWORD cbValueData = 0;
  562. BYTE FAR * pbValueData = NULL;
  563. LONG err = ERROR_SUCCESS;
  564. HKEY hTempKey = NULL;
  565. FILETIME ft;
  566. HKEY hkeyStore = NULL;
  567. if( (hStore == NULL) ||
  568. (plsiName == NULL) ||
  569. (plsiName->pbScope == NULL) ||
  570. (plsiName->pbCompany == NULL) ||
  571. (plsiName->pbProductID == NULL) )
  572. return LSSTAT_INVALID_HANDLE;
  573. hkeyStore = (HKEY)hStore;
  574. if( ERROR_SUCCESS != RegQueryInfoKey(hkeyStore,
  575. NULL,
  576. NULL,
  577. NULL,
  578. &dwSubKeys,
  579. NULL,
  580. NULL,
  581. NULL,
  582. NULL,
  583. NULL,
  584. NULL,
  585. NULL) )
  586. goto ErrorReturn;
  587. for(dwIndex = 0; dwIndex <dwSubKeys; dwIndex ++)
  588. {
  589. if( ERROR_SUCCESS != RegEnumKeyEx(
  590. hkeyStore,
  591. dwIndex,
  592. szKeyName,
  593. &dwKeyNameLen,
  594. NULL,
  595. NULL,
  596. NULL,
  597. &ft
  598. ) )
  599. {
  600. continue;
  601. }
  602. err = RegOpenKeyEx(hkeyStore, szKeyName, 0, KEY_READ | KEY_WRITE | DELETE, &hTempKey);
  603. if(err != ERROR_SUCCESS)
  604. continue;
  605. err = RegQueryValueEx(hTempKey,
  606. TEXT("LicenseScope"),
  607. NULL,
  608. NULL,
  609. NULL,
  610. &cbValueData);
  611. if( (err!=ERROR_SUCCESS)||
  612. (cbValueData != plsiName->cbScope) )
  613. continue;
  614. if( NULL == (pbValueData = (BYTE FAR *)malloc(cbValueData)) )
  615. {
  616. lsResult = LSSTAT_OUT_OF_MEMORY;
  617. goto ErrorReturn;
  618. }
  619. memset(pbValueData, 0x00, cbValueData);
  620. err = RegQueryValueEx(hTempKey,
  621. TEXT("LicenseScope"),
  622. NULL,
  623. NULL,
  624. pbValueData,
  625. &cbValueData);
  626. if( (err!=ERROR_SUCCESS) ||
  627. (memcmp(pbValueData, plsiName->pbScope, cbValueData)) )
  628. {
  629. if(pbValueData)
  630. {
  631. free(pbValueData);
  632. pbValueData = NULL;
  633. }
  634. continue;
  635. }
  636. if(pbValueData)
  637. {
  638. free(pbValueData);
  639. pbValueData = NULL;
  640. }
  641. err = RegQueryValueEx(hTempKey,
  642. TEXT("CompanyName"),
  643. NULL,
  644. NULL,
  645. NULL,
  646. &cbValueData);
  647. if( (err!=ERROR_SUCCESS) ||
  648. (cbValueData != plsiName->cbCompany) )
  649. continue;
  650. if( NULL == (pbValueData = (BYTE FAR *)malloc(cbValueData)) )
  651. {
  652. lsResult = LSSTAT_OUT_OF_MEMORY;
  653. goto ErrorReturn;
  654. }
  655. memset(pbValueData, 0x00, cbValueData);
  656. err = RegQueryValueEx(hTempKey,
  657. TEXT("CompanyName"),
  658. NULL,
  659. NULL,
  660. pbValueData,
  661. &cbValueData);
  662. if( (err!=ERROR_SUCCESS) ||
  663. (memcmp(pbValueData, plsiName->pbCompany, cbValueData)) )
  664. {
  665. if(pbValueData)
  666. {
  667. free(pbValueData);
  668. pbValueData = NULL;
  669. }
  670. continue;
  671. }
  672. if(pbValueData)
  673. {
  674. free(pbValueData);
  675. pbValueData = NULL;
  676. }
  677. err = RegQueryValueEx(hTempKey,
  678. TEXT("ProductID"),
  679. NULL,
  680. NULL,
  681. NULL,
  682. &cbValueData);
  683. if( (err!=ERROR_SUCCESS) ||
  684. (cbValueData != plsiName->cbProductID) )
  685. continue;
  686. if( NULL == (pbValueData = (BYTE FAR *)malloc(cbValueData)) )
  687. {
  688. lsResult = LSSTAT_OUT_OF_MEMORY;
  689. goto ErrorReturn;
  690. }
  691. memset(pbValueData, 0x00, cbValueData);
  692. err = RegQueryValueEx(hTempKey,
  693. TEXT("ProductID"),
  694. NULL,
  695. NULL,
  696. pbValueData,
  697. &cbValueData);
  698. if( (err!=ERROR_SUCCESS) ||
  699. (memcmp(pbValueData, plsiName->pbProductID, cbValueData)) )
  700. {
  701. if(pbValueData)
  702. {
  703. free(pbValueData);
  704. pbValueData = NULL;
  705. }
  706. continue;
  707. }
  708. if(pbValueData)
  709. {
  710. free(pbValueData);
  711. pbValueData = NULL;
  712. }
  713. if(hTempKey)
  714. {
  715. RegCloseKey(hTempKey);
  716. hTempKey = NULL;
  717. }
  718. if( ERROR_SUCCESS == RegDeleteKey(hkeyStore, szKeyName) )
  719. {
  720. lsResult = LSSTAT_SUCCESS;
  721. break;
  722. }
  723. lsResult = LSSTAT_LICENSE_NOT_FOUND;
  724. }
  725. CommonReturn:
  726. return lsResult;
  727. ErrorReturn:
  728. goto CommonReturn;
  729. }
  730. //Finds a license in an open store against a particular store Index
  731. LS_STATUS
  732. CALL_TYPE
  733. LSFindLicenseInStore(
  734. IN HANDLE hStore, //Handle of a open store
  735. IN PLSINDEX plsiName, //LSIndex against which store is searched
  736. IN OUT DWORD FAR *pdwLicenseInfoLen, //Size of the license found
  737. OUT BYTE FAR *pbLicenseInfo //License Data
  738. )
  739. {
  740. LS_STATUS lsResult = LSSTAT_ERROR;
  741. HANDLE hLicense = NULL;
  742. HKEY hkeyLicense = NULL;
  743. DWORD dwStatus = ERROR_SUCCESS;
  744. if( LSSTAT_SUCCESS != (lsResult = LSOpenLicenseHandle( hStore, TRUE, plsiName, &hLicense)) )
  745. goto ErrorReturn;
  746. hkeyLicense = (HKEY)hLicense;
  747. #ifndef OS_WINCE
  748. if( ERROR_SUCCESS == (dwStatus = RegQueryValueEx((HKEY)hkeyLicense,
  749. TEXT("ClientLicense"),
  750. NULL,
  751. NULL,
  752. pbLicenseInfo,
  753. pdwLicenseInfoLen)) )
  754. {
  755. lsResult = LSSTAT_SUCCESS;
  756. goto CommonReturn;
  757. }
  758. #else
  759. if( ERROR_SUCCESS == (dwStatus = ReadLicenseFromStore(
  760. (STORE_HANDLE)hkeyLicense,
  761. pbLicenseInfo,
  762. pdwLicenseInfoLen)) )
  763. {
  764. lsResult = LSSTAT_SUCCESS;
  765. goto CommonReturn;
  766. }
  767. #endif
  768. if( dwStatus != ERROR_SUCCESS)
  769. {
  770. lsResult = LSSTAT_ERROR;
  771. }
  772. if(lsResult != LSSTAT_SUCCESS)
  773. {
  774. goto ErrorReturn;
  775. }
  776. else if(*pdwLicenseInfoLen == 0)
  777. {
  778. lsResult = LSSTAT_LICENSE_NOT_FOUND;
  779. goto ErrorReturn;
  780. }
  781. CommonReturn:
  782. if(hLicense)
  783. {
  784. LSCloseLicenseHandle(hLicense, 0);
  785. hLicense = NULL;
  786. }
  787. return lsResult;
  788. ErrorReturn:
  789. goto CommonReturn;
  790. }
  791. LS_STATUS
  792. CALL_TYPE
  793. LSEnumLicenses(
  794. IN HANDLE hStore, //Handle of a open store
  795. IN DWORD dwIndex, //numeric Index of the license to query
  796. OUT PLSINDEX plsiName //The LSIndex structure corresponding to dwIndex
  797. )
  798. {
  799. LS_STATUS lsResult = LSSTAT_ERROR;
  800. TCHAR szKeyName[MAX_LEN];
  801. DWORD dwKeyLen = MAX_LEN;
  802. FILETIME ft;
  803. LONG err = 0;
  804. HKEY hTempKey = NULL;
  805. HKEY hkeyStore = NULL;
  806. if( (hStore == NULL) ||
  807. (plsiName == NULL) )
  808. return LSSTAT_INVALID_HANDLE;
  809. plsiName->dwVersion = 0x01;
  810. hkeyStore = (HKEY)hStore;
  811. if( ERROR_SUCCESS != RegEnumKeyEx(
  812. (HKEY)hkeyStore,
  813. dwIndex,
  814. szKeyName,
  815. &dwKeyLen,
  816. NULL,
  817. NULL,
  818. NULL,
  819. &ft
  820. ) )
  821. goto ErrorReturn;
  822. if( ERROR_SUCCESS != RegOpenKeyEx((HKEY)hkeyStore, szKeyName, 0, KEY_ALL_ACCESS, &hTempKey) )
  823. goto ErrorReturn;
  824. err = RegQueryValueEx(hTempKey,
  825. TEXT("LicenseScope"),
  826. NULL,
  827. NULL,
  828. NULL,
  829. &plsiName->cbScope);
  830. if(err!=ERROR_SUCCESS)
  831. goto ErrorReturn;
  832. if( NULL == (plsiName->pbScope = (BYTE FAR *)malloc(plsiName->cbScope)) )
  833. {
  834. lsResult = LSSTAT_OUT_OF_MEMORY;
  835. goto ErrorReturn;
  836. }
  837. memset(plsiName->pbScope, 0x00, plsiName->cbScope);
  838. err = RegQueryValueEx(hTempKey,
  839. TEXT("LicenseScope"),
  840. NULL,
  841. NULL,
  842. plsiName->pbScope,
  843. &plsiName->cbScope);
  844. if(err!=ERROR_SUCCESS)
  845. goto ErrorReturn;
  846. err = RegQueryValueEx(hTempKey,
  847. TEXT("CompanyName"),
  848. NULL,
  849. NULL,
  850. NULL,
  851. &plsiName->cbCompany);
  852. if(err!=ERROR_SUCCESS)
  853. goto ErrorReturn;
  854. if( NULL == (plsiName->pbCompany = (BYTE FAR *)malloc(plsiName->cbCompany)) )
  855. {
  856. lsResult = LSSTAT_OUT_OF_MEMORY;;
  857. goto ErrorReturn;
  858. }
  859. memset(plsiName->pbCompany, 0x00, plsiName->cbCompany);
  860. err = RegQueryValueEx(hTempKey,
  861. TEXT("CompanyName"),
  862. NULL,
  863. NULL,
  864. (BYTE FAR *)plsiName->pbCompany,
  865. &plsiName->cbCompany);
  866. if(err!=ERROR_SUCCESS)
  867. goto ErrorReturn;
  868. err = RegQueryValueEx(hTempKey,
  869. TEXT("ProductID"),
  870. NULL,
  871. NULL,
  872. NULL,
  873. &plsiName->cbProductID);
  874. if(err!=ERROR_SUCCESS)
  875. goto ErrorReturn;
  876. if( NULL == (plsiName->pbProductID = (BYTE FAR *)malloc(plsiName->cbProductID)) )
  877. {
  878. lsResult = LSSTAT_OUT_OF_MEMORY;
  879. goto ErrorReturn;
  880. }
  881. memset(plsiName->pbProductID, 0x00, plsiName->cbProductID);
  882. err = RegQueryValueEx(hTempKey,
  883. TEXT("ProductID"),
  884. NULL,
  885. NULL,
  886. plsiName->pbProductID,
  887. &plsiName->cbProductID);
  888. if(err!=ERROR_SUCCESS)
  889. {
  890. goto ErrorReturn;
  891. }
  892. lsResult = LSSTAT_SUCCESS;
  893. CommonReturn:
  894. if(hTempKey)
  895. {
  896. RegCloseKey(hTempKey);
  897. hTempKey = NULL;
  898. }
  899. return lsResult;
  900. ErrorReturn:
  901. if(plsiName->pbScope)
  902. {
  903. free(plsiName->pbScope);
  904. plsiName->pbScope = NULL;
  905. }
  906. if(plsiName->pbCompany)
  907. {
  908. free(plsiName->pbCompany);
  909. plsiName->pbCompany = NULL;
  910. }
  911. if(plsiName->pbProductID)
  912. {
  913. free(plsiName->pbProductID);
  914. plsiName->pbProductID = NULL;
  915. }
  916. lsResult = LSSTAT_ERROR;
  917. goto CommonReturn;
  918. }
  919. LS_STATUS
  920. CALL_TYPE
  921. LSQueryInfoLicense(
  922. IN HANDLE hStore, //Handle of a open store
  923. OUT DWORD FAR *pdwLicenses, //Total no. of licenses available
  924. OUT DWORD FAR *pdwMaxCompanyNameLen, //Maximum length of the company length
  925. OUT DWORD FAR *pdwMaxScopeLen, //Maximum length of the company length
  926. OUT DWORD FAR *pdwMaxProductIDLen //Maximum length of the company length
  927. )
  928. {
  929. LS_STATUS lsResult = LSSTAT_ERROR;
  930. FILETIME ft;
  931. HKEY hTempKey = NULL;
  932. TCHAR szKey[MAX_LEN];
  933. DWORD dwKeyLen = MAX_LEN;
  934. DWORD dwSize = 0, dwIndex;
  935. HKEY hkeyStore = NULL;
  936. if(pdwLicenses == NULL)
  937. return LSSTAT_ERROR;
  938. if(pdwMaxCompanyNameLen)
  939. *pdwMaxCompanyNameLen = 0;
  940. if(pdwMaxScopeLen)
  941. *pdwMaxScopeLen = 0;
  942. if(pdwMaxProductIDLen)
  943. *pdwMaxProductIDLen = 0;
  944. hkeyStore = (HKEY)hStore;
  945. if(ERROR_SUCCESS != RegQueryInfoKey((HKEY)hkeyStore,
  946. NULL,
  947. NULL,
  948. NULL,
  949. pdwLicenses,
  950. NULL,
  951. NULL,
  952. NULL,
  953. NULL,
  954. NULL,
  955. NULL,
  956. &ft
  957. ) )
  958. goto ErrorReturn;
  959. for (dwIndex = 0; dwIndex<*pdwLicenses; dwIndex++)
  960. {
  961. if( ERROR_SUCCESS != RegEnumKeyEx((HKEY)hkeyStore,
  962. dwIndex,
  963. szKey,
  964. &dwKeyLen,
  965. NULL,
  966. NULL,
  967. NULL,
  968. &ft) )
  969. goto ErrorReturn;
  970. if( ERROR_SUCCESS != RegOpenKeyEx((HKEY)hkeyStore,
  971. szKey,
  972. 0,
  973. KEY_READ,
  974. &hTempKey) )
  975. goto ErrorReturn;
  976. if(pdwMaxCompanyNameLen)
  977. {
  978. if( ERROR_SUCCESS != RegQueryValueEx( hTempKey,
  979. TEXT("CompanyName"),
  980. NULL,
  981. NULL,
  982. NULL,
  983. &dwSize) )
  984. goto ErrorReturn;
  985. if(dwSize >= *pdwMaxCompanyNameLen)
  986. *pdwMaxCompanyNameLen = dwSize;
  987. }
  988. if(pdwMaxScopeLen)
  989. {
  990. if( ERROR_SUCCESS != RegQueryValueEx( hTempKey,
  991. TEXT("LicenseScope"),
  992. NULL,
  993. NULL,
  994. NULL,
  995. &dwSize) )
  996. goto ErrorReturn;
  997. if(dwSize >= *pdwMaxScopeLen)
  998. *pdwMaxScopeLen = dwSize;
  999. }
  1000. if(pdwMaxProductIDLen)
  1001. {
  1002. if( ERROR_SUCCESS != RegQueryValueEx( hTempKey,
  1003. TEXT("ProductID"),
  1004. NULL,
  1005. NULL,
  1006. NULL,
  1007. &dwSize) )
  1008. goto ErrorReturn;
  1009. if(dwSize >= *pdwMaxProductIDLen)
  1010. *pdwMaxProductIDLen = dwSize;
  1011. }
  1012. }
  1013. lsResult = LSSTAT_SUCCESS;
  1014. CommonReturn:
  1015. if(hTempKey)
  1016. {
  1017. RegCloseKey(hTempKey);
  1018. hTempKey = NULL;
  1019. }
  1020. return lsResult;
  1021. ErrorReturn:
  1022. goto CommonReturn;
  1023. }
  1024. LS_STATUS
  1025. CALL_TYPE
  1026. LSOpenLicenseHandle(
  1027. IN HANDLE hStore, //Handle of a open store
  1028. IN BOOL fReadOnly,
  1029. IN PLSINDEX plsiName,
  1030. OUT HANDLE *phLicense
  1031. )
  1032. {
  1033. LS_STATUS lsReturn = LSSTAT_LICENSE_NOT_FOUND;
  1034. TCHAR szKeyName[MAX_LEN];
  1035. DWORD dwKeyNameLen = MAX_LEN;
  1036. DWORD dwSubKeys = 0;
  1037. DWORD dwIndex = 0;
  1038. DWORD cbValueData = 0;
  1039. BYTE FAR *pbValueData = NULL;
  1040. LONG err = ERROR_SUCCESS;
  1041. HKEY hTempKey = NULL;
  1042. FILETIME ft;
  1043. HKEY hkeyStore = NULL;
  1044. if( (phLicense == NULL) ||
  1045. (hStore == NULL) ||
  1046. (plsiName == NULL) ||
  1047. (plsiName->pbScope == NULL) ||
  1048. (plsiName->pbCompany == NULL) ||
  1049. (plsiName->pbProductID == NULL) )
  1050. {
  1051. return LSSTAT_INVALID_HANDLE;
  1052. }
  1053. hkeyStore = (HKEY)hStore;
  1054. //Get the number of Licenses available
  1055. if( ERROR_SUCCESS != RegQueryInfoKey((HKEY)hkeyStore,
  1056. NULL,
  1057. NULL,
  1058. NULL,
  1059. &dwSubKeys,
  1060. NULL,
  1061. NULL,
  1062. NULL,
  1063. NULL,
  1064. NULL,
  1065. NULL,
  1066. NULL) )
  1067. goto ErrorReturn;
  1068. //Start searching from the first license until a match is obtained
  1069. for(dwIndex = 0; dwIndex <dwSubKeys; dwIndex ++)
  1070. {
  1071. dwKeyNameLen = MAX_LEN;
  1072. if( ERROR_SUCCESS != RegEnumKeyEx(
  1073. (HKEY)hkeyStore,
  1074. dwIndex,
  1075. szKeyName,
  1076. &dwKeyNameLen,
  1077. NULL,
  1078. NULL,
  1079. NULL,
  1080. &ft
  1081. ) )
  1082. {
  1083. continue;
  1084. }
  1085. err = RegOpenKeyEx((HKEY)hkeyStore,
  1086. szKeyName,
  1087. 0,
  1088. fReadOnly ? KEY_READ : KEY_READ | KEY_WRITE,
  1089. &hTempKey);
  1090. if(err != ERROR_SUCCESS)
  1091. continue;
  1092. err = RegQueryValueEx(hTempKey,
  1093. TEXT("LicenseScope"),
  1094. NULL,
  1095. NULL,
  1096. NULL,
  1097. &cbValueData);
  1098. if( (err != ERROR_SUCCESS) ||
  1099. (cbValueData != plsiName->cbScope) )
  1100. {
  1101. if(hTempKey)
  1102. {
  1103. RegCloseKey(hTempKey);
  1104. hTempKey = NULL;
  1105. }
  1106. continue;
  1107. }
  1108. if( NULL == (pbValueData = (BYTE FAR *)malloc(cbValueData)) )
  1109. {
  1110. if(hTempKey)
  1111. {
  1112. RegCloseKey(hTempKey);
  1113. hTempKey = NULL;
  1114. }
  1115. lsReturn = LSSTAT_OUT_OF_MEMORY;
  1116. goto ErrorReturn;
  1117. }
  1118. memset(pbValueData, 0x00, cbValueData);
  1119. err = RegQueryValueEx(hTempKey,
  1120. TEXT("LicenseScope"),
  1121. NULL,
  1122. NULL,
  1123. pbValueData,
  1124. &cbValueData);
  1125. if( (err!=ERROR_SUCCESS) ||
  1126. (memcmp(pbValueData, plsiName->pbScope, cbValueData)) )
  1127. {
  1128. if(hTempKey)
  1129. {
  1130. RegCloseKey(hTempKey);
  1131. hTempKey = NULL;
  1132. }
  1133. if(pbValueData)
  1134. {
  1135. free(pbValueData);
  1136. pbValueData = NULL;
  1137. cbValueData = 0;
  1138. }
  1139. continue;
  1140. }
  1141. if(pbValueData)
  1142. {
  1143. free(pbValueData);
  1144. pbValueData = NULL;
  1145. cbValueData = 0;
  1146. }
  1147. err = RegQueryValueEx(hTempKey,
  1148. TEXT("CompanyName"),
  1149. NULL,
  1150. NULL,
  1151. NULL,
  1152. &cbValueData);
  1153. if( (err != ERROR_SUCCESS) ||
  1154. (cbValueData != plsiName->cbCompany) )
  1155. {
  1156. if(hTempKey)
  1157. {
  1158. RegCloseKey(hTempKey);
  1159. hTempKey = NULL;
  1160. }
  1161. continue;
  1162. }
  1163. if( NULL == (pbValueData = (BYTE FAR *)malloc(cbValueData)) )
  1164. {
  1165. if(hTempKey)
  1166. {
  1167. RegCloseKey(hTempKey);
  1168. hTempKey = NULL;
  1169. }
  1170. lsReturn = LSSTAT_OUT_OF_MEMORY;
  1171. goto ErrorReturn;
  1172. }
  1173. memset(pbValueData, 0x00, cbValueData);
  1174. err = RegQueryValueEx(hTempKey,
  1175. TEXT("CompanyName"),
  1176. NULL,
  1177. NULL,
  1178. pbValueData,
  1179. &cbValueData);
  1180. if( (err!=ERROR_SUCCESS) ||
  1181. (memcmp(pbValueData, plsiName->pbCompany, cbValueData)) )
  1182. {
  1183. if(hTempKey)
  1184. {
  1185. RegCloseKey(hTempKey);
  1186. hTempKey = NULL;
  1187. }
  1188. if(pbValueData)
  1189. {
  1190. free(pbValueData);
  1191. pbValueData = NULL;
  1192. cbValueData = 0;
  1193. }
  1194. continue;
  1195. }
  1196. if(pbValueData)
  1197. {
  1198. free(pbValueData);
  1199. pbValueData = NULL;
  1200. cbValueData = 0;
  1201. }
  1202. err = RegQueryValueEx(hTempKey,
  1203. TEXT("ProductID"),
  1204. NULL,
  1205. NULL,
  1206. NULL,
  1207. &cbValueData);
  1208. if( (err != ERROR_SUCCESS) ||
  1209. ( cbValueData != plsiName->cbProductID ) )
  1210. {
  1211. if(hTempKey)
  1212. {
  1213. RegCloseKey(hTempKey);
  1214. hTempKey = NULL;
  1215. }
  1216. continue;
  1217. }
  1218. if( NULL == (pbValueData = (BYTE FAR *)malloc(cbValueData)) )
  1219. {
  1220. if(hTempKey)
  1221. {
  1222. RegCloseKey(hTempKey);
  1223. hTempKey = NULL;
  1224. }
  1225. lsReturn = LSSTAT_OUT_OF_MEMORY;
  1226. goto ErrorReturn;
  1227. }
  1228. memset(pbValueData, 0x00, cbValueData);
  1229. err = RegQueryValueEx(hTempKey,
  1230. TEXT("ProductID"),
  1231. NULL,
  1232. NULL,
  1233. pbValueData,
  1234. &cbValueData);
  1235. if( (err!=ERROR_SUCCESS) ||
  1236. (memcmp(pbValueData, plsiName->pbProductID, cbValueData)) )
  1237. {
  1238. if(hTempKey)
  1239. {
  1240. RegCloseKey(hTempKey);
  1241. hTempKey = NULL;
  1242. }
  1243. if(pbValueData)
  1244. {
  1245. free(pbValueData);
  1246. pbValueData = NULL;
  1247. }
  1248. continue;
  1249. }
  1250. lsReturn = LSSTAT_SUCCESS;
  1251. if(pbValueData)
  1252. {
  1253. free(pbValueData);
  1254. pbValueData = NULL;
  1255. cbValueData = 0;
  1256. }
  1257. break;
  1258. }
  1259. if (dwIndex == dwSubKeys)
  1260. {
  1261. // nothing found
  1262. goto ErrorReturn;
  1263. }
  1264. *phLicense = (HANDLE)hTempKey;
  1265. CommonReturn:
  1266. return lsReturn;
  1267. ErrorReturn:
  1268. if(pbValueData)
  1269. {
  1270. free(pbValueData);
  1271. pbValueData = NULL;
  1272. }
  1273. *phLicense = NULL;
  1274. pbValueData = NULL;
  1275. cbValueData = 0;
  1276. goto CommonReturn;
  1277. }
  1278. LS_STATUS
  1279. CALL_TYPE
  1280. LSCloseLicenseHandle(
  1281. IN HANDLE hLicense, //Handle of a open store
  1282. IN DWORD dwFlags //For future Use
  1283. )
  1284. {
  1285. LS_STATUS lsResult = LSSTAT_ERROR;
  1286. HKEY hKey = (HKEY)hLicense;
  1287. if(hKey)
  1288. {
  1289. RegCloseKey(hKey);
  1290. hKey = NULL;
  1291. lsResult = LSSTAT_SUCCESS;
  1292. }
  1293. return lsResult;
  1294. }