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.

2689 lines
75 KiB

  1. #include "precomp.h"
  2. DEBUG_FILEZONE(ZONE_T120_GCCNC);
  3. /*
  4. * registry.cpp
  5. *
  6. * Copyright (c) 1995 by DataBeam Corporation, Lexington, KY
  7. *
  8. * Abstract:
  9. * This is the registry class implementation file. All registry operations
  10. * at both the Top Provider and subordinate nodes. It is responsible for
  11. * queing registry request, maintaining the registry, sending confirms to
  12. * the application SAP, etc. Registry objects at sub-ordinate nodes are
  13. * responsible for queuing up the registry request to be sent on to the
  14. * Top Provider. On of these classes should be created per node. This
  15. * class handles request from all existing application SAPs.
  16. *
  17. * FOR A MORE DETAILED EXPLANATION OF THIS CLASS SEE THE INTERFACE FILE
  18. *
  19. * Private Instance Variables:
  20. * m_pMCSUserObject
  21. * Pointer to the User Attachment object used to deliver all registry
  22. * request and responses to remote nodes.
  23. * m_RegEntryList
  24. * This is the list that holds all the registry entries associated
  25. * with this conference.
  26. * m_fTopProvider
  27. * This flag specifies if this is the top provider node (TRUE means
  28. * this is the top provider node).
  29. * m_nCurrentTokenID
  30. * This is a counter that is used to generate the token IDs by the
  31. * registry object at the top provider.
  32. * m_nConfID
  33. * Conference ID assocaited with this conference.
  34. * m_pEmptyRegItem
  35. * This is a pointer to an empty registry item that is used to generate
  36. * empty items for PDUs that don't contain a registry item.
  37. * m_AppSapEidList2
  38. * This list contains pointers to the command target objects associated
  39. * with each of the enrolled APEs
  40. * m_nRegHandle
  41. * This is a counter that is used to generate the handles allocated
  42. * by the registry object at the top provider.
  43. * m_pAppRosterMgrList
  44. * This list hold all the current application roster managers and
  45. * is used to verify that a requesting APE is actually enrolled with
  46. * the conference.
  47. *
  48. * Caveats:
  49. * None.
  50. *
  51. * Author:
  52. * blp
  53. */
  54. #include "registry.h"
  55. #include "appsap.h"
  56. #define FIRST_DYNAMIC_TOKEN_ID 16384
  57. #define MAXIMUM_ALLOWABLE_ALLOCATED_HANDLES (16 * 1024) // for T.126
  58. /*
  59. * CRegistry()
  60. *
  61. * Public Function Description
  62. * This is the registry constructor. It is responsible for initializing
  63. * instance variables.
  64. *
  65. */
  66. CRegistry::CRegistry(PMCSUser user_object,
  67. BOOL top_provider,
  68. GCCConfID conference_id,
  69. CAppRosterMgrList *app_roster_manager_list,
  70. PGCCError pRetCode)
  71. :
  72. CRefCount(MAKE_STAMP_ID('A','R','e','g')),
  73. m_AppSapEidList2(DESIRED_MAX_APP_SAP_ITEMS),
  74. m_pMCSUserObject(user_object),
  75. m_fTopProvider(top_provider),
  76. m_nCurrentTokenID(FIRST_DYNAMIC_TOKEN_ID),
  77. m_nConfID(conference_id),
  78. m_nRegHandle(0),
  79. m_pAppRosterMgrList(app_roster_manager_list)
  80. {
  81. GCCRegistryItem registry_item;
  82. *pRetCode = GCC_NO_ERROR;
  83. /*
  84. ** If this is the Top Provider we now build a vacant registry item to
  85. ** be used when an entry in the registry is being accessed that does not
  86. ** exists.
  87. */
  88. if (m_fTopProvider)
  89. {
  90. registry_item.item_type = GCC_REGISTRY_NONE;
  91. DBG_SAVE_FILE_LINE
  92. m_pEmptyRegItem = new CRegItem(&registry_item, pRetCode);
  93. if (m_pEmptyRegItem == NULL || GCC_NO_ERROR != *pRetCode)
  94. {
  95. *pRetCode = GCC_ALLOCATION_FAILURE;
  96. }
  97. }
  98. else
  99. {
  100. m_pEmptyRegItem = NULL;
  101. }
  102. }
  103. /*
  104. * ~CRegistry()
  105. *
  106. * Public Function Description
  107. * This is the registry destructor. It is responsible for freeing any
  108. * outstanding memory associated with the application registry.
  109. */
  110. CRegistry::~CRegistry(void)
  111. {
  112. REG_ENTRY *pRegEntry;
  113. m_RegEntryList.Reset();
  114. // Free up any registry entries
  115. while (NULL != (pRegEntry = m_RegEntryList.Iterate()))
  116. {
  117. if (NULL != pRegEntry->registry_key)
  118. {
  119. pRegEntry->registry_key->Release();
  120. }
  121. if (NULL != pRegEntry->entry_item)
  122. {
  123. pRegEntry->entry_item->Release();
  124. }
  125. delete pRegEntry;
  126. }
  127. if (NULL != m_pEmptyRegItem)
  128. {
  129. m_pEmptyRegItem->Release();
  130. }
  131. }
  132. /*
  133. * void EnrollAPE ()
  134. *
  135. * Public Function Description
  136. * This routine is used to inform the application registry of a newly
  137. * enrolling APE and its corresponding command target interface.
  138. */
  139. void CRegistry::EnrollAPE(EntityID eid, CAppSap *pAppSap)
  140. {
  141. m_AppSapEidList2.Append(eid, pAppSap);
  142. }
  143. /*
  144. * void UnEnrollApplicationSAP ()
  145. *
  146. * Public Function Description
  147. * This routine is used to inform the application registry of an
  148. * APE that is unerolling from the conference.
  149. *
  150. * Caveats
  151. * This routine removes ownership from all the entries currently owned by
  152. * the passed in application entity. It will also remove any outstanding
  153. * request for the SAP that unenrolled.
  154. */
  155. void CRegistry::UnEnrollAPE ( EntityID entity_id )
  156. {
  157. REG_ENTRY *lpRegEntry;
  158. UserID my_user_id = m_pMCSUserObject->GetMyNodeID();
  159. m_RegEntryList.Reset();
  160. while (NULL != (lpRegEntry = m_RegEntryList.Iterate()))
  161. {
  162. /*
  163. ** First we remove this APE from the list of nodes that are
  164. ** monitoring this entry.
  165. */
  166. lpRegEntry->monitoring_list.Remove(entity_id);
  167. /*
  168. ** Next, if this is the top provider, we clean up the the
  169. ** ownership properties of this entry and issue any PDUs and/or
  170. ** messages that are necessary.
  171. */
  172. if (m_fTopProvider)
  173. {
  174. if ((lpRegEntry->owner_id == my_user_id) &&
  175. (lpRegEntry->entity_id == entity_id))
  176. {
  177. /*
  178. ** Ownership is removed from any registry entries this
  179. ** entity owned.
  180. */
  181. lpRegEntry->owner_id = 0;
  182. lpRegEntry->entity_id = 0;
  183. // Send Monitor Indication if necessary
  184. if (lpRegEntry->monitoring_state == ON)
  185. {
  186. /*
  187. ** Deliver the monitor indication to the Top
  188. ** Provider's Node Controller if necessary.
  189. */
  190. SendMonitorEntryIndicationMessage (lpRegEntry);
  191. m_pMCSUserObject->RegistryMonitorEntryIndication(
  192. lpRegEntry->registry_key,
  193. lpRegEntry->entry_item,
  194. lpRegEntry->owner_id,
  195. lpRegEntry->entity_id,
  196. lpRegEntry->modification_rights);
  197. }
  198. }
  199. }
  200. }
  201. // Remove this enity from the command target list if it exists.
  202. m_AppSapEidList2.Remove(entity_id);
  203. }
  204. /*
  205. * GCCError RegisterChannel ()
  206. *
  207. * Public Function Description
  208. * This routine is responsible for registering a specified channel.
  209. * It has two different paths of execution based on whether this is
  210. * a Top Provider registry or a subordinate node registry object.
  211. */
  212. GCCError CRegistry::RegisterChannel (
  213. PGCCRegistryKey registry_key,
  214. ChannelID channel_id,
  215. EntityID entity_id)
  216. {
  217. GCCError rc = GCC_NO_ERROR;
  218. REG_ENTRY *registry_entry = NULL; // a must
  219. CRegKeyContainer *registry_key_data = NULL; // a must
  220. CRegItem *registry_item_data = NULL; // a must
  221. GCCRegistryItem registry_item;
  222. CAppSap *requester_sap;
  223. if (NULL == (requester_sap = m_AppSapEidList2.Find(entity_id)))
  224. return (GCC_APP_NOT_ENROLLED);
  225. /*
  226. ** Next set up the Registry Key and Registry Item. Return immediately if
  227. ** a resource failure occurs.
  228. */
  229. DBG_SAVE_FILE_LINE
  230. registry_key_data = new CRegKeyContainer(registry_key, &rc);
  231. if (NULL == registry_key_data || GCC_NO_ERROR != rc)
  232. {
  233. ERROR_OUT(("CRegistry::RegisterChannel: can't create regitry key"));
  234. rc = GCC_ALLOCATION_FAILURE;
  235. goto MyExit;
  236. }
  237. if (m_fTopProvider == FALSE)
  238. {
  239. m_pMCSUserObject->RegistryRegisterChannelRequest(registry_key_data, channel_id, entity_id);
  240. // The registry key data object is no longer needed here
  241. registry_key_data->Release();
  242. rc = GCC_NO_ERROR;
  243. goto MyExit;
  244. }
  245. // no PDU is sent when request occurs at the top provider
  246. /*
  247. ** First check to see if the registry entry exists and if it
  248. ** does check the ownership to make sure this node has
  249. ** permission to change the entry.
  250. */
  251. registry_entry = GetRegistryEntry(registry_key_data);
  252. if (registry_entry != NULL)
  253. {
  254. // Entry already exists, send back negative result
  255. requester_sap->RegistryConfirm(
  256. m_nConfID,
  257. GCC_REGISTER_CHANNEL_CONFIRM,
  258. registry_entry->registry_key,
  259. registry_entry->entry_item,
  260. registry_entry->modification_rights,
  261. registry_entry->owner_id,
  262. registry_entry->entity_id,
  263. FALSE,
  264. GCC_RESULT_ENTRY_ALREADY_EXISTS);
  265. // The registry key data object is no longer needed
  266. registry_key_data->Release();
  267. rc = GCC_NO_ERROR;
  268. goto MyExit;
  269. }
  270. // Set up the registry item here
  271. registry_item.item_type = GCC_REGISTRY_CHANNEL_ID;
  272. registry_item.channel_id = channel_id;
  273. DBG_SAVE_FILE_LINE
  274. registry_item_data = new CRegItem(&registry_item, &rc);
  275. if (registry_item_data == NULL || GCC_NO_ERROR != rc)
  276. {
  277. ERROR_OUT(("CRegistry::RegisterChannel: can't create regitry item"));
  278. rc = GCC_ALLOCATION_FAILURE;
  279. goto MyExit;
  280. }
  281. // Since entry does not exists create it here
  282. DBG_SAVE_FILE_LINE
  283. registry_entry = new REG_ENTRY;
  284. if (registry_entry == NULL)
  285. {
  286. ERROR_OUT(("CRegistry::RegisterChannel: can't create regitry entry"));
  287. rc = GCC_ALLOCATION_FAILURE;
  288. goto MyExit;
  289. }
  290. // Fill in the new entry
  291. registry_entry->registry_key = registry_key_data;
  292. registry_entry->entry_item = registry_item_data;
  293. registry_entry->monitoring_state = OFF;
  294. registry_entry->owner_id = m_pMCSUserObject->GetMyNodeID();
  295. registry_entry->entity_id = entity_id;
  296. /*
  297. ** Initialize to public incase entry is switched to
  298. ** a parameter. Note that as long as the entry is
  299. ** not a PARAMETER modification rights will not be
  300. ** used.
  301. */
  302. registry_entry->modification_rights = GCC_PUBLIC_RIGHTS;
  303. // Add registry entry to registry list
  304. m_RegEntryList.Append(registry_entry);
  305. // Send success for the result
  306. requester_sap->RegistryConfirm (
  307. m_nConfID,
  308. GCC_REGISTER_CHANNEL_CONFIRM,
  309. registry_entry->registry_key,
  310. registry_entry->entry_item,
  311. registry_entry->modification_rights,
  312. registry_entry->owner_id,
  313. registry_entry->entity_id,
  314. FALSE,
  315. GCC_RESULT_SUCCESSFUL);
  316. rc = GCC_NO_ERROR;
  317. MyExit:
  318. if (GCC_NO_ERROR != rc)
  319. {
  320. if (NULL != registry_key_data)
  321. {
  322. registry_key_data->Release();
  323. }
  324. if (NULL != registry_item_data)
  325. {
  326. registry_item_data->Release();
  327. }
  328. if(registry_entry)
  329. {
  330. delete registry_entry;
  331. }
  332. }
  333. return (rc);
  334. }
  335. /*
  336. * GCCError AssignToken ()
  337. *
  338. * Public Function Description
  339. * This routine is responsible for generating and registering a new token.
  340. * It has two different paths of execution based on whether this is
  341. * a Top Provider registry or a subordinate node registry object.
  342. */
  343. GCCError CRegistry::AssignToken (
  344. PGCCRegistryKey registry_key,
  345. EntityID entity_id )
  346. {
  347. GCCError rc = GCC_NO_ERROR;
  348. REG_ENTRY *registry_entry = NULL; // a must
  349. CRegKeyContainer *registry_key_data = NULL; // a must
  350. CRegItem *registry_item_data = NULL; // a must
  351. GCCRegistryItem registry_item;
  352. CAppSap *requester_sap;
  353. if (NULL == (requester_sap = m_AppSapEidList2.Find(entity_id)))
  354. return (GCC_APP_NOT_ENROLLED);
  355. DBG_SAVE_FILE_LINE
  356. registry_key_data = new CRegKeyContainer(registry_key, &rc);
  357. if ((registry_key_data == NULL) || (rc != GCC_NO_ERROR))
  358. {
  359. ERROR_OUT(("CRegistry::AssignToken: can't create regitry key"));
  360. rc = GCC_ALLOCATION_FAILURE;
  361. goto MyExit;
  362. }
  363. if (m_fTopProvider == FALSE)
  364. {
  365. m_pMCSUserObject->RegistryAssignTokenRequest(registry_key_data, entity_id);
  366. // The registry key data object is no longer needed here
  367. registry_key_data->Release();
  368. rc = GCC_NO_ERROR;
  369. goto MyExit;
  370. }
  371. // no PDU is sent when request occurs at the top provider
  372. /*
  373. ** First check to see if the registry entry exists and if it
  374. ** does check the ownership to make sure this node has
  375. ** permission to change the entry.
  376. */
  377. registry_entry = GetRegistryEntry(registry_key_data);
  378. if (registry_entry != NULL)
  379. {
  380. // Entry already exists, send back negative result
  381. requester_sap->RegistryConfirm(
  382. m_nConfID,
  383. GCC_ASSIGN_TOKEN_CONFIRM,
  384. registry_entry->registry_key,
  385. registry_entry->entry_item,
  386. registry_entry->modification_rights,
  387. registry_entry->owner_id,
  388. registry_entry->entity_id,
  389. FALSE,
  390. GCC_RESULT_ENTRY_ALREADY_EXISTS);
  391. // The registry key data object is no longer needed
  392. registry_key_data->Release();
  393. rc = GCC_NO_ERROR;
  394. goto MyExit;
  395. }
  396. // Set up the registry item here
  397. registry_item.item_type = GCC_REGISTRY_TOKEN_ID;
  398. registry_item.token_id = GetUnusedToken();
  399. DBG_SAVE_FILE_LINE
  400. registry_item_data = new CRegItem(&registry_item, &rc);
  401. if ((registry_item_data == NULL) || (rc != GCC_NO_ERROR))
  402. {
  403. ERROR_OUT(("CRegistry::AssignToken: can't create regitry item"));
  404. rc = GCC_ALLOCATION_FAILURE;
  405. goto MyExit;
  406. }
  407. DBG_SAVE_FILE_LINE
  408. registry_entry = new REG_ENTRY;
  409. if (registry_entry == NULL)
  410. {
  411. ERROR_OUT(("CRegistry::AssignToken: can't create regitry entry"));
  412. rc = GCC_ALLOCATION_FAILURE;
  413. goto MyExit;
  414. }
  415. // Fill in the new entry
  416. registry_entry->registry_key = registry_key_data;
  417. registry_entry->entry_item = registry_item_data;
  418. registry_entry->monitoring_state = OFF;
  419. registry_entry->owner_id = m_pMCSUserObject->GetMyNodeID();
  420. registry_entry->entity_id = entity_id;
  421. /*
  422. ** Initialize to public incase entry is switched to
  423. ** a parameter. Note that as long as the entry is
  424. ** not a PARAMETER modification rights will not be
  425. ** used.
  426. */
  427. registry_entry->modification_rights = GCC_PUBLIC_RIGHTS;
  428. // Add registry entry to registry list
  429. m_RegEntryList.Append(registry_entry);
  430. // Send success for the result
  431. requester_sap->RegistryConfirm (
  432. m_nConfID,
  433. GCC_ASSIGN_TOKEN_CONFIRM,
  434. registry_entry->registry_key,
  435. registry_entry->entry_item,
  436. registry_entry->modification_rights,
  437. registry_entry->owner_id,
  438. registry_entry->entity_id,
  439. FALSE,
  440. GCC_RESULT_SUCCESSFUL);
  441. rc = GCC_NO_ERROR;
  442. MyExit:
  443. if (GCC_NO_ERROR != rc)
  444. {
  445. if (NULL != registry_key_data)
  446. {
  447. registry_key_data->Release();
  448. }
  449. if (NULL != registry_item_data)
  450. {
  451. registry_item_data->Release();
  452. }
  453. delete registry_entry;
  454. }
  455. return (rc);
  456. }
  457. /*
  458. * GCCError SetParameter ()
  459. *
  460. * Public Function Description
  461. * This routine is responsible for generating and registering a new token.
  462. * It has two different paths of execution based on whether this is
  463. * a Top Provider registry or a subordinate node registry object.
  464. */
  465. GCCError CRegistry::SetParameter (
  466. PGCCRegistryKey registry_key,
  467. LPOSTR parameter_value,
  468. GCCModificationRights modification_rights,
  469. EntityID entity_id )
  470. {
  471. GCCError rc = GCC_NO_ERROR;
  472. REG_ENTRY *registry_entry = NULL; // a must
  473. CRegKeyContainer *registry_key_data = NULL; // a must
  474. CRegItem *registry_item_data = NULL; // a must
  475. GCCResult result;
  476. GCCRegistryItem registry_item;
  477. BOOL application_is_enrolled = FALSE;
  478. CAppSap *requester_sap;
  479. if (NULL == (requester_sap = m_AppSapEidList2.Find(entity_id)))
  480. return (GCC_APP_NOT_ENROLLED);
  481. DBG_SAVE_FILE_LINE
  482. registry_key_data = new CRegKeyContainer(registry_key, &rc);
  483. if ((registry_key_data == NULL) || (rc != GCC_NO_ERROR))
  484. {
  485. ERROR_OUT(("CRegistry::SetParameter: can't create regitry key"));
  486. rc = GCC_ALLOCATION_FAILURE;
  487. goto MyExit;
  488. }
  489. if (m_fTopProvider == FALSE)
  490. {
  491. m_pMCSUserObject->RegistrySetParameterRequest(registry_key_data,
  492. parameter_value,
  493. modification_rights,
  494. entity_id);
  495. // The registry key data object is no longer needed here
  496. registry_key_data->Release();
  497. rc = GCC_NO_ERROR;
  498. goto MyExit;
  499. }
  500. // no PDU is sent when request occurs at the top provider
  501. // Set up the registry item here
  502. if (parameter_value != NULL)
  503. {
  504. registry_item.item_type = GCC_REGISTRY_PARAMETER;
  505. registry_item.parameter = *parameter_value;
  506. }
  507. else
  508. {
  509. registry_item.item_type = GCC_REGISTRY_NONE;
  510. }
  511. DBG_SAVE_FILE_LINE
  512. registry_item_data = new CRegItem(&registry_item, &rc);
  513. if ((registry_item_data == NULL) || (rc != GCC_NO_ERROR))
  514. {
  515. ERROR_OUT(("CRegistry::SetParameter: can't create regitry item"));
  516. rc = GCC_ALLOCATION_FAILURE;
  517. goto MyExit;
  518. }
  519. /*
  520. ** First check to see if the registry entry exists and if it
  521. ** does check the ownership and modification rights to make
  522. ** sure this node has permission to change the entry.
  523. */
  524. registry_entry = GetRegistryEntry(registry_key_data);
  525. if (registry_entry != NULL)
  526. {
  527. /*
  528. ** Here we make sure that this request is comming from an
  529. ** APE that previously enrolled.
  530. */
  531. CAppRosterMgr *lpAppRosterMgr;
  532. m_pAppRosterMgrList->Reset();
  533. while (NULL != (lpAppRosterMgr = m_pAppRosterMgrList->Iterate()))
  534. {
  535. if (lpAppRosterMgr->IsAPEEnrolled(registry_key_data->GetSessionKey(),
  536. m_pMCSUserObject->GetMyNodeID(),
  537. entity_id))
  538. {
  539. application_is_enrolled = TRUE;
  540. break;
  541. }
  542. }
  543. /*
  544. ** Check ownership rights here: First check is to make
  545. ** sure that this is the owner if Owner rights is
  546. ** specified. Next check is to make sure that
  547. */
  548. if (((registry_entry->modification_rights == GCC_OWNER_RIGHTS) &&
  549. (registry_entry->owner_id == m_pMCSUserObject->GetMyNodeID()) &&
  550. (registry_entry->entity_id == entity_id)) ||
  551. ((registry_entry->modification_rights == GCC_SESSION_RIGHTS) &&
  552. (application_is_enrolled)) ||
  553. (registry_entry->modification_rights == GCC_PUBLIC_RIGHTS) ||
  554. (registry_entry->owner_id == 0))
  555. {
  556. /*
  557. ** Monitoring state should not be affected by
  558. ** this request.
  559. */
  560. *registry_entry->entry_item = *registry_item_data;
  561. /*
  562. ** Only the owner is allowed to change the modification
  563. ** rights of a registry entry (unless the entry is
  564. ** unowned). Also if there is no owner, we set up the
  565. ** new owner here.
  566. */
  567. if (((registry_entry->owner_id == m_pMCSUserObject->GetMyNodeID()) &&
  568. (registry_entry->entity_id == entity_id)) ||
  569. (registry_entry->owner_id == 0))
  570. {
  571. registry_entry->owner_id = m_pMCSUserObject->GetMyNodeID();
  572. registry_entry->entity_id = entity_id;
  573. /*
  574. ** If no modification rights are specified we must
  575. ** set the modification rights to be public.
  576. */
  577. if (modification_rights != GCC_NO_MODIFICATION_RIGHTS_SPECIFIED)
  578. {
  579. registry_entry->modification_rights = modification_rights;
  580. }
  581. }
  582. // Send Monitor Indication if necessary
  583. if (registry_entry->monitoring_state == ON)
  584. {
  585. /*
  586. ** Deliver the monitor indication to the Top
  587. ** Provider's Node Controller if necessary.
  588. */
  589. SendMonitorEntryIndicationMessage(registry_entry);
  590. /*
  591. ** Broadcast a monitor entry indication to all
  592. ** nodes in the conference.
  593. */
  594. m_pMCSUserObject->RegistryMonitorEntryIndication(
  595. registry_entry->registry_key,
  596. registry_entry->entry_item,
  597. registry_entry->owner_id,
  598. registry_entry->entity_id,
  599. registry_entry->modification_rights);
  600. }
  601. // Send success for the result
  602. result = GCC_RESULT_SUCCESSFUL;
  603. }
  604. else
  605. {
  606. result = GCC_RESULT_INDEX_ALREADY_OWNED;
  607. }
  608. requester_sap->RegistryConfirm(
  609. m_nConfID,
  610. GCC_SET_PARAMETER_CONFIRM,
  611. registry_entry->registry_key,
  612. registry_entry->entry_item,
  613. registry_entry->modification_rights,
  614. registry_entry->owner_id,
  615. registry_entry->entity_id,
  616. FALSE,
  617. result);
  618. // The registry key data object is no longer needed
  619. registry_key_data->Release();
  620. // The registry item data object is no longer needed
  621. registry_item_data->Release();
  622. rc = GCC_NO_ERROR;
  623. goto MyExit;
  624. }
  625. // registry entry does not exist, create one.
  626. DBG_SAVE_FILE_LINE
  627. registry_entry = new REG_ENTRY;
  628. if (registry_entry == NULL)
  629. {
  630. ERROR_OUT(("CRegistry::SetParameter: can't create regitry entry"));
  631. rc = GCC_ALLOCATION_FAILURE;
  632. goto MyExit;
  633. }
  634. // Fill in the new entry
  635. registry_entry->registry_key = registry_key_data;
  636. registry_entry->entry_item = registry_item_data;
  637. registry_entry->monitoring_state = OFF;
  638. registry_entry->owner_id = m_pMCSUserObject->GetMyNodeID();
  639. registry_entry->entity_id = entity_id;
  640. /*
  641. ** If no modification rights are specified we must
  642. ** initialize the modification rights to be public.
  643. ** Note that modification rights are only specified
  644. ** for the SetParameter call.
  645. */
  646. registry_entry->modification_rights =
  647. (modification_rights == GCC_NO_MODIFICATION_RIGHTS_SPECIFIED) ?
  648. GCC_PUBLIC_RIGHTS :
  649. modification_rights;
  650. // Add registry entry to registry list
  651. m_RegEntryList.Append(registry_entry);
  652. // Send success for the result
  653. requester_sap->RegistryConfirm(
  654. m_nConfID,
  655. GCC_SET_PARAMETER_CONFIRM,
  656. registry_entry->registry_key,
  657. registry_entry->entry_item,
  658. registry_entry->modification_rights,
  659. registry_entry->owner_id,
  660. registry_entry->entity_id,
  661. FALSE,
  662. GCC_RESULT_SUCCESSFUL);
  663. rc = GCC_NO_ERROR;
  664. MyExit:
  665. if (GCC_NO_ERROR != rc)
  666. {
  667. if (NULL != registry_key_data)
  668. {
  669. registry_key_data->Release();
  670. }
  671. if (NULL != registry_item_data)
  672. {
  673. registry_item_data->Release();
  674. }
  675. delete registry_entry;
  676. }
  677. return (rc);
  678. }
  679. /*
  680. * GCCError RetrieveEntry ()
  681. *
  682. * Public Function Description
  683. * This routine is used by a local APE to obtain an item that was
  684. * registered with GCC. If this registry object does NOT
  685. * live at the top provider node this class is responsible for
  686. * forwarding the request on up to the top provider.
  687. */
  688. GCCError CRegistry::RetrieveEntry (
  689. PGCCRegistryKey registry_key,
  690. EntityID entity_id )
  691. {
  692. GCCError rc;
  693. REG_ENTRY *registry_entry;
  694. CRegKeyContainer *registry_key_data = NULL; // a must
  695. CAppSap *requester_sap;
  696. if (NULL == (requester_sap = m_AppSapEidList2.Find(entity_id)))
  697. {
  698. return GCC_APP_NOT_ENROLLED;
  699. }
  700. DBG_SAVE_FILE_LINE
  701. registry_key_data = new CRegKeyContainer(registry_key, &rc);
  702. if ((registry_key_data == NULL) || (rc != GCC_NO_ERROR))
  703. {
  704. ERROR_OUT(("CRegistry::RetrieveEntry: can't create regitry key"));
  705. rc = GCC_ALLOCATION_FAILURE;
  706. goto MyExit;
  707. }
  708. if (m_fTopProvider == FALSE)
  709. {
  710. m_pMCSUserObject->RegistryRetrieveEntryRequest(registry_key_data, entity_id);
  711. rc = GCC_NO_ERROR;
  712. goto MyExit;
  713. }
  714. // no PDU is sent when request occurs at the top provider
  715. registry_entry = GetRegistryEntry(registry_key_data);
  716. if (registry_entry != NULL)
  717. {
  718. // Send back a positive result with the entry item
  719. requester_sap->RegistryConfirm(
  720. m_nConfID,
  721. GCC_RETRIEVE_ENTRY_CONFIRM,
  722. registry_entry->registry_key,
  723. registry_entry->entry_item,
  724. registry_entry->modification_rights,
  725. registry_entry->owner_id,
  726. registry_entry->entity_id,
  727. FALSE,
  728. GCC_RESULT_SUCCESSFUL);
  729. }
  730. else
  731. {
  732. // Send back a negative result
  733. requester_sap->RegistryConfirm(
  734. m_nConfID,
  735. GCC_RETRIEVE_ENTRY_CONFIRM,
  736. registry_key_data,
  737. m_pEmptyRegItem,
  738. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  739. 0, // No owner id
  740. 0, // No entity id
  741. FALSE,
  742. GCC_RESULT_ENTRY_DOES_NOT_EXIST);
  743. }
  744. rc = GCC_NO_ERROR;
  745. MyExit:
  746. if (NULL != registry_key_data)
  747. {
  748. registry_key_data->Release();
  749. }
  750. return (rc);
  751. }
  752. /*
  753. * GCCError DeleteEntry ()
  754. *
  755. * Public Function Description
  756. * This routine is used by a local APE to delete an item that was
  757. * registered with GCC. If this registry object does NOT
  758. * live at the top provider node this class is responsible for
  759. * forwarding the request on up to the top provider.
  760. */
  761. GCCError CRegistry::DeleteEntry (
  762. PGCCRegistryKey registry_key,
  763. EntityID entity_id )
  764. {
  765. GCCError rc;
  766. REG_ENTRY *registry_entry;
  767. CRegKeyContainer *registry_key_data = NULL; // a must
  768. CAppSap *requester_sap;
  769. if (NULL == (requester_sap = m_AppSapEidList2.Find(entity_id)))
  770. {
  771. return GCC_APP_NOT_ENROLLED;
  772. }
  773. DBG_SAVE_FILE_LINE
  774. registry_key_data = new CRegKeyContainer(registry_key, &rc);
  775. if ((registry_key_data == NULL) || (rc != GCC_NO_ERROR))
  776. {
  777. ERROR_OUT(("CRegistry::DeleteEntry: can't create regitry key"));
  778. rc = GCC_ALLOCATION_FAILURE;
  779. goto MyExit;
  780. }
  781. if (m_fTopProvider == FALSE)
  782. {
  783. m_pMCSUserObject->RegistryDeleteEntryRequest(registry_key_data, entity_id);
  784. rc = GCC_NO_ERROR;
  785. goto MyExit;
  786. }
  787. // no PDU is sent when request occurs at the top provider
  788. /*
  789. ** First check to see if the registry entry exists and if it does
  790. ** check the ownership to make sure this node has permission to
  791. ** change the entry.
  792. */
  793. registry_entry = GetRegistryEntry(registry_key_data);
  794. if (registry_entry != NULL)
  795. {
  796. if (((registry_entry->owner_id == m_pMCSUserObject->GetMyNodeID()) &&
  797. (registry_entry->entity_id == entity_id)) ||
  798. (registry_entry->owner_id == 0))
  799. {
  800. /*
  801. ** First convert this to a non-entry incase it needs to
  802. ** be included in a monitor indication. We first delete
  803. ** the old entry item and replace it with an Emtpy item.
  804. */
  805. registry_entry->entry_item->Release();
  806. registry_entry->entry_item = m_pEmptyRegItem;
  807. registry_entry->owner_id = 0;
  808. registry_entry->entity_id = 0;
  809. registry_entry->modification_rights = GCC_NO_MODIFICATION_RIGHTS_SPECIFIED;
  810. // Send Monitor Indication if necessary
  811. if (registry_entry->monitoring_state == ON)
  812. {
  813. /*
  814. ** Deliver the monitor indication to the Top
  815. ** Provider's Node Controller if necessary.
  816. */
  817. SendMonitorEntryIndicationMessage(registry_entry);
  818. /*
  819. ** Broadcast a monitor entry indication to all
  820. ** nodes in the conference.
  821. */
  822. m_pMCSUserObject->RegistryMonitorEntryIndication(
  823. registry_entry->registry_key,
  824. registry_entry->entry_item,
  825. registry_entry->owner_id,
  826. registry_entry->entity_id,
  827. registry_entry->modification_rights);
  828. }
  829. m_RegEntryList.Remove(registry_entry);
  830. if (NULL != registry_entry->registry_key)
  831. {
  832. registry_entry->registry_key->Release();
  833. }
  834. delete registry_entry;
  835. // Send success for the result
  836. requester_sap->RegistryConfirm(
  837. m_nConfID,
  838. GCC_DELETE_ENTRY_CONFIRM,
  839. registry_key_data,
  840. NULL,
  841. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  842. 0,
  843. 0,
  844. FALSE,
  845. GCC_RESULT_SUCCESSFUL);
  846. }
  847. else
  848. {
  849. // No ownership rights send back negative result
  850. requester_sap->RegistryConfirm (
  851. m_nConfID,
  852. GCC_DELETE_ENTRY_CONFIRM,
  853. registry_entry->registry_key,
  854. registry_entry->entry_item,
  855. registry_entry->modification_rights,
  856. registry_entry->owner_id,
  857. registry_entry->entity_id,
  858. FALSE,
  859. GCC_RESULT_INDEX_ALREADY_OWNED);
  860. }
  861. }
  862. else
  863. {
  864. // Send failure for the result. Entry does not exist
  865. requester_sap->RegistryConfirm (
  866. m_nConfID,
  867. GCC_DELETE_ENTRY_CONFIRM,
  868. registry_key_data,
  869. NULL,
  870. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  871. 0,
  872. 0,
  873. FALSE,
  874. GCC_RESULT_ENTRY_DOES_NOT_EXIST);
  875. }
  876. rc = GCC_NO_ERROR;
  877. MyExit:
  878. // The registry key data object is no longer needed here
  879. if (NULL != registry_key_data)
  880. {
  881. registry_key_data->Release();
  882. }
  883. return (rc);
  884. }
  885. /*
  886. * GCCError MonitorRequest ()
  887. *
  888. * Public Function Description
  889. * This routine is used by a local APE to monitor an item that was
  890. * registered with GCC. If this registry object does NOT
  891. * live at the top provider node this class is responsible for
  892. * forwarding the request on up to the top provider.
  893. */
  894. GCCError CRegistry::MonitorRequest (
  895. PGCCRegistryKey registry_key,
  896. BOOL enable_delivery,
  897. EntityID entity_id )
  898. {
  899. GCCError rc = GCC_NO_ERROR;
  900. REG_ENTRY *registry_entry;
  901. CRegKeyContainer *registry_key_data;
  902. GCCResult result = GCC_RESULT_SUCCESSFUL;
  903. CAppSap *requester_sap;
  904. BOOL fToConfirm = FALSE;
  905. if (NULL == (requester_sap = m_AppSapEidList2.Find(entity_id)))
  906. {
  907. return GCC_APP_NOT_ENROLLED;
  908. }
  909. /*
  910. ** First set up the Registry Key. Return immediately if a resource
  911. ** failure occurs.
  912. */
  913. DBG_SAVE_FILE_LINE
  914. registry_key_data = new CRegKeyContainer(registry_key, &rc);
  915. if ((registry_key_data != NULL) && (rc == GCC_NO_ERROR))
  916. {
  917. /*
  918. ** If the request is recieved at a node that is not the top
  919. ** provider we must send the request on to the top provider.
  920. */
  921. if (m_fTopProvider == FALSE)
  922. {
  923. if (enable_delivery)
  924. {
  925. /*
  926. ** Here we first go ahead and add the requesting APE to the
  927. ** list of applications wishing to monitor this particular
  928. ** entry. Note that if this entry does not exists at the top
  929. ** provider, this entry will be removed during the confirm.
  930. */
  931. rc = AddAPEToMonitoringList(registry_key_data, entity_id, requester_sap);
  932. if (rc == GCC_NO_ERROR)
  933. {
  934. /*
  935. ** Wait for the response before sending the confirm
  936. ** if we get this far.
  937. */
  938. m_pMCSUserObject->RegistryMonitorRequest(registry_key_data, entity_id);
  939. }
  940. else
  941. {
  942. result = GCC_RESULT_RESOURCES_UNAVAILABLE;
  943. fToConfirm = TRUE;
  944. }
  945. }
  946. else
  947. {
  948. RemoveAPEFromMonitoringList(registry_key_data, entity_id);
  949. result = GCC_RESULT_SUCCESSFUL;
  950. fToConfirm = TRUE;
  951. }
  952. }
  953. else // No PDU is sent when request occurs at the top provider
  954. {
  955. if (enable_delivery)
  956. {
  957. /*
  958. ** First check to see if the registry entry exists. If it does
  959. ** not we go ahead and create an empty entry so that we can
  960. ** add the monitoring APE to that entries list of monitoring
  961. ** APEs.
  962. */
  963. registry_entry = GetRegistryEntry(registry_key_data);
  964. if (registry_entry != NULL)
  965. {
  966. /*
  967. ** Here we go ahead and add the requesting APE to the
  968. ** list of applications wishing to monitor this entry.
  969. */
  970. rc = AddAPEToMonitoringList(registry_key_data, entity_id, requester_sap);
  971. if (rc == GCC_NO_ERROR)
  972. {
  973. // Set the monitoring state to ON
  974. registry_entry->monitoring_state = ON;
  975. }
  976. else
  977. {
  978. result = GCC_RESULT_RESOURCES_UNAVAILABLE;
  979. }
  980. }
  981. else
  982. {
  983. result = GCC_RESULT_ENTRY_DOES_NOT_EXIST;
  984. }
  985. }
  986. else
  987. {
  988. RemoveAPEFromMonitoringList(registry_key_data, entity_id);
  989. }
  990. fToConfirm = TRUE;
  991. }
  992. }
  993. else
  994. {
  995. ERROR_OUT(("CRegistry::MonitorRequest: can't create registry key"));
  996. rc = GCC_ALLOCATION_FAILURE;
  997. }
  998. if (fToConfirm)
  999. {
  1000. ASSERT(NULL != registry_key_data);
  1001. requester_sap->RegistryConfirm(
  1002. m_nConfID,
  1003. GCC_MONITOR_CONFIRM,
  1004. registry_key_data,
  1005. NULL,
  1006. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  1007. 0,
  1008. 0,
  1009. enable_delivery,
  1010. result);
  1011. }
  1012. // The registry key data object is no longer needed
  1013. if (NULL != registry_key_data)
  1014. {
  1015. registry_key_data->Release();
  1016. }
  1017. return (rc);
  1018. }
  1019. /*
  1020. * GCCError AllocateHandleRequest ()
  1021. *
  1022. * Public Function Description
  1023. * This routine is used by a local APE to allocate a specified number of
  1024. * handles from the application registry. If this registry object does NOT
  1025. * live at the top provider node this class is responsible for
  1026. * forwarding the request on up to the top provider.
  1027. */
  1028. GCCError CRegistry::AllocateHandleRequest(
  1029. UINT number_of_handles,
  1030. EntityID entity_id )
  1031. {
  1032. UINT temp_registry_handle;
  1033. CAppSap *requester_sap;
  1034. if (NULL == (requester_sap = m_AppSapEidList2.Find(entity_id)))
  1035. {
  1036. return GCC_APP_NOT_ENROLLED;
  1037. }
  1038. if (m_fTopProvider == FALSE)
  1039. {
  1040. m_pMCSUserObject->RegistryAllocateHandleRequest(number_of_handles, entity_id);
  1041. }
  1042. else // No PDU is sent when request occurs at the top provider
  1043. {
  1044. UINT nFirstHandle = 0;
  1045. GCCResult nResult;
  1046. if ((number_of_handles > 0) &&
  1047. (number_of_handles <= MAXIMUM_ALLOWABLE_ALLOCATED_HANDLES))
  1048. {
  1049. temp_registry_handle = m_nRegHandle + number_of_handles;
  1050. if (temp_registry_handle > m_nRegHandle)
  1051. {
  1052. nFirstHandle = m_nRegHandle;
  1053. nResult = GCC_RESULT_SUCCESSFUL;
  1054. m_nRegHandle = temp_registry_handle;
  1055. }
  1056. else
  1057. {
  1058. ASSERT(0 == nFirstHandle);
  1059. nResult = GCC_RESULT_NO_HANDLES_AVAILABLE;
  1060. }
  1061. }
  1062. else
  1063. {
  1064. ASSERT(0 == nFirstHandle);
  1065. nResult = GCC_RESULT_INVALID_NUMBER_OF_HANDLES;
  1066. }
  1067. requester_sap->RegistryAllocateHandleConfirm (
  1068. m_nConfID,
  1069. number_of_handles,
  1070. nFirstHandle,
  1071. nResult);
  1072. }
  1073. return (GCC_NO_ERROR);
  1074. }
  1075. /*
  1076. * GCCError ProcessRegisterChannelPDU ()
  1077. *
  1078. * Public Function Description
  1079. * This routine is used by the top provider node to process incomming
  1080. * register channel PDUs. It is responsible for returning any
  1081. * necessary responses that must be sent back to the requesting node.
  1082. */
  1083. GCCError CRegistry::ProcessRegisterChannelPDU (
  1084. CRegKeyContainer *registry_key_data,
  1085. ChannelID channel_id,
  1086. UserID requester_node_id,
  1087. EntityID requester_entity_id )
  1088. {
  1089. GCCError rc = GCC_NO_ERROR;
  1090. REG_ENTRY *registry_entry;
  1091. CRegItem *registry_item_data;
  1092. GCCRegistryItem registry_item;
  1093. BOOL application_is_enrolled = FALSE;
  1094. CAppRosterMgr *lpAppRosterMgr;
  1095. /*
  1096. ** We first make sure that this request is comming from an APE that
  1097. ** previously enrolled. Here we are not worried about a specific
  1098. ** session, only that the APE is enrolled.
  1099. */
  1100. m_pAppRosterMgrList->Reset();
  1101. while (NULL != (lpAppRosterMgr = m_pAppRosterMgrList->Iterate()))
  1102. {
  1103. if (lpAppRosterMgr->IsAPEEnrolled (requester_node_id, requester_entity_id))
  1104. {
  1105. application_is_enrolled = TRUE;
  1106. break;
  1107. }
  1108. }
  1109. if (application_is_enrolled)
  1110. {
  1111. /*
  1112. ** Next check to see if the registry entry exists and if it does
  1113. ** check the ownership to make sure this node has permission to
  1114. ** change the entry.
  1115. */
  1116. registry_entry = GetRegistryEntry ( registry_key_data );
  1117. if (registry_entry != NULL)
  1118. {
  1119. // Entry already exists, send back negative result
  1120. m_pMCSUserObject->RegistryResponse(
  1121. REGISTER_CHANNEL,
  1122. requester_node_id,
  1123. requester_entity_id,
  1124. registry_key_data,
  1125. registry_entry->entry_item,
  1126. registry_entry->modification_rights,
  1127. registry_entry->owner_id,
  1128. registry_entry->entity_id,
  1129. GCC_RESULT_ENTRY_ALREADY_EXISTS);
  1130. }
  1131. else
  1132. {
  1133. registry_item.item_type = GCC_REGISTRY_CHANNEL_ID;
  1134. registry_item.channel_id = channel_id;
  1135. DBG_SAVE_FILE_LINE
  1136. registry_item_data = new CRegItem(&registry_item, &rc);
  1137. if ((registry_item_data != NULL) && (rc == GCC_NO_ERROR))
  1138. {
  1139. DBG_SAVE_FILE_LINE
  1140. registry_entry = new REG_ENTRY;
  1141. if (registry_entry != NULL)
  1142. {
  1143. // Fill in the new entry
  1144. DBG_SAVE_FILE_LINE
  1145. registry_entry->registry_key = new CRegKeyContainer(registry_key_data, &rc);
  1146. if ((registry_entry->registry_key != NULL) && (rc == GCC_NO_ERROR))
  1147. {
  1148. registry_entry->entry_item = registry_item_data;
  1149. registry_entry->monitoring_state = OFF;
  1150. registry_entry->owner_id = requester_node_id;
  1151. registry_entry->entity_id = requester_entity_id;
  1152. /*
  1153. ** Initialize to public incase entry is switched to
  1154. ** a parameter. Note that as long as the entry is
  1155. ** not a PARAMETER modification rights will not be
  1156. ** used.
  1157. */
  1158. registry_entry->modification_rights = GCC_PUBLIC_RIGHTS;
  1159. m_RegEntryList.Append(registry_entry);
  1160. // Send success for the result
  1161. m_pMCSUserObject->RegistryResponse(
  1162. REGISTER_CHANNEL,
  1163. requester_node_id,
  1164. requester_entity_id,
  1165. registry_entry->registry_key,
  1166. registry_entry->entry_item,
  1167. registry_entry->modification_rights,
  1168. registry_entry->owner_id,
  1169. registry_entry->entity_id,
  1170. GCC_RESULT_SUCCESSFUL);
  1171. }
  1172. else if (registry_entry->registry_key == NULL)
  1173. {
  1174. delete registry_entry;
  1175. registry_item_data->Release();
  1176. rc = GCC_ALLOCATION_FAILURE;
  1177. }
  1178. else
  1179. {
  1180. registry_entry->registry_key->Release();
  1181. delete registry_entry;
  1182. registry_item_data->Release();
  1183. }
  1184. }
  1185. else
  1186. {
  1187. rc = GCC_ALLOCATION_FAILURE;
  1188. }
  1189. }
  1190. else if (registry_item_data == NULL)
  1191. {
  1192. rc = GCC_ALLOCATION_FAILURE;
  1193. }
  1194. else
  1195. {
  1196. registry_item_data->Release();
  1197. }
  1198. }
  1199. }
  1200. else
  1201. {
  1202. // Send back negative result stating invalid requester
  1203. m_pMCSUserObject->RegistryResponse(
  1204. REGISTER_CHANNEL,
  1205. requester_node_id,
  1206. requester_entity_id,
  1207. registry_key_data,
  1208. NULL,
  1209. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  1210. 0,
  1211. 0,
  1212. GCC_RESULT_INVALID_REQUESTER);
  1213. }
  1214. return (rc);
  1215. }
  1216. /*
  1217. * GCCError ProcessAssignTokenPDU ()
  1218. *
  1219. * Public Function Description
  1220. * This routine is used by the top provider node to process incomming
  1221. * register token PDUs. It is responsible for returning any
  1222. * necessary responses that must be sent back to the requesting node.
  1223. */
  1224. GCCError CRegistry::ProcessAssignTokenPDU (
  1225. CRegKeyContainer *registry_key_data,
  1226. UserID requester_node_id,
  1227. EntityID requester_entity_id )
  1228. {
  1229. GCCError rc = GCC_NO_ERROR;
  1230. REG_ENTRY *registry_entry;
  1231. CRegItem *registry_item_data;
  1232. GCCRegistryItem registry_item;
  1233. BOOL application_is_enrolled = FALSE;
  1234. CAppRosterMgr *lpAppRosterMgr;
  1235. /*
  1236. ** We first make sure that this request is comming from an APE that
  1237. ** previously enrolled. Here we are not worried about a specific
  1238. ** session, only that the APE is enrolled.
  1239. */
  1240. m_pAppRosterMgrList->Reset();
  1241. while (NULL != (lpAppRosterMgr = m_pAppRosterMgrList->Iterate()))
  1242. {
  1243. if (lpAppRosterMgr->IsAPEEnrolled (requester_node_id, requester_entity_id))
  1244. {
  1245. application_is_enrolled = TRUE;
  1246. break;
  1247. }
  1248. }
  1249. if (application_is_enrolled)
  1250. {
  1251. /*
  1252. ** First check to see if the registry entry exists and if it does
  1253. ** check the ownership to make sure this node has permission to
  1254. ** change the entry.
  1255. */
  1256. registry_entry = GetRegistryEntry ( registry_key_data );
  1257. if (registry_entry != NULL)
  1258. {
  1259. // Entry already exists, send back negative result
  1260. m_pMCSUserObject->RegistryResponse(ASSIGN_TOKEN,
  1261. requester_node_id,
  1262. requester_entity_id,
  1263. registry_key_data,
  1264. registry_entry->entry_item,
  1265. registry_entry->modification_rights,
  1266. registry_entry->owner_id,
  1267. registry_entry->entity_id,
  1268. GCC_RESULT_ENTRY_ALREADY_EXISTS);
  1269. }
  1270. else
  1271. {
  1272. DBG_SAVE_FILE_LINE
  1273. registry_entry = new REG_ENTRY;
  1274. if (registry_entry != NULL)
  1275. {
  1276. registry_item.item_type = GCC_REGISTRY_TOKEN_ID;
  1277. registry_item.token_id = GetUnusedToken();
  1278. DBG_SAVE_FILE_LINE
  1279. registry_item_data = new CRegItem(&registry_item, &rc);
  1280. if ((registry_item_data != NULL) && (rc == GCC_NO_ERROR))
  1281. {
  1282. // Fill in the new entry
  1283. DBG_SAVE_FILE_LINE
  1284. registry_entry->registry_key = new CRegKeyContainer(registry_key_data, &rc);
  1285. if ((registry_entry->registry_key != NULL) && (rc == GCC_NO_ERROR))
  1286. {
  1287. registry_entry->entry_item = registry_item_data;
  1288. registry_entry->monitoring_state = OFF;
  1289. registry_entry->owner_id = requester_node_id;
  1290. registry_entry->entity_id = requester_entity_id;
  1291. /*
  1292. ** Initialize to public incase entry is switched to
  1293. ** a parameter. Note that as long as the entry is
  1294. ** not a PARAMETER modification rights will not be
  1295. ** used.
  1296. */
  1297. registry_entry->modification_rights = GCC_PUBLIC_RIGHTS;
  1298. // Add registry entry to registry list
  1299. m_RegEntryList.Append(registry_entry);
  1300. // Send success for the result
  1301. m_pMCSUserObject->RegistryResponse(
  1302. ASSIGN_TOKEN,
  1303. requester_node_id,
  1304. requester_entity_id,
  1305. registry_key_data,
  1306. registry_entry->entry_item,
  1307. registry_entry->modification_rights,
  1308. registry_entry->owner_id,
  1309. registry_entry->entity_id,
  1310. GCC_RESULT_SUCCESSFUL);
  1311. }
  1312. else if (registry_entry->registry_key == NULL)
  1313. {
  1314. registry_item_data->Release();
  1315. delete registry_entry;
  1316. rc = GCC_ALLOCATION_FAILURE;
  1317. }
  1318. else
  1319. {
  1320. registry_entry->registry_key->Release();
  1321. registry_item_data->Release();
  1322. delete registry_entry;
  1323. }
  1324. }
  1325. else
  1326. {
  1327. if (registry_item_data == NULL)
  1328. {
  1329. rc = GCC_ALLOCATION_FAILURE;
  1330. }
  1331. else
  1332. {
  1333. registry_item_data->Release();
  1334. }
  1335. delete registry_entry;
  1336. }
  1337. }
  1338. else
  1339. {
  1340. rc = GCC_ALLOCATION_FAILURE;
  1341. }
  1342. }
  1343. }
  1344. else
  1345. {
  1346. m_pMCSUserObject->RegistryResponse(
  1347. ASSIGN_TOKEN,
  1348. requester_node_id,
  1349. requester_entity_id,
  1350. registry_key_data,
  1351. NULL,
  1352. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  1353. 0,
  1354. 0,
  1355. GCC_RESULT_INVALID_REQUESTER);
  1356. }
  1357. return (rc);
  1358. }
  1359. /*
  1360. * GCCError ProcessSetParameterPDU ()
  1361. *
  1362. * Public Function Description
  1363. * This routine is used by the top provider node to process incomming
  1364. * register parameter PDUs. It is responsible for returning any
  1365. * necessary responses that must be sent back to the requesting node.
  1366. */
  1367. GCCError CRegistry::ProcessSetParameterPDU (
  1368. CRegKeyContainer *registry_key_data,
  1369. LPOSTR parameter_value,
  1370. GCCModificationRights modification_rights,
  1371. UserID requester_node_id,
  1372. EntityID requester_entity_id )
  1373. {
  1374. GCCError rc = GCC_NO_ERROR;
  1375. REG_ENTRY *registry_entry;
  1376. CRegItem *registry_item_data;
  1377. GCCResult result;
  1378. GCCRegistryItem registry_item;
  1379. BOOL application_is_enrolled = FALSE;
  1380. CAppRosterMgr *lpAppRosterMgr;
  1381. /*
  1382. ** We first make sure that this request is comming from an APE that
  1383. ** previously enrolled. Here we are not worried about a specific
  1384. ** session, only that the APE is enrolled.
  1385. */
  1386. m_pAppRosterMgrList->Reset();
  1387. while (NULL != (lpAppRosterMgr = m_pAppRosterMgrList->Iterate()))
  1388. {
  1389. if (lpAppRosterMgr->IsAPEEnrolled (requester_node_id, requester_entity_id))
  1390. {
  1391. application_is_enrolled = TRUE;
  1392. break;
  1393. }
  1394. }
  1395. if (application_is_enrolled)
  1396. {
  1397. // Set up the registry item
  1398. if (parameter_value != NULL)
  1399. {
  1400. registry_item.item_type = GCC_REGISTRY_PARAMETER;
  1401. registry_item.parameter = *parameter_value;
  1402. }
  1403. else
  1404. registry_item.item_type = GCC_REGISTRY_NONE;
  1405. /*
  1406. ** Check to see if the registry entry exists and if it does
  1407. ** check the ownership to make sure this node has permission to
  1408. ** change the entry.
  1409. */
  1410. registry_entry = GetRegistryEntry ( registry_key_data );
  1411. if (registry_entry != NULL)
  1412. {
  1413. /*
  1414. ** Here we make sure that this request is comming from an
  1415. ** APE that previously enrolled in the appropriate session.
  1416. */
  1417. m_pAppRosterMgrList->Reset();
  1418. while (NULL != (lpAppRosterMgr = m_pAppRosterMgrList->Iterate()))
  1419. {
  1420. if (lpAppRosterMgr->IsAPEEnrolled (registry_key_data->GetSessionKey (),
  1421. requester_node_id,
  1422. requester_entity_id))
  1423. {
  1424. application_is_enrolled = TRUE;
  1425. break;
  1426. }
  1427. }
  1428. /*
  1429. ** Check ownership rights here: First check is to make
  1430. ** sure that this is the owner if Owner rights is
  1431. ** specified. Next check is to make sure that
  1432. */
  1433. if (((registry_entry->modification_rights == GCC_OWNER_RIGHTS) &&
  1434. (registry_entry->owner_id == requester_node_id) &&
  1435. (registry_entry->entity_id == requester_entity_id)) ||
  1436. ((registry_entry->modification_rights == GCC_SESSION_RIGHTS) &&
  1437. (application_is_enrolled)) ||
  1438. (registry_entry->modification_rights == GCC_PUBLIC_RIGHTS) ||
  1439. (registry_entry->owner_id == 0))
  1440. {
  1441. DBG_SAVE_FILE_LINE
  1442. registry_item_data = new CRegItem(&registry_item, &rc);
  1443. if ((registry_item_data != NULL) && (rc == GCC_NO_ERROR))
  1444. {
  1445. // Monitoring state should not be affected by this request
  1446. *registry_entry->entry_item = *registry_item_data;
  1447. /*
  1448. ** Only the owner is allowed to change the modification
  1449. ** rights of a registry entry (unless the entry is
  1450. ** unowned). Also if there is no owner, we set up the
  1451. ** new owner here.
  1452. */
  1453. if (((registry_entry->owner_id == requester_node_id) &&
  1454. (registry_entry->entity_id == requester_entity_id)) ||
  1455. (registry_entry->owner_id == 0))
  1456. {
  1457. /*
  1458. ** This will take care of setting up the new owner if
  1459. ** one exists.
  1460. */
  1461. registry_entry->owner_id = requester_node_id;
  1462. registry_entry->entity_id = requester_entity_id;
  1463. /*
  1464. ** If no modification rights are specified we must
  1465. ** set the modification rights to be public.
  1466. */
  1467. if (modification_rights !=
  1468. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED)
  1469. {
  1470. registry_entry->modification_rights = modification_rights;
  1471. }
  1472. }
  1473. // Send Monitor Indication if necessary
  1474. if (registry_entry->monitoring_state == ON)
  1475. {
  1476. /*
  1477. ** Deliver the monitor indication to the Top
  1478. ** Provider's Node Controller if necessary.
  1479. */
  1480. SendMonitorEntryIndicationMessage(registry_entry);
  1481. /*
  1482. ** Broadcast a monitor entry indication to all
  1483. ** nodes in the conference.
  1484. */
  1485. m_pMCSUserObject->RegistryMonitorEntryIndication(
  1486. registry_entry->registry_key,
  1487. registry_entry->entry_item,
  1488. registry_entry->owner_id,
  1489. registry_entry->entity_id,
  1490. registry_entry->modification_rights);
  1491. }
  1492. registry_item_data->Release();
  1493. // Send success for the result
  1494. result = GCC_RESULT_SUCCESSFUL;
  1495. }
  1496. else if (registry_item_data == NULL)
  1497. {
  1498. rc = GCC_ALLOCATION_FAILURE;
  1499. result = GCC_RESULT_RESOURCES_UNAVAILABLE;
  1500. }
  1501. else
  1502. {
  1503. registry_item_data->Release();
  1504. result = GCC_RESULT_RESOURCES_UNAVAILABLE;
  1505. }
  1506. }
  1507. else
  1508. result = GCC_RESULT_INDEX_ALREADY_OWNED;
  1509. // No ownership rights send back negative result
  1510. m_pMCSUserObject->RegistryResponse(SET_PARAMETER,
  1511. requester_node_id,
  1512. requester_entity_id,
  1513. registry_key_data,
  1514. registry_entry->entry_item,
  1515. registry_entry->modification_rights,
  1516. registry_entry->owner_id,
  1517. registry_entry->entity_id,
  1518. result);
  1519. }
  1520. else
  1521. {
  1522. DBG_SAVE_FILE_LINE
  1523. registry_entry = new REG_ENTRY;
  1524. if (registry_entry != NULL)
  1525. {
  1526. DBG_SAVE_FILE_LINE
  1527. registry_item_data = new CRegItem(&registry_item, &rc);
  1528. if ((registry_item_data != NULL) && (rc == GCC_NO_ERROR))
  1529. {
  1530. // Fill in the new entry
  1531. DBG_SAVE_FILE_LINE
  1532. registry_entry->registry_key = new CRegKeyContainer(registry_key_data, &rc);
  1533. if ((registry_entry->registry_key != NULL) && (rc == GCC_NO_ERROR))
  1534. {
  1535. registry_entry->entry_item = registry_item_data;
  1536. registry_entry->monitoring_state = OFF;
  1537. registry_entry->owner_id = requester_node_id;
  1538. registry_entry->entity_id = requester_entity_id;
  1539. /*
  1540. ** If no modification rights are specified we must
  1541. ** initialize the modification rights to be public.
  1542. ** Note that modification rights are only specified
  1543. ** for the SetParameter call.
  1544. */
  1545. if (modification_rights == GCC_NO_MODIFICATION_RIGHTS_SPECIFIED)
  1546. {
  1547. registry_entry->modification_rights = GCC_PUBLIC_RIGHTS;
  1548. }
  1549. else
  1550. {
  1551. registry_entry->modification_rights = modification_rights;
  1552. }
  1553. // Add registry entry to registry list
  1554. m_RegEntryList.Append(registry_entry);
  1555. // Send success for the result
  1556. m_pMCSUserObject->RegistryResponse(
  1557. SET_PARAMETER,
  1558. requester_node_id,
  1559. requester_entity_id,
  1560. registry_key_data,
  1561. registry_entry->entry_item,
  1562. registry_entry->modification_rights,
  1563. registry_entry->owner_id,
  1564. registry_entry->entity_id,
  1565. GCC_RESULT_SUCCESSFUL);
  1566. }
  1567. else if (registry_entry->registry_key == NULL)
  1568. {
  1569. registry_item_data->Release();
  1570. delete registry_entry;
  1571. rc = GCC_ALLOCATION_FAILURE;
  1572. }
  1573. else
  1574. {
  1575. registry_entry->registry_key->Release();
  1576. registry_item_data->Release();
  1577. delete registry_entry;
  1578. }
  1579. }
  1580. else if (registry_item_data == NULL)
  1581. {
  1582. delete registry_entry;
  1583. rc = GCC_ALLOCATION_FAILURE;
  1584. }
  1585. }
  1586. else
  1587. {
  1588. rc = GCC_ALLOCATION_FAILURE;
  1589. }
  1590. }
  1591. }
  1592. else
  1593. {
  1594. m_pMCSUserObject->RegistryResponse(
  1595. SET_PARAMETER,
  1596. requester_node_id,
  1597. requester_entity_id,
  1598. registry_key_data,
  1599. NULL,
  1600. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  1601. 0,
  1602. 0,
  1603. GCC_RESULT_INVALID_REQUESTER);
  1604. }
  1605. return (rc);
  1606. }
  1607. /*
  1608. * void ProcessRetrieveEntryPDU ()
  1609. *
  1610. * Public Function Description
  1611. * This routine is used by the top provider node to process an incomming
  1612. * request to retrieve a registry entry. It is responsible for returning
  1613. * any necessary responses that must be sent back to the requesting node.
  1614. */
  1615. void CRegistry::ProcessRetrieveEntryPDU (
  1616. CRegKeyContainer *registry_key_data,
  1617. UserID requester_node_id,
  1618. EntityID requester_entity_id)
  1619. {
  1620. REG_ENTRY *registry_entry;
  1621. registry_entry = GetRegistryEntry ( registry_key_data );
  1622. if (registry_entry != NULL)
  1623. {
  1624. // Send back a positive result with the entry item
  1625. m_pMCSUserObject->RegistryResponse(RETRIEVE_ENTRY,
  1626. requester_node_id,
  1627. requester_entity_id,
  1628. registry_key_data,
  1629. registry_entry->entry_item,
  1630. registry_entry->modification_rights,
  1631. registry_entry->owner_id,
  1632. registry_entry->entity_id,
  1633. GCC_RESULT_SUCCESSFUL);
  1634. }
  1635. else
  1636. {
  1637. // Send back a negative result
  1638. m_pMCSUserObject->RegistryResponse(RETRIEVE_ENTRY,
  1639. requester_node_id,
  1640. requester_entity_id,
  1641. registry_key_data,
  1642. m_pEmptyRegItem,
  1643. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  1644. 0,
  1645. 0,
  1646. GCC_RESULT_ENTRY_DOES_NOT_EXIST);
  1647. }
  1648. }
  1649. /*
  1650. * void ProcessDeleteEntryPDU ()
  1651. *
  1652. * Public Function Description
  1653. * This routine is used by the top provider node to process an incomming
  1654. * request to delete a registry entry. It is responsible for returning
  1655. * any necessary responses that must be sent back to the requesting node.
  1656. */
  1657. void CRegistry::ProcessDeleteEntryPDU (
  1658. CRegKeyContainer *registry_key_data,
  1659. UserID requester_node_id,
  1660. EntityID requester_entity_id)
  1661. {
  1662. REG_ENTRY *registry_entry;
  1663. BOOL application_is_enrolled = FALSE;
  1664. CAppRosterMgr *lpAppRosterMgr;
  1665. /*
  1666. ** We first make sure that this request is comming from an APE that
  1667. ** previously enrolled. Here we are not worried about a specific
  1668. ** session, only that the APE is enrolled.
  1669. */
  1670. m_pAppRosterMgrList->Reset();
  1671. while (NULL != (lpAppRosterMgr = m_pAppRosterMgrList->Iterate()))
  1672. {
  1673. if (lpAppRosterMgr->IsAPEEnrolled (requester_node_id, requester_entity_id))
  1674. {
  1675. application_is_enrolled = TRUE;
  1676. break;
  1677. }
  1678. }
  1679. if (application_is_enrolled)
  1680. {
  1681. /*
  1682. ** First check to see if the registry entry exists and if it does
  1683. ** check the ownership to make sure this node has permission to
  1684. ** change the entry.
  1685. */
  1686. registry_entry = GetRegistryEntry ( registry_key_data );
  1687. if (registry_entry != NULL)
  1688. {
  1689. if (((registry_entry->owner_id == requester_node_id) &&
  1690. (registry_entry->entity_id == requester_entity_id)) ||
  1691. (registry_entry->owner_id == NULL))
  1692. {
  1693. m_pMCSUserObject->RegistryResponse(
  1694. DELETE_ENTRY,
  1695. requester_node_id,
  1696. requester_entity_id,
  1697. registry_key_data,
  1698. registry_entry->entry_item,
  1699. registry_entry->modification_rights,
  1700. registry_entry->owner_id,
  1701. registry_entry->entity_id,
  1702. GCC_RESULT_SUCCESSFUL);
  1703. /*
  1704. ** First convert this to a non-entry incase it needs to
  1705. ** be included in a monitor indication. We first delete
  1706. ** the old entry item and replace it with an Emtpy item.
  1707. */
  1708. if (NULL != registry_entry->entry_item)
  1709. {
  1710. registry_entry->entry_item->Release();
  1711. }
  1712. registry_entry->entry_item = m_pEmptyRegItem;
  1713. registry_entry->owner_id = 0;
  1714. registry_entry->entity_id = 0;
  1715. registry_entry->modification_rights = GCC_NO_MODIFICATION_RIGHTS_SPECIFIED;
  1716. // Send Monitor Indication if necessary
  1717. if (registry_entry->monitoring_state == ON)
  1718. {
  1719. /*
  1720. ** Deliver the monitor indication to the Top
  1721. ** Provider's Node Controller if necessary.
  1722. */
  1723. SendMonitorEntryIndicationMessage(registry_entry);
  1724. /*
  1725. ** Broadcast a monitor entry indication to all
  1726. ** nodes in the conference.
  1727. */
  1728. m_pMCSUserObject->RegistryMonitorEntryIndication(
  1729. registry_entry->registry_key,
  1730. registry_entry->entry_item,
  1731. registry_entry->owner_id,
  1732. registry_entry->entity_id,
  1733. registry_entry->modification_rights);
  1734. }
  1735. // Remove the entry from the list
  1736. m_RegEntryList.Remove(registry_entry);
  1737. if (NULL != registry_entry->registry_key)
  1738. {
  1739. registry_entry->registry_key->Release();
  1740. }
  1741. delete registry_entry;
  1742. }
  1743. else
  1744. {
  1745. // No ownership rights send back negative result
  1746. m_pMCSUserObject->RegistryResponse(
  1747. DELETE_ENTRY,
  1748. requester_node_id,
  1749. requester_entity_id,
  1750. registry_key_data,
  1751. registry_entry->entry_item,
  1752. registry_entry->modification_rights,
  1753. registry_entry->owner_id,
  1754. registry_entry->entity_id,
  1755. GCC_RESULT_INDEX_ALREADY_OWNED);
  1756. }
  1757. }
  1758. else
  1759. {
  1760. // Send failure for the result. Entry does not exist
  1761. m_pMCSUserObject->RegistryResponse(
  1762. DELETE_ENTRY,
  1763. requester_node_id,
  1764. requester_entity_id,
  1765. registry_key_data,
  1766. m_pEmptyRegItem,
  1767. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  1768. 0,
  1769. 0,
  1770. GCC_RESULT_ENTRY_DOES_NOT_EXIST);
  1771. }
  1772. }
  1773. else
  1774. {
  1775. m_pMCSUserObject->RegistryResponse(
  1776. DELETE_ENTRY,
  1777. requester_node_id,
  1778. requester_entity_id,
  1779. registry_key_data,
  1780. NULL,
  1781. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  1782. 0,
  1783. 0,
  1784. GCC_RESULT_INVALID_REQUESTER);
  1785. }
  1786. }
  1787. /*
  1788. * void ProcessMonitorEntryPDU ()
  1789. *
  1790. * Public Function Description
  1791. * This routine is used by the top provider node to process an incomming
  1792. * request to monitor a registry entry. It is responsible for returning
  1793. * any necessary responses that must be sent back to the requesting node.
  1794. */
  1795. void CRegistry::ProcessMonitorEntryPDU (
  1796. CRegKeyContainer *registry_key_data,
  1797. UserID requester_node_id,
  1798. EntityID requester_entity_id )
  1799. {
  1800. REG_ENTRY *registry_entry;
  1801. /*
  1802. ** First check to see if the registry entry exists and if it does
  1803. ** check the ownership to make sure this node has permission to
  1804. ** change the entry.
  1805. */
  1806. registry_entry = GetRegistryEntry ( registry_key_data );
  1807. if (registry_entry != NULL)
  1808. {
  1809. // Set the monitoring state to on for the life of this entry.
  1810. registry_entry->monitoring_state = ON;
  1811. // No ownership rights send back negative result
  1812. m_pMCSUserObject->RegistryResponse(MONITOR_ENTRY,
  1813. requester_node_id,
  1814. requester_entity_id,
  1815. registry_key_data,
  1816. registry_entry->entry_item,
  1817. registry_entry->modification_rights,
  1818. registry_entry->owner_id,
  1819. registry_entry->entity_id,
  1820. GCC_RESULT_SUCCESSFUL);
  1821. }
  1822. else
  1823. {
  1824. // Send failure for the result. Entry does not exist
  1825. m_pMCSUserObject->RegistryResponse(MONITOR_ENTRY,
  1826. requester_node_id,
  1827. requester_entity_id,
  1828. registry_key_data,
  1829. m_pEmptyRegItem,
  1830. GCC_NO_MODIFICATION_RIGHTS_SPECIFIED,
  1831. 0,
  1832. 0,
  1833. GCC_RESULT_ENTRY_DOES_NOT_EXIST);
  1834. }
  1835. }
  1836. /*
  1837. * void ProcessRegistryResponsePDU ()
  1838. *
  1839. * Public Function Description
  1840. * This routine is used by nodes other than the top provider node to
  1841. * process registry responses from the top provider. It is responsible for
  1842. * generating any local messages associated with this response.
  1843. */
  1844. void CRegistry::ProcessRegistryResponsePDU (
  1845. RegistryResponsePrimitiveType primitive_type,
  1846. CRegKeyContainer *registry_key_data,
  1847. CRegItem *registry_item_data,
  1848. GCCModificationRights modification_rights,
  1849. EntityID requester_entity_id,
  1850. UserID owner_node_id,
  1851. EntityID owner_entity_id,
  1852. GCCResult result)
  1853. {
  1854. GCCError error_value = GCC_NO_ERROR;
  1855. GCCMessageType message_type;
  1856. CAppSap *pAppSap;
  1857. // Pop the next outstanding request off the queue
  1858. if (NULL != (pAppSap = m_AppSapEidList2.Find(requester_entity_id)))
  1859. {
  1860. switch (primitive_type)
  1861. {
  1862. case REGISTER_CHANNEL:
  1863. message_type = GCC_REGISTER_CHANNEL_CONFIRM;
  1864. break;
  1865. case ASSIGN_TOKEN:
  1866. message_type = GCC_ASSIGN_TOKEN_CONFIRM;
  1867. break;
  1868. case SET_PARAMETER:
  1869. message_type = GCC_SET_PARAMETER_CONFIRM;
  1870. break;
  1871. case RETRIEVE_ENTRY:
  1872. message_type = GCC_RETRIEVE_ENTRY_CONFIRM;
  1873. break;
  1874. case DELETE_ENTRY:
  1875. message_type = GCC_DELETE_ENTRY_CONFIRM;
  1876. break;
  1877. case MONITOR_ENTRY:
  1878. message_type = GCC_MONITOR_CONFIRM;
  1879. /*
  1880. ** Here we must check the result. If the result failed
  1881. ** we pull the monitoring SAP from the monitor list.
  1882. */
  1883. if (result != GCC_RESULT_SUCCESSFUL)
  1884. {
  1885. RemoveAPEFromMonitoringList ( registry_key_data,
  1886. requester_entity_id);
  1887. }
  1888. break;
  1889. default:
  1890. error_value = GCC_INVALID_PARAMETER;
  1891. ERROR_OUT(("CRegistry::ProcessRegistryResponsePDU: Bad request type, primitive_type=%d", (UINT) primitive_type));
  1892. break;
  1893. }
  1894. if (error_value == GCC_NO_ERROR)
  1895. {
  1896. /*
  1897. ** Note the the monitor enable variable is always set to TRUE
  1898. ** when a monitor response is received from the Top Provider.
  1899. ** Otherwise, this is not even used.
  1900. */
  1901. pAppSap->RegistryConfirm(m_nConfID,
  1902. message_type,
  1903. registry_key_data,
  1904. registry_item_data,
  1905. modification_rights,
  1906. owner_node_id,
  1907. owner_entity_id,
  1908. TRUE,
  1909. result);
  1910. }
  1911. }
  1912. else
  1913. {
  1914. WARNING_OUT(("CRegistry::ProcessRegistryResponsePDU: no such app sap"));
  1915. }
  1916. }
  1917. /*
  1918. * void ProcessMonitorIndicationPDU ()
  1919. *
  1920. * Public Function Description
  1921. * This routine is used by nodes other than the top provider node to
  1922. * process registry monitor indications from the top provider. It is
  1923. * responsible for generating any local messages associated with this
  1924. * response.
  1925. */
  1926. void CRegistry::ProcessMonitorIndicationPDU (
  1927. CRegKeyContainer *registry_key_data,
  1928. CRegItem *registry_item_data,
  1929. GCCModificationRights modification_rights,
  1930. UserID owner_node_id,
  1931. EntityID owner_entity_id)
  1932. {
  1933. REG_ENTRY *lpRegEntry;
  1934. EntityID eid;
  1935. CAppSap *pAppSap;
  1936. m_RegEntryList.Reset();
  1937. while (NULL != (lpRegEntry = m_RegEntryList.Iterate()))
  1938. {
  1939. if (*registry_key_data == *lpRegEntry->registry_key)
  1940. {
  1941. lpRegEntry->monitoring_list.Reset();
  1942. while (GCC_INVALID_EID != (eid = lpRegEntry->monitoring_list.Iterate()))
  1943. {
  1944. if (NULL != (pAppSap = m_AppSapEidList2.Find(eid)))
  1945. {
  1946. pAppSap->RegistryMonitorIndication(m_nConfID,
  1947. registry_key_data,
  1948. registry_item_data,
  1949. modification_rights,
  1950. owner_node_id,
  1951. owner_entity_id);
  1952. }
  1953. }
  1954. }
  1955. }
  1956. }
  1957. /*
  1958. * void ProcessAllocateHandleRequestPDU ()
  1959. *
  1960. * Public Function Description
  1961. * This routine is used by the top provider node to process an incomming
  1962. * request to allocate a number of handles. It is responsible for
  1963. * returning any necessary responses that must be sent back to the
  1964. * requesting node.
  1965. */
  1966. void CRegistry::ProcessAllocateHandleRequestPDU (
  1967. UINT number_of_handles,
  1968. EntityID requester_entity_id,
  1969. UserID requester_node_id)
  1970. {
  1971. UINT temp_registry_handle;
  1972. if (m_fTopProvider)
  1973. {
  1974. if ((number_of_handles > 0) &&
  1975. (number_of_handles <= MAXIMUM_ALLOWABLE_ALLOCATED_HANDLES))
  1976. {
  1977. temp_registry_handle = m_nRegHandle + number_of_handles;
  1978. if (temp_registry_handle > m_nRegHandle)
  1979. {
  1980. m_pMCSUserObject->RegistryAllocateHandleResponse(
  1981. number_of_handles,
  1982. m_nRegHandle,
  1983. requester_entity_id,
  1984. requester_node_id,
  1985. GCC_RESULT_SUCCESSFUL);
  1986. m_nRegHandle = temp_registry_handle;
  1987. }
  1988. else
  1989. {
  1990. m_pMCSUserObject->RegistryAllocateHandleResponse(
  1991. number_of_handles,
  1992. 0,
  1993. requester_entity_id,
  1994. requester_node_id,
  1995. GCC_RESULT_NO_HANDLES_AVAILABLE);
  1996. }
  1997. }
  1998. else
  1999. {
  2000. m_pMCSUserObject->RegistryAllocateHandleResponse(
  2001. number_of_handles,
  2002. 0,
  2003. requester_entity_id,
  2004. requester_node_id,
  2005. GCC_RESULT_INVALID_NUMBER_OF_HANDLES);
  2006. }
  2007. }
  2008. }
  2009. /*
  2010. * void ProcessAllocateHandleResponsePDU ()
  2011. *
  2012. * Public Function Description
  2013. * This routine is used by a node other than the top provider node to
  2014. * process an allocate handle response. It is responsible for generating
  2015. * any local messages associated with this response.
  2016. */
  2017. void CRegistry::ProcessAllocateHandleResponsePDU (
  2018. UINT number_of_handles,
  2019. UINT first_handle,
  2020. EntityID eidRequester,
  2021. GCCResult result)
  2022. {
  2023. CAppSap *pAppSap;
  2024. if (NULL != (pAppSap = m_AppSapEidList2.Find(eidRequester)))
  2025. {
  2026. pAppSap->RegistryAllocateHandleConfirm(m_nConfID,
  2027. number_of_handles,
  2028. first_handle,
  2029. result);
  2030. }
  2031. }
  2032. /*
  2033. * void RemoveNodeOwnership ()
  2034. *
  2035. * Public Function Description
  2036. * This routine removes ownership of all the registry entries associated
  2037. * with the specified node ID. These entries become unowned. This request
  2038. * should only be made from the top provider node. This is a local
  2039. * operation.
  2040. */
  2041. void CRegistry::RemoveNodeOwnership (
  2042. UserID node_id )
  2043. {
  2044. if (m_fTopProvider)
  2045. {
  2046. REG_ENTRY *lpRegEntry;
  2047. m_RegEntryList.Reset();
  2048. while (NULL != (lpRegEntry = m_RegEntryList.Iterate()))
  2049. {
  2050. if (lpRegEntry->owner_id == node_id)
  2051. {
  2052. lpRegEntry->owner_id = 0;
  2053. lpRegEntry->entity_id = 0;
  2054. // Send Monitor Indication if necessary
  2055. if (lpRegEntry->monitoring_state == ON)
  2056. {
  2057. /*
  2058. ** Deliver the monitor indication to the Top
  2059. ** Provider's Node Controller if necessary.
  2060. */
  2061. SendMonitorEntryIndicationMessage (lpRegEntry);
  2062. m_pMCSUserObject->RegistryMonitorEntryIndication(
  2063. lpRegEntry->registry_key,
  2064. lpRegEntry->entry_item,
  2065. lpRegEntry->owner_id,
  2066. lpRegEntry->entity_id,
  2067. lpRegEntry->modification_rights);
  2068. }
  2069. }
  2070. }
  2071. }
  2072. }
  2073. /*
  2074. * void RemoveEntityOwnership ()
  2075. *
  2076. * Public Function Description
  2077. * This routine removes ownership of all the registry entries associated
  2078. * with the specified APE. These entries become unowned. This request
  2079. * should only be made from the top provider node. This is a local
  2080. * operation.
  2081. */
  2082. void CRegistry::RemoveEntityOwnership (
  2083. UserID node_id,
  2084. EntityID entity_id )
  2085. {
  2086. if (m_fTopProvider)
  2087. {
  2088. REG_ENTRY *lpRegEntry;
  2089. m_RegEntryList.Reset();
  2090. while (NULL != (lpRegEntry = m_RegEntryList.Iterate()))
  2091. {
  2092. if ((lpRegEntry->owner_id == node_id) &&
  2093. (lpRegEntry->entity_id == entity_id))
  2094. {
  2095. lpRegEntry->owner_id = 0;
  2096. lpRegEntry->entity_id = 0;
  2097. // Send Monitor Indication if necessary
  2098. if (lpRegEntry->monitoring_state == ON)
  2099. {
  2100. /*
  2101. ** Deliver the monitor indication to the Top
  2102. ** Provider's Node Controller if necessary.
  2103. */
  2104. SendMonitorEntryIndicationMessage(lpRegEntry);
  2105. m_pMCSUserObject->RegistryMonitorEntryIndication(
  2106. lpRegEntry->registry_key,
  2107. lpRegEntry->entry_item,
  2108. lpRegEntry->owner_id,
  2109. lpRegEntry->entity_id,
  2110. lpRegEntry->modification_rights);
  2111. }
  2112. }
  2113. }
  2114. }
  2115. }
  2116. /*
  2117. * void RemoveSessionKeyReference ()
  2118. *
  2119. * Public Function Description
  2120. * This routine removes all registry entries associated with the
  2121. * specified session. This is a local operation.
  2122. */
  2123. void CRegistry::RemoveSessionKeyReference(CSessKeyContainer *session_key)
  2124. {
  2125. BOOL keys_match;
  2126. CRegKeyContainer *registry_key_data;
  2127. if (m_fTopProvider)
  2128. {
  2129. /*
  2130. ** This outer loop is to handle resetting the rogue wave iterator.
  2131. ** You can not delete a list entry while in the iterator with out
  2132. ** resetting it.
  2133. */
  2134. while (1)
  2135. {
  2136. REG_ENTRY *lpRegEntry;
  2137. keys_match = FALSE;
  2138. m_RegEntryList.Reset();
  2139. while (NULL != (lpRegEntry= m_RegEntryList.Iterate()))
  2140. {
  2141. registry_key_data = lpRegEntry->registry_key;
  2142. if (registry_key_data->IsThisYourSessionKey (session_key))
  2143. keys_match = TRUE;
  2144. if (keys_match)
  2145. {
  2146. /*
  2147. ** First convert this to a non-entry incase it needs to
  2148. ** be included in a monitor indication. We first delete
  2149. ** the old entry item and replace it with an Emtpy item.
  2150. */
  2151. if (NULL != lpRegEntry->entry_item)
  2152. {
  2153. lpRegEntry->entry_item->Release();
  2154. }
  2155. lpRegEntry->entry_item = m_pEmptyRegItem;
  2156. lpRegEntry->owner_id = 0;
  2157. lpRegEntry->entity_id = 0;
  2158. lpRegEntry->modification_rights = GCC_NO_MODIFICATION_RIGHTS_SPECIFIED;
  2159. // Send Monitor Indication if necessary
  2160. if (lpRegEntry->monitoring_state == ON)
  2161. {
  2162. /*
  2163. ** Deliver the monitor indication to the Top
  2164. ** Provider's Node Controller if necessary.
  2165. */
  2166. SendMonitorEntryIndicationMessage(lpRegEntry);
  2167. /*
  2168. ** Broadcast a monitor entry indication to all
  2169. ** nodes in the conference.
  2170. */
  2171. m_pMCSUserObject->RegistryMonitorEntryIndication(
  2172. lpRegEntry->registry_key,
  2173. lpRegEntry->entry_item,
  2174. lpRegEntry->owner_id,
  2175. lpRegEntry->entity_id,
  2176. lpRegEntry->modification_rights);
  2177. }
  2178. if (NULL != lpRegEntry->registry_key)
  2179. {
  2180. lpRegEntry->registry_key->Release();
  2181. }
  2182. m_RegEntryList.Remove(lpRegEntry);
  2183. delete lpRegEntry;
  2184. break;
  2185. }
  2186. }
  2187. if (keys_match == FALSE)
  2188. break;
  2189. }
  2190. }
  2191. }
  2192. /*
  2193. * REG_ENTRY *GetRegistryEntry ()
  2194. *
  2195. * Private Function Description
  2196. * This routine is responsible for searching the registry list for
  2197. * the registry entry specified by the passed in registry key. NULL
  2198. * is returned if the entry can not be found.
  2199. *
  2200. * Formal Parameters:
  2201. * registry_key_data - (i) Registry key associated with entry to get.
  2202. *
  2203. * Return Value
  2204. * Pointer to the registry item assoicated with the specified registry
  2205. * key. NULL if it does not exists.
  2206. *
  2207. * Side Effects
  2208. * None.
  2209. *
  2210. * Caveats
  2211. * None.
  2212. */
  2213. REG_ENTRY *CRegistry::GetRegistryEntry(CRegKeyContainer *registry_key_data)
  2214. {
  2215. REG_ENTRY *registry_entry = NULL;
  2216. REG_ENTRY *lpRegEntry;
  2217. m_RegEntryList.Reset();
  2218. while (NULL != (lpRegEntry = m_RegEntryList.Iterate()))
  2219. {
  2220. if (*lpRegEntry->registry_key == *registry_key_data)
  2221. {
  2222. registry_entry = lpRegEntry;
  2223. break;
  2224. }
  2225. }
  2226. return (registry_entry);
  2227. }
  2228. /*
  2229. * TokenID GetUnusedToken ()
  2230. *
  2231. * Private Function Description
  2232. * This routine is responsible for generating an unused token. The routine
  2233. * will return a token ID of zero if all are used up (this is very
  2234. * unlikely).
  2235. *
  2236. * Formal Parameters:
  2237. * None.
  2238. *
  2239. * Return Value
  2240. * The generated token ID. Zero if no token IDs are available.
  2241. *
  2242. * Side Effects
  2243. * None.
  2244. *
  2245. * Caveats
  2246. * None.
  2247. */
  2248. TokenID CRegistry::GetUnusedToken ()
  2249. {
  2250. TokenID token_id = 0;
  2251. CRegItem *registry_item_data;
  2252. REG_ENTRY *lpRegEntry;
  2253. while (token_id == 0)
  2254. {
  2255. token_id = m_nCurrentTokenID;
  2256. m_nCurrentTokenID++;
  2257. if (m_nCurrentTokenID == (TokenID)0xffff)
  2258. {
  2259. m_nCurrentTokenID = (TokenID)16384;
  2260. }
  2261. m_RegEntryList.Reset();
  2262. while (NULL != (lpRegEntry = m_RegEntryList.Iterate()))
  2263. {
  2264. registry_item_data = lpRegEntry->entry_item;
  2265. if (registry_item_data->IsThisYourTokenID(token_id))
  2266. {
  2267. token_id = 0;
  2268. break;
  2269. }
  2270. }
  2271. }
  2272. return (token_id);
  2273. }
  2274. /*
  2275. * GCCError AddAPEToMonitoringList ()
  2276. *
  2277. * Private Function Description
  2278. * This routine is used to add a new APE to the monitoring list.
  2279. *
  2280. * Formal Parameters:
  2281. * registry_key_data - (i) Registry key associated with entry being
  2282. * monitored.
  2283. * entity_id - (i) Entity ID associated with the APE that is
  2284. * doing the monitoring.
  2285. * requester_sap - (i) Pointer to the command target associated
  2286. * with APE making the request.
  2287. *
  2288. * Return Value
  2289. * GCC_NO_ERROR - No error occured.
  2290. * GCC_ALLOCATION_FAILURE - A resource error occured.
  2291. *
  2292. * Side Effects
  2293. * None.
  2294. *
  2295. * Caveats
  2296. * None.
  2297. */
  2298. GCCError CRegistry::AddAPEToMonitoringList(
  2299. CRegKeyContainer *registry_key_data,
  2300. EntityID entity_id,
  2301. CAppSap *requester_sap)
  2302. {
  2303. GCCError rc = GCC_NO_ERROR;
  2304. REG_ENTRY *registry_entry;
  2305. BOOL entry_does_exists;
  2306. GCCRegistryItem registry_item;
  2307. registry_entry = GetRegistryEntry (registry_key_data);
  2308. /*
  2309. ** If the registry does not exists we go ahead and create an empty
  2310. ** entry here.
  2311. */
  2312. if (registry_entry == NULL)
  2313. {
  2314. DBG_SAVE_FILE_LINE
  2315. registry_entry = new REG_ENTRY;
  2316. if (registry_entry != NULL)
  2317. {
  2318. // First allocate an empty registry item
  2319. registry_item.item_type = GCC_REGISTRY_NONE;
  2320. DBG_SAVE_FILE_LINE
  2321. registry_entry->entry_item = new CRegItem(&registry_item, &rc);
  2322. if ((registry_entry->entry_item != NULL) && (rc == GCC_NO_ERROR))
  2323. {
  2324. // Next allocate the registry key
  2325. DBG_SAVE_FILE_LINE
  2326. registry_entry->registry_key = new CRegKeyContainer(registry_key_data, &rc);
  2327. if ((registry_entry->registry_key != NULL) && (rc == GCC_NO_ERROR))
  2328. {
  2329. /*
  2330. ** If everything is OK up to here we go ahead and add the
  2331. ** registry entry to the local entry list.
  2332. */
  2333. m_RegEntryList.Append(registry_entry);
  2334. }
  2335. else if (registry_entry->registry_key == NULL)
  2336. {
  2337. rc = GCC_ALLOCATION_FAILURE;
  2338. registry_entry->entry_item->Release();
  2339. }
  2340. else
  2341. {
  2342. registry_entry->registry_key->Release();
  2343. registry_entry->entry_item->Release();
  2344. }
  2345. }
  2346. else if (registry_entry->entry_item == NULL)
  2347. {
  2348. rc = GCC_ALLOCATION_FAILURE;
  2349. }
  2350. else
  2351. {
  2352. registry_entry->entry_item->Release();
  2353. }
  2354. if (rc != GCC_NO_ERROR)
  2355. {
  2356. delete registry_entry;
  2357. }
  2358. }
  2359. else
  2360. {
  2361. rc = GCC_ALLOCATION_FAILURE;
  2362. }
  2363. }
  2364. if (rc == GCC_NO_ERROR)
  2365. {
  2366. m_AppSapEidList2.Append(entity_id, requester_sap);
  2367. /*
  2368. ** Make sure that this entry does not already exists in the
  2369. ** monitoring list.
  2370. */
  2371. EntityID eid;
  2372. registry_entry->monitoring_list.Reset();
  2373. entry_does_exists = FALSE;
  2374. while (GCC_INVALID_EID != (eid = registry_entry->monitoring_list.Iterate()))
  2375. {
  2376. if (eid == entity_id)
  2377. {
  2378. entry_does_exists = TRUE;
  2379. break;
  2380. }
  2381. }
  2382. if (entry_does_exists == FALSE)
  2383. {
  2384. registry_entry->monitoring_list.Append(entity_id);
  2385. }
  2386. }
  2387. return rc;
  2388. }
  2389. /*
  2390. * void RemoveAPEFromMonitoringList ()
  2391. *
  2392. * Private Function Description
  2393. * This routine is used to remove an APE from the monitoring list.
  2394. *
  2395. * Formal Parameters:
  2396. * registry_key_data - (i) Registry key associated with entry being
  2397. * monitored.
  2398. * entity_id - (i) Entity ID associated with the APE that is
  2399. * being removed from the monitoring list.
  2400. *
  2401. * Return Value
  2402. * None.
  2403. *
  2404. * Side Effects
  2405. * None.
  2406. *
  2407. * Caveats
  2408. * None.
  2409. */
  2410. void CRegistry::RemoveAPEFromMonitoringList(
  2411. CRegKeyContainer *registry_key_data,
  2412. EntityID entity_id)
  2413. {
  2414. REG_ENTRY *registry_entry;
  2415. registry_entry = GetRegistryEntry (registry_key_data);
  2416. if (registry_entry != NULL)
  2417. {
  2418. /*
  2419. ** Make sure that this entry does not already exists in the
  2420. ** monitoring list.
  2421. */
  2422. registry_entry->monitoring_list.Remove(entity_id);
  2423. }
  2424. }
  2425. /*
  2426. * void SendMonitorEntryIndicationMessage ()
  2427. *
  2428. * Private Function Description
  2429. * This routine is used to generate a monitor indication to all the
  2430. * APEs that are currently monitoring the specified registry entry.
  2431. *
  2432. * Formal Parameters:
  2433. * registry_entry - (i) Pointer to the registry entry being monitored.
  2434. *
  2435. * Return Value
  2436. * None.
  2437. *
  2438. * Side Effects
  2439. * None.
  2440. *
  2441. * Caveats
  2442. * None.
  2443. */
  2444. void CRegistry::SendMonitorEntryIndicationMessage(REG_ENTRY *registry_entry)
  2445. {
  2446. EntityID eid;
  2447. CAppSap *pAppSap;
  2448. registry_entry->monitoring_list.Reset();
  2449. while (GCC_INVALID_EID != (eid = registry_entry->monitoring_list.Iterate()))
  2450. {
  2451. if (NULL != (pAppSap = m_AppSapEidList2.Find(eid)))
  2452. {
  2453. pAppSap->RegistryMonitorIndication(
  2454. m_nConfID,
  2455. registry_entry->registry_key,
  2456. registry_entry->entry_item,
  2457. registry_entry->modification_rights,
  2458. registry_entry->owner_id,
  2459. registry_entry->entity_id);
  2460. }
  2461. }
  2462. }