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

1625 lines
45 KiB

  1. #include "precomp.h"
  2. DEBUG_FILEZONE(ZONE_T120_SAP);
  3. #include "appsap.h"
  4. #include "conf.h"
  5. #include "gcontrol.h"
  6. void CALLBACK MCS_SapCallback(UINT, LPARAM, LPVOID);
  7. void CALLBACK GCC_SapCallback(GCCAppSapMsg *);
  8. T120Error WINAPI T120_CreateAppletSAP
  9. (
  10. IT120Applet **ppApplet
  11. )
  12. {
  13. if (NULL != ppApplet)
  14. {
  15. *ppApplet = NULL;
  16. if (NULL != g_pGCCController)
  17. {
  18. T120Error rc;
  19. DBG_SAVE_FILE_LINE
  20. CApplet *pApplet = new CApplet(&rc);
  21. if (NULL != pApplet)
  22. {
  23. if (T120_NO_ERROR == rc)
  24. {
  25. *ppApplet = (IT120Applet *) pApplet;
  26. return T120_NO_ERROR;
  27. }
  28. ERROR_OUT(("T120_CreateAppletSAP: CApplet failed, rc=%u", rc));
  29. pApplet->Release();
  30. return rc;
  31. }
  32. ERROR_OUT(("T120_CreateAppletSAP: cannot create CApplet"));
  33. return T120_ALLOCATION_FAILURE;
  34. }
  35. WARNING_OUT(("T120_CreateAppletSAP: GCC Provider is not initialized."));
  36. return T120_NOT_INITIALIZED;
  37. }
  38. ERROR_OUT(("T120_CreateAppletSAP: callback pfn null"));
  39. return T120_INVALID_PARAMETER;
  40. }
  41. /* ------ interface methods for applet session ------ */
  42. CAppletSession::CAppletSession
  43. (
  44. CApplet *pApplet,
  45. T120ConfID nConfID
  46. )
  47. :
  48. CRefCount(MAKE_STAMP_ID('A','p','p','S')),
  49. m_pApplet(pApplet),
  50. m_pAppletContext(NULL),
  51. m_pSessionContext(NULL),
  52. m_pfnCallback(NULL),
  53. m_pMCSAppletSAP(NULL),
  54. m_nConfID(nConfID),
  55. m_uidMyself(0),
  56. m_sidMyself(0),
  57. m_eidMyself(0),
  58. m_nidMyself(0),
  59. m_eState(APPSESS_INITIALIZED),
  60. m_nArrayIndex(0),
  61. m_eErrorType(NONE_CHOSEN),
  62. m_eDynamicChannelJoinState(DCJS_INITIALIZED),
  63. m_fMCSFreeDataIndBuffer(0),
  64. m_fFirstRoster(FALSE),
  65. m_pTempMsg(NULL)
  66. {
  67. ASSERT(0 != m_nConfID);
  68. ::ZeroMemory(&m_JoinRequest, sizeof(m_JoinRequest));
  69. m_pApplet->RegisterSession(this);
  70. }
  71. CAppletSession::~CAppletSession(void)
  72. {
  73. m_pApplet->UnregisterSession(this);
  74. FreeJoinRequest(FALSE);
  75. ASSERT(NULL == m_pfnCallback);
  76. ASSERT(NULL == m_pAppletContext);
  77. ASSERT(NULL == m_pSessionContext);
  78. }
  79. void CAppletSession::FreeJoinRequest(BOOL fZeroOut)
  80. {
  81. delete [] m_JoinRequest.aResourceReqs;
  82. if (fZeroOut)
  83. {
  84. ::ZeroMemory(&m_JoinRequest, sizeof(m_JoinRequest));
  85. }
  86. }
  87. void CAppletSession::ReleaseInterface(void)
  88. {
  89. ASSERT(NULL != g_pGCCController);
  90. Leave();
  91. m_pfnCallback = NULL;
  92. m_pAppletContext = NULL;
  93. m_pSessionContext = NULL;
  94. Release();
  95. }
  96. void CAppletSession::Advise
  97. (
  98. LPFN_APPLET_SESSION_CB pfnCallback,
  99. LPVOID pAppletContext,
  100. LPVOID pSessionContext
  101. )
  102. {
  103. m_pfnCallback = pfnCallback;
  104. m_pAppletContext = pAppletContext;
  105. m_pSessionContext = pSessionContext;
  106. }
  107. void CAppletSession::Unadvise(void)
  108. {
  109. m_pfnCallback = NULL;
  110. m_pAppletContext = NULL;
  111. m_pSessionContext = NULL;
  112. }
  113. BOOL CAppletSession::IsThisNodeTopProvider(void)
  114. {
  115. return m_pApplet->GetAppSap()->IsThisNodeTopProvider(m_nConfID);
  116. }
  117. T120NodeID CAppletSession::GetTopProvider(void)
  118. {
  119. return m_pApplet->GetAppSap()->GetTopProvider(m_nConfID);
  120. }
  121. T120Error CAppletSession::Join
  122. (
  123. T120JoinSessionRequest *pReq
  124. )
  125. {
  126. ASSERT(0 != m_nConfID);
  127. if (NULL != g_pGCCController->GetConfObject(m_nConfID))
  128. {
  129. T120Error rc = T120_NO_ERROR;
  130. // remember the join request, shallow structure copy
  131. m_JoinRequest = *pReq;
  132. // we need to duplicate the resource requests because we put the results in place.
  133. // we have to do this in order to support multiple conferences simultaneously
  134. if (NULL != pReq->aResourceReqs && 0 != pReq->cResourceReqs)
  135. {
  136. DBG_SAVE_FILE_LINE
  137. m_JoinRequest.aResourceReqs = new T120ResourceRequest[m_JoinRequest.cResourceReqs];
  138. if (NULL != m_JoinRequest.aResourceReqs)
  139. {
  140. ::CopyMemory(m_JoinRequest.aResourceReqs, pReq->aResourceReqs,
  141. sizeof(T120ResourceRequest) * m_JoinRequest.cResourceReqs);
  142. }
  143. else
  144. {
  145. ERROR_OUT(("CAppletSession::Join: can't create resource requests"));
  146. rc = T120_ALLOCATION_FAILURE;
  147. }
  148. }
  149. // attach user now
  150. if (T120_NO_ERROR == rc)
  151. {
  152. m_fFirstRoster = FALSE;
  153. m_fMCSFreeDataIndBuffer = (pReq->dwAttachmentFlags & ATTACHMENT_MCS_FREES_DATA_IND_BUFFER);
  154. SetState(APPSESS_ATTACH_USER_REQ);
  155. rc = ::MCS_AttachRequest(&m_pMCSAppletSAP,
  156. (LPBYTE) &m_nConfID, sizeof(m_nConfID),
  157. MCS_SapCallback,
  158. this,
  159. pReq->dwAttachmentFlags);
  160. ASSERT(T120_NO_ERROR == rc);
  161. }
  162. if (T120_NO_ERROR == rc)
  163. {
  164. return T120_NO_ERROR;
  165. }
  166. FreeJoinRequest(TRUE);
  167. return rc;
  168. }
  169. return GCC_INVALID_CONFERENCE;
  170. }
  171. void CAppletSession::Leave(void)
  172. {
  173. if (APPSESS_LEAVING != m_eState && APPSESS_LEFT != m_eState)
  174. {
  175. APPLET_SESSION_STATE eOldState = m_eState;
  176. m_eState = APPSESS_LEAVING;
  177. switch (eOldState)
  178. {
  179. case APPSESS_INACTIVELY_ENROLL_REQ:
  180. case APPSESS_INACTIVELY_ENROLL_CON:
  181. case APPSESS_RESOURCE_REQ:
  182. case APPSESS_RESOURCE_CON:
  183. case APPSESS_ACTIVELY_ENROLL_REQ:
  184. case APPSESS_ACTIVELY_ENROLL_CON:
  185. case APPSESS_JOINED:
  186. default:
  187. // un-enroll
  188. DoEnroll(FALSE);
  189. // fall through
  190. case APPSESS_ATTACH_USER_REQ:
  191. case APPSESS_ATTACH_USER_CON:
  192. case APPSESS_JOIN_MY_CHANNEL_REQ:
  193. case APPSESS_JOIN_MY_CHANNEL_CON:
  194. case APPSESS_JOIN_STATIC_CHANNEL_REQ:
  195. case APPSESS_JOIN_STATIC_CHANNEL_CON:
  196. if (NULL != m_pMCSAppletSAP)
  197. {
  198. m_pMCSAppletSAP->ReleaseInterface();
  199. m_pMCSAppletSAP = NULL;
  200. }
  201. // fall through
  202. case APPSESS_INITIALIZED:
  203. m_fMCSFreeDataIndBuffer = 0;
  204. break;
  205. }
  206. m_eState = APPSESS_LEFT;
  207. m_fFirstRoster = FALSE;
  208. }
  209. FreeJoinRequest(TRUE);
  210. }
  211. T120Error CAppletSession::AllocateSendDataBuffer
  212. (
  213. ULONG cbBufSize,
  214. void **ppBuf
  215. )
  216. {
  217. if (NULL != m_pMCSAppletSAP)
  218. {
  219. return m_pMCSAppletSAP->GetBuffer(cbBufSize, ppBuf);
  220. }
  221. return T120_NOT_INITIALIZED;
  222. }
  223. void CAppletSession::FreeSendDataBuffer
  224. (
  225. void *pBuf
  226. )
  227. {
  228. if (NULL != m_pMCSAppletSAP && (! m_fMCSFreeDataIndBuffer))
  229. {
  230. m_pMCSAppletSAP->FreeBuffer(pBuf);
  231. }
  232. else
  233. {
  234. ASSERT(0);
  235. }
  236. }
  237. T120Error CAppletSession::SendData
  238. (
  239. DataRequestType eReqType,
  240. T120ChannelID nChannelID,
  241. T120Priority ePriority,
  242. LPBYTE pbBuf,
  243. ULONG cbBufSize,
  244. SendDataFlags eBufSource
  245. )
  246. {
  247. if (NULL != m_pMCSAppletSAP)
  248. {
  249. return m_pMCSAppletSAP->SendData(eReqType,
  250. nChannelID,
  251. (Priority) ePriority,
  252. pbBuf,
  253. cbBufSize,
  254. eBufSource);
  255. }
  256. return T120_NOT_INITIALIZED;
  257. }
  258. T120Error CAppletSession::InvokeApplet
  259. (
  260. GCCAppProtEntityList *pApeList,
  261. GCCSimpleNodeList *pNodeList,
  262. T120RequestTag *pnReqTag
  263. )
  264. {
  265. return m_pApplet->GetAppSap()->AppInvoke(m_nConfID, pApeList, pNodeList, pnReqTag);
  266. }
  267. T120Error CAppletSession::InquireRoster
  268. (
  269. GCCSessionKey *pSessionKey
  270. )
  271. {
  272. return m_pApplet->GetAppSap()->AppRosterInquire(m_nConfID, pSessionKey, NULL);
  273. }
  274. T120Error CAppletSession::RegistryRequest
  275. (
  276. T120RegistryRequest *pReq
  277. )
  278. {
  279. T120Error rc;
  280. if (NULL != pReq)
  281. {
  282. IGCCAppSap *pAppSap = m_pApplet->GetAppSap();
  283. ASSERT(NULL != pAppSap);
  284. GCCRegistryKey *pKey = pReq->pRegistryKey;
  285. switch (pReq->eCommand)
  286. {
  287. case APPLET_REGISTER_CHANNEL:
  288. rc = pAppSap->RegisterChannel(m_nConfID, pKey, pReq->nChannelID);
  289. break;
  290. case APPLET_ASSIGN_TOKEN:
  291. rc = pAppSap->RegistryAssignToken(m_nConfID, pKey);
  292. break;
  293. case APPLET_SET_PARAMETER:
  294. rc = pAppSap->RegistrySetParameter(m_nConfID, pKey,
  295. pReq->Param.postrValue, pReq->Param.eModifyRights);
  296. break;
  297. case APPLET_RETRIEVE_ENTRY:
  298. rc = pAppSap->RegistryRetrieveEntry(m_nConfID, pKey);
  299. break;
  300. case APPLET_DELETE_ENTRY:
  301. rc = pAppSap->RegistryDeleteEntry(m_nConfID, pKey);
  302. break;
  303. case APPLET_ALLOCATE_HANDLE:
  304. rc = pAppSap->RegistryAllocateHandle(m_nConfID, pReq->cHandles);
  305. break;
  306. case APPLET_MONITOR:
  307. rc = pAppSap->RegistryMonitor(m_nConfID, pReq->fEnableDelivery, pKey);
  308. break;
  309. default:
  310. ERROR_OUT(("CAppletSession::RegistryRequest: invalid command=%u", (UINT) pReq->eCommand));
  311. rc = T120_INVALID_PARAMETER;
  312. break;
  313. }
  314. }
  315. else
  316. {
  317. rc = T120_INVALID_PARAMETER;
  318. }
  319. return rc;
  320. }
  321. T120Error CAppletSession::ChannelRequest
  322. (
  323. T120ChannelRequest *pReq
  324. )
  325. {
  326. T120Error rc;
  327. if (NULL != pReq)
  328. {
  329. T120ChannelID chid = pReq->nChannelID;
  330. switch (pReq->eCommand)
  331. {
  332. case APPLET_JOIN_CHANNEL:
  333. rc = m_pMCSAppletSAP->ChannelJoin(chid);
  334. break;
  335. case APPLET_LEAVE_CHANNEL:
  336. rc = m_pMCSAppletSAP->ChannelLeave(chid);
  337. break;
  338. case APPLET_CONVENE_CHANNEL:
  339. rc = m_pMCSAppletSAP->ChannelConvene();
  340. break;
  341. case APPLET_DISBAND_CHANNEL:
  342. rc = m_pMCSAppletSAP->ChannelDisband(chid);
  343. break;
  344. case APPLET_ADMIT_CHANNEL:
  345. rc = m_pMCSAppletSAP->ChannelAdmit(chid, pReq->aUsers, pReq->cUsers);
  346. break;
  347. default:
  348. ERROR_OUT(("CAppletSession::ChannelRequest: invalid command=%u", (UINT) pReq->eCommand));
  349. rc = T120_INVALID_PARAMETER;
  350. break;
  351. }
  352. }
  353. else
  354. {
  355. rc = T120_INVALID_PARAMETER;
  356. }
  357. return rc;
  358. }
  359. T120Error CAppletSession::TokenRequest
  360. (
  361. T120TokenRequest *pReq
  362. )
  363. {
  364. //T120TokenID nTokenID;
  365. //T120UserID uidGiveTo;
  366. T120Error rc;
  367. if (NULL != pReq)
  368. {
  369. T120TokenID tid = pReq->nTokenID;
  370. switch (pReq->eCommand)
  371. {
  372. case APPLET_GRAB_TOKEN:
  373. rc = m_pMCSAppletSAP->TokenGrab(tid);
  374. break;
  375. case APPLET_INHIBIT_TOKEN:
  376. rc = m_pMCSAppletSAP->TokenInhibit(tid);
  377. break;
  378. case APPLET_GIVE_TOKEN:
  379. rc = m_pMCSAppletSAP->TokenGive(tid, pReq->uidGiveTo);
  380. break;
  381. case APPLET_GIVE_TOKEN_RESPONSE:
  382. rc = m_pMCSAppletSAP->TokenGiveResponse(tid, pReq->eGiveResponse);
  383. break;
  384. case APPLET_PLEASE_TOKEN:
  385. rc = m_pMCSAppletSAP->TokenPlease(tid);
  386. break;
  387. case APPLET_RELEASE_TOKEN:
  388. rc = m_pMCSAppletSAP->TokenRelease(tid);
  389. break;
  390. case APPLET_TEST_TOKEN:
  391. rc = m_pMCSAppletSAP->TokenTest(tid);
  392. break;
  393. default:
  394. ERROR_OUT(("CAppletSession::TokenRequest: invalid command=%u", (UINT) pReq->eCommand));
  395. rc = T120_INVALID_PARAMETER;
  396. break;
  397. }
  398. }
  399. else
  400. {
  401. rc = T120_INVALID_PARAMETER;
  402. }
  403. return rc;
  404. }
  405. /* ------ private methods ------ */
  406. void CAppletSession::SendCallbackMessage
  407. (
  408. T120AppletSessionMsg *pMsg
  409. )
  410. {
  411. ASSERT(NULL != pMsg);
  412. if (NULL != m_pfnCallback)
  413. {
  414. pMsg->pAppletContext = m_pAppletContext;
  415. pMsg->pSessionContext = m_pSessionContext;
  416. (*m_pfnCallback)(pMsg);
  417. }
  418. }
  419. void CAppletSession::SendMCSMessage
  420. (
  421. T120AppletSessionMsg *pMsg
  422. )
  423. {
  424. ASSERT(NULL != pMsg);
  425. if (NULL != m_pfnCallback)
  426. {
  427. pMsg->nConfID = m_nConfID;
  428. pMsg->pAppletContext = m_pAppletContext;
  429. pMsg->pSessionContext = m_pSessionContext;
  430. (*m_pfnCallback)(pMsg);
  431. }
  432. else
  433. {
  434. if (pMsg->eMsgType == MCS_UNIFORM_SEND_DATA_INDICATION ||
  435. pMsg->eMsgType == MCS_SEND_DATA_INDICATION)
  436. {
  437. if (! m_fMCSFreeDataIndBuffer)
  438. {
  439. WARNING_OUT(("CAppletSession::SendMCSMessage: send data ind, free ptr=0x%x, len=%d", pMsg->SendDataInd.user_data.value, pMsg->SendDataInd.user_data.length));
  440. FreeSendDataBuffer(pMsg->SendDataInd.user_data.value);
  441. }
  442. }
  443. }
  444. }
  445. void CAppletSession::MCSCallback
  446. (
  447. T120AppletSessionMsg *pMsg
  448. )
  449. {
  450. // dispatch the message depeneding on whether we are still in the join process or not
  451. if (IsJoining())
  452. {
  453. SetTempMsg(pMsg);
  454. switch (pMsg->eMsgType)
  455. {
  456. case MCS_ATTACH_USER_CONFIRM:
  457. HandleAttachUserConfirm();
  458. break;
  459. case MCS_CHANNEL_JOIN_CONFIRM:
  460. HandleJoinChannelConfirm();
  461. break;
  462. case MCS_TOKEN_GRAB_CONFIRM:
  463. HandleTokenGrabConfirm();
  464. break;
  465. }
  466. }
  467. else
  468. {
  469. SendMCSMessage(pMsg);
  470. }
  471. }
  472. void CAppletSession::GCCCallback
  473. (
  474. T120AppletSessionMsg *pMsg
  475. )
  476. {
  477. if (IsJoining())
  478. {
  479. // remember the current GCC applet SAP message
  480. SetTempMsg(pMsg);
  481. switch (pMsg->eMsgType)
  482. {
  483. case GCC_ENROLL_CONFIRM:
  484. HandleEnrollConfirm();
  485. break;
  486. case GCC_APP_ROSTER_REPORT_INDICATION:
  487. if (! m_fFirstRoster)
  488. {
  489. if (APPSESS_INACTIVELY_ENROLL_CON == m_eState)
  490. {
  491. DoResourceRequests();
  492. }
  493. m_fFirstRoster = TRUE;
  494. }
  495. break;
  496. case GCC_REGISTER_CHANNEL_CONFIRM:
  497. HandleRegisterChannelConfirm();
  498. break;
  499. case GCC_RETRIEVE_ENTRY_CONFIRM:
  500. HandleRetrieveEntryConfirm();
  501. break;
  502. }
  503. }
  504. else
  505. {
  506. SendCallbackMessage(pMsg);
  507. }
  508. }
  509. void CAppletSession::SetState(APPLET_SESSION_STATE eNewState)
  510. {
  511. #ifdef _DEBUG
  512. if (APPSESS_LEAVING != eNewState)
  513. {
  514. switch (m_eState)
  515. {
  516. case APPSESS_INITIALIZED:
  517. ASSERT(APPSESS_ATTACH_USER_REQ == eNewState);
  518. break;
  519. // attach user
  520. case APPSESS_ATTACH_USER_REQ:
  521. ASSERT(APPSESS_ATTACH_USER_CON == eNewState);
  522. break;
  523. case APPSESS_ATTACH_USER_CON:
  524. ASSERT(APPSESS_JOIN_MY_CHANNEL_REQ == eNewState);
  525. break;
  526. // join my channel
  527. case APPSESS_JOIN_MY_CHANNEL_REQ:
  528. ASSERT(APPSESS_JOIN_MY_CHANNEL_CON == eNewState);
  529. break;
  530. case APPSESS_JOIN_MY_CHANNEL_CON:
  531. ASSERT(APPSESS_JOIN_STATIC_CHANNEL_REQ == eNewState ||
  532. APPSESS_INACTIVELY_ENROLL_REQ == eNewState ||
  533. APPSESS_ACTIVELY_ENROLL_REQ == eNewState);
  534. break;
  535. // join static channels
  536. case APPSESS_JOIN_STATIC_CHANNEL_REQ:
  537. ASSERT(APPSESS_JOIN_STATIC_CHANNEL_CON == eNewState);
  538. break;
  539. case APPSESS_JOIN_STATIC_CHANNEL_CON:
  540. ASSERT(APPSESS_JOIN_STATIC_CHANNEL_REQ == eNewState ||
  541. APPSESS_INACTIVELY_ENROLL_REQ == eNewState ||
  542. APPSESS_ACTIVELY_ENROLL_REQ == eNewState);
  543. break;
  544. // enroll applet in order to do resource requests
  545. case APPSESS_INACTIVELY_ENROLL_REQ:
  546. ASSERT(APPSESS_INACTIVELY_ENROLL_CON == eNewState);
  547. break;
  548. case APPSESS_INACTIVELY_ENROLL_CON:
  549. ASSERT(APPSESS_RESOURCE_REQ == eNewState);
  550. break;
  551. // do resource requests
  552. case APPSESS_RESOURCE_REQ:
  553. ASSERT(APPSESS_RESOURCE_CON == eNewState ||
  554. APPSESS_ACTIVELY_ENROLL_REQ == eNewState);
  555. break;
  556. case APPSESS_RESOURCE_CON:
  557. ASSERT(APPSESS_RESOURCE_REQ == eNewState);
  558. break;
  559. // enroll applet in order to do resource requests
  560. case APPSESS_ACTIVELY_ENROLL_REQ:
  561. ASSERT(APPSESS_ACTIVELY_ENROLL_CON == eNewState);
  562. break;
  563. case APPSESS_ACTIVELY_ENROLL_CON:
  564. ASSERT(APPSESS_JOINED == eNewState);
  565. break;
  566. // done with the join process
  567. case APPSESS_JOINED:
  568. ASSERT(APPSESS_LEAVING == eNewState);
  569. break;
  570. case APPSESS_LEAVING:
  571. ASSERT(APPSESS_LEFT == eNewState);
  572. break;
  573. default:
  574. ASSERT(0);
  575. break;
  576. } // switch
  577. } // if
  578. #endif
  579. m_eState = eNewState;
  580. }
  581. BOOL CAppletSession::IsJoining(void)
  582. {
  583. return (APPSESS_INITIALIZED < m_eState && m_eState < APPSESS_JOINED);
  584. }
  585. void CAppletSession::HandleAttachUserConfirm(void)
  586. {
  587. if (MCS_ATTACH_USER_CONFIRM == m_pTempMsg->eMsgType)
  588. {
  589. ASSERT(IsJoining());
  590. SetState(APPSESS_ATTACH_USER_CON);
  591. if (RESULT_SUCCESSFUL == m_pTempMsg->AttachUserConfirm.eResult)
  592. {
  593. m_uidMyself = m_pTempMsg->AttachUserConfirm.nUserID;
  594. // join my channel
  595. SetState(APPSESS_JOIN_MY_CHANNEL_REQ);
  596. T120Error rc = m_pMCSAppletSAP->ChannelJoin(m_uidMyself);
  597. if (T120_NO_ERROR == rc)
  598. {
  599. return;
  600. }
  601. SetError(rc);
  602. AbortJoin();
  603. }
  604. else
  605. {
  606. SetError(m_pTempMsg->AttachUserConfirm.eResult);
  607. AbortJoin();
  608. }
  609. }
  610. else
  611. {
  612. ERROR_OUT(("CAppletSession::HandleAttachUserConfirm: expecting attach user confirm, invalid msg type=%u",
  613. m_pTempMsg->eMsgType));
  614. }
  615. }
  616. void CAppletSession::HandleTokenGrabConfirm(void)
  617. {
  618. if (MCS_TOKEN_GRAB_CONFIRM == m_pTempMsg->eMsgType)
  619. {
  620. BOOL fImmediateNotification = m_JoinRequest.aResourceReqs[m_nArrayIndex].fImmediateNotification;
  621. ASSERT(IsJoining());
  622. switch (GetState())
  623. {
  624. case APPSESS_RESOURCE_REQ:
  625. ASSERT(APPLET_GRAB_TOKEN_REQUEST == m_JoinRequest.aResourceReqs[m_nArrayIndex].eCommand);
  626. // remember the notification message if needed
  627. if (fImmediateNotification)
  628. {
  629. AddRef();
  630. SendMCSMessage(m_pTempMsg);
  631. if (0 == Release())
  632. {
  633. WARNING_OUT(("CAppletSession::HandleTokenGrabConfirm: involuntary exit"));
  634. return;
  635. }
  636. }
  637. SetState(APPSESS_RESOURCE_CON);
  638. if (RESULT_SUCCESSFUL != m_pTempMsg->TokenConfirm.eResult)
  639. {
  640. m_JoinRequest.aResourceReqs[m_nArrayIndex].nTokenID = 0; // do not grab it
  641. }
  642. DoResourceRequests();
  643. break;
  644. default:
  645. ERROR_OUT(("CAppletSession::HandleTokenGrabConfirm: unknown state=%u", (UINT) GetState()));
  646. break;
  647. }
  648. }
  649. }
  650. void CAppletSession::HandleJoinChannelConfirm(void)
  651. {
  652. if (MCS_CHANNEL_JOIN_CONFIRM == m_pTempMsg->eMsgType)
  653. {
  654. ASSERT(IsJoining());
  655. if (RESULT_SUCCESSFUL == m_pTempMsg->ChannelConfirm.eResult)
  656. {
  657. T120ChannelID nChannelID = m_pTempMsg->ChannelConfirm.nChannelID;
  658. switch (GetState())
  659. {
  660. case APPSESS_JOIN_MY_CHANNEL_REQ:
  661. if (nChannelID == m_uidMyself)
  662. {
  663. SetState(APPSESS_JOIN_MY_CHANNEL_CON);
  664. DoJoinStaticChannels();
  665. }
  666. else
  667. {
  668. ERROR_OUT(("CAppletSession::HandleJoinChannelConfirm: unknown channel join confirm, chid=%x", (UINT) nChannelID));
  669. }
  670. break;
  671. case APPSESS_JOIN_STATIC_CHANNEL_REQ:
  672. if (nChannelID == m_JoinRequest.aStaticChannels[m_nArrayIndex])
  673. {
  674. SetState(APPSESS_JOIN_STATIC_CHANNEL_CON);
  675. DoJoinStaticChannels();
  676. }
  677. else
  678. {
  679. ERROR_OUT(("CAppletSession::HandleJoinChannelConfirm: unknown channel join confirm, chid=%x", (UINT) nChannelID));
  680. }
  681. break;
  682. case APPSESS_RESOURCE_REQ:
  683. // SetState(APPSESS_RESOURCE_CON);
  684. DoResourceRequests();
  685. break;
  686. default:
  687. ERROR_OUT(("CAppletSession::HandleJoinChannelConfirm: unknown state=%u", (UINT) GetState()));
  688. break;
  689. }
  690. }
  691. else
  692. {
  693. ERROR_OUT(("CAppletSession::HandleJoinChannelConfirm: mcs_result=%u", (UINT) m_pTempMsg->ChannelConfirm.eResult));
  694. SetError(m_pTempMsg->ChannelConfirm.eResult);
  695. AbortJoin();
  696. }
  697. }
  698. else
  699. {
  700. ERROR_OUT(("CAppletSession::HandleJoinChannelConfirm: invalid msg type=%u", (UINT) m_pTempMsg->eMsgType));
  701. }
  702. }
  703. void CAppletSession::HandleEnrollConfirm(void)
  704. {
  705. if (GCC_ENROLL_CONFIRM == m_pTempMsg->eMsgType)
  706. {
  707. m_sidMyself = m_pTempMsg->AppEnrollConfirm.sidMyself;
  708. m_eidMyself = m_pTempMsg->AppEnrollConfirm.eidMyself;
  709. m_nidMyself = m_pTempMsg->AppEnrollConfirm.nidMyself;
  710. switch (GetState())
  711. {
  712. case APPSESS_ACTIVELY_ENROLL_REQ:
  713. ASSERT(m_pTempMsg->AppEnrollConfirm.nConfID == m_nConfID);
  714. SetState(APPSESS_ACTIVELY_ENROLL_CON);
  715. if (GCC_RESULT_SUCCESSFUL == m_pTempMsg->AppEnrollConfirm.nResult)
  716. {
  717. SetState(APPSESS_JOINED);
  718. SendJoinResult(GCC_RESULT_SUCCESSFUL);
  719. }
  720. else
  721. {
  722. ERROR_OUT(("CAppletSession::HandleEnrollConfirm: gcc_result=%u", (UINT) m_pTempMsg->AppEnrollConfirm.nResult));
  723. SetError(m_pTempMsg->AppEnrollConfirm.nResult);
  724. AbortJoin();
  725. }
  726. break;
  727. case APPSESS_INACTIVELY_ENROLL_REQ:
  728. ASSERT(m_pTempMsg->AppEnrollConfirm.nConfID == m_nConfID);
  729. SetState(APPSESS_INACTIVELY_ENROLL_CON);
  730. if (GCC_RESULT_SUCCESSFUL == m_pTempMsg->AppEnrollConfirm.nResult)
  731. {
  732. // DoResourceRequests();
  733. }
  734. else
  735. {
  736. ERROR_OUT(("CAppletSession::HandleEnrollConfirm: gcc_result=%u", (UINT) m_pTempMsg->AppEnrollConfirm.nResult));
  737. SetError(m_pTempMsg->AppEnrollConfirm.nResult);
  738. AbortJoin();
  739. }
  740. break;
  741. default:
  742. ERROR_OUT(("CAppletSession::HandleEnrollConfirm: unknown state=%u", (UINT) GetState()));
  743. break;
  744. }
  745. }
  746. else
  747. {
  748. ERROR_OUT(("CAppletSession::HandleEnrollConfirm: expecting enroll confirm, invalid msg type=%u",
  749. (UINT) m_pTempMsg->eMsgType));
  750. }
  751. }
  752. void CAppletSession::HandleRegisterChannelConfirm(void)
  753. {
  754. if (GCC_REGISTER_CHANNEL_CONFIRM == m_pTempMsg->eMsgType)
  755. {
  756. switch (GetState())
  757. {
  758. case APPSESS_RESOURCE_REQ:
  759. DoResourceRequests();
  760. break;
  761. default:
  762. ERROR_OUT(("CAppletSession::HandleRegisterChannelConfirm: unknown state=%u", (UINT) GetState()));
  763. break;
  764. }
  765. }
  766. else
  767. {
  768. ERROR_OUT(("CAppletSession::HandleEnrollConfirm: expecting channel register confirm, invalid msg type=%u",
  769. (UINT) m_pTempMsg->eMsgType));
  770. }
  771. }
  772. void CAppletSession::HandleRetrieveEntryConfirm(void)
  773. {
  774. if (GCC_RETRIEVE_ENTRY_CONFIRM == m_pTempMsg->eMsgType)
  775. {
  776. switch (GetState())
  777. {
  778. case APPSESS_RESOURCE_REQ:
  779. DoResourceRequests();
  780. break;
  781. default:
  782. ERROR_OUT(("CAppletSession::HandleRetrieveEntryConfirm: unknown state=%u", (UINT) GetState()));
  783. break;
  784. }
  785. }
  786. else
  787. {
  788. ERROR_OUT(("CAppletSession::HandleEnrollConfirm: expecting entry retrieve confirm, invalid msg type=%u",
  789. (UINT) m_pTempMsg->eMsgType));
  790. }
  791. }
  792. T120Error CAppletSession::DoEnroll
  793. (
  794. BOOL fEnroll,
  795. BOOL fEnrollActively
  796. )
  797. {
  798. T120Error rc;
  799. T120RequestTag tag;
  800. GCCEnrollRequest Req;
  801. Req.pSessionKey = &m_JoinRequest.SessionKey;
  802. Req.fEnrollActively = fEnrollActively;
  803. Req.nUserID = m_uidMyself;
  804. Req.fConductingCapable = m_JoinRequest.fConductingCapable;
  805. Req.nStartupChannelType = m_JoinRequest.nStartupChannelType;
  806. Req.cNonCollapsedCaps = m_JoinRequest.cNonCollapsedCaps;
  807. Req.apNonCollapsedCaps = m_JoinRequest.apNonCollapsedCaps;
  808. Req.cCollapsedCaps = m_JoinRequest.cCollapsedCaps;
  809. Req.apCollapsedCaps = m_JoinRequest.apCollapsedCaps;
  810. Req.fEnroll = fEnroll;
  811. rc = m_pApplet->GetAppSap()->AppEnroll(m_nConfID, &Req, &tag);
  812. if (GCC_NO_ERROR == rc)
  813. {
  814. return GCC_NO_ERROR;
  815. }
  816. if (fEnroll)
  817. {
  818. WARNING_OUT(("CAppletSession::DoEnroll: AppEnroll failed, rc=%u", (UINT) rc));
  819. ASSERT(GCC_CONFERENCE_NOT_ESTABLISHED == rc);
  820. SetError(rc);
  821. AbortJoin();
  822. }
  823. else
  824. {
  825. // doing nothing because we don't care we fail to unenroll...
  826. }
  827. return rc;
  828. }
  829. void CAppletSession::DoJoinStaticChannels(void)
  830. {
  831. T120Error rc;
  832. ASSERT(IsJoining());
  833. // set up array index
  834. switch (GetState())
  835. {
  836. case APPSESS_JOIN_MY_CHANNEL_CON:
  837. m_nArrayIndex = 0;
  838. break;
  839. case APPSESS_JOIN_STATIC_CHANNEL_CON:
  840. m_nArrayIndex++;
  841. break;
  842. default:
  843. ERROR_OUT(("CAppletSession::DoJoinStaticChannels: invalid state=%u", (UINT) GetState()));
  844. break;
  845. }
  846. if (m_nArrayIndex < m_JoinRequest.cStaticChannels &&
  847. NULL != m_JoinRequest.aStaticChannels)
  848. {
  849. SetState(APPSESS_JOIN_STATIC_CHANNEL_REQ);
  850. rc = m_pMCSAppletSAP->ChannelJoin(m_JoinRequest.aStaticChannels[m_nArrayIndex]);
  851. if (T120_NO_ERROR == rc)
  852. {
  853. return;
  854. }
  855. ERROR_OUT(("CAppletSession::DoJoinStaticChannels: ChannelJoin failed, rc=%u", (UINT) rc));
  856. SetError(rc);
  857. AbortJoin();
  858. }
  859. else
  860. {
  861. m_nArrayIndex = 0;
  862. if (m_JoinRequest.cResourceReqs == 0)
  863. {
  864. SetState(APPSESS_ACTIVELY_ENROLL_REQ);
  865. DoEnroll(TRUE, TRUE);
  866. }
  867. else
  868. {
  869. SetState(APPSESS_INACTIVELY_ENROLL_REQ);
  870. DoEnroll(TRUE, FALSE);
  871. }
  872. }
  873. }
  874. void CAppletSession::DoResourceRequests(void)
  875. {
  876. //T120Error rc;
  877. BOOL fInitResourceState = FALSE;
  878. //ULONG i;
  879. ASSERT(IsJoining());
  880. // set up array index
  881. switch (GetState())
  882. {
  883. case APPSESS_INACTIVELY_ENROLL_CON:
  884. m_nArrayIndex = 0;
  885. fInitResourceState = TRUE;
  886. SetState(APPSESS_RESOURCE_REQ);
  887. break;
  888. case APPSESS_RESOURCE_REQ:
  889. // do nothing
  890. break;
  891. case APPSESS_RESOURCE_CON:
  892. m_nArrayIndex++;
  893. fInitResourceState = TRUE;
  894. SetState(APPSESS_RESOURCE_REQ);
  895. break;
  896. default:
  897. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: invalid state=%u", (UINT) GetState()));
  898. break;
  899. }
  900. if (m_nArrayIndex < m_JoinRequest.cResourceReqs)
  901. {
  902. ASSERT(NULL != m_JoinRequest.aResourceReqs);
  903. switch (m_JoinRequest.aResourceReqs[m_nArrayIndex].eCommand)
  904. {
  905. case APPLET_GRAB_TOKEN_REQUEST:
  906. DoGrabTokenRequest();
  907. break;
  908. case APPLET_JOIN_DYNAMIC_CHANNEL:
  909. DoJoinDynamicChannels(fInitResourceState);
  910. break;
  911. default:
  912. ERROR_OUT(("CAppletSession::DoResourceRequests: should not get here, state=%u",
  913. (UINT) m_JoinRequest.aResourceReqs[m_nArrayIndex].eCommand));
  914. break;
  915. }
  916. }
  917. else
  918. {
  919. SetState(APPSESS_ACTIVELY_ENROLL_REQ);
  920. DoEnroll(TRUE, TRUE);
  921. }
  922. }
  923. void CAppletSession::DoGrabTokenRequest(void)
  924. {
  925. T120TokenRequest Req;
  926. Req.eCommand = APPLET_GRAB_TOKEN;
  927. Req.nTokenID = m_JoinRequest.aResourceReqs[m_nArrayIndex].nTokenID;
  928. TokenRequest(&Req);
  929. }
  930. void CAppletSession::DoJoinDynamicChannels(BOOL fInitState)
  931. {
  932. T120Error rc;
  933. //ULONG i;
  934. ASSERT(IsJoining());
  935. ASSERT(APPLET_JOIN_DYNAMIC_CHANNEL == m_JoinRequest.aResourceReqs[m_nArrayIndex].eCommand);
  936. if (fInitState)
  937. {
  938. m_eDynamicChannelJoinState = DCJS_INITIALIZED;
  939. }
  940. switch (m_eDynamicChannelJoinState)
  941. {
  942. case DCJS_INITIALIZED:
  943. // clean up all the dynamic channel id
  944. m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID = 0;
  945. // start the first dynamic channel negotiation process
  946. // SetState(APPSESS_JOIN_DYNAMIC_CHANNEL_REQ);
  947. m_eDynamicChannelJoinState = DCJS_RETRIEVE_ENTRY_REQ;
  948. rc = m_pApplet->GetAppSap()->RegistryRetrieveEntry(m_nConfID,
  949. &m_JoinRequest.aResourceReqs[m_nArrayIndex].RegKey);
  950. if (T120_NO_ERROR != rc)
  951. {
  952. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: RegistryRetrieveEntry failed, rc=%u", (UINT) rc));
  953. SetError(rc);
  954. AbortJoin();
  955. }
  956. break;
  957. case DCJS_EXISTING_CHANNEL_JOIN_REQ:
  958. if (MCS_CHANNEL_JOIN_CONFIRM == m_pTempMsg->eMsgType)
  959. {
  960. if (m_pTempMsg->ChannelConfirm.nChannelID == m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID)
  961. {
  962. m_eDynamicChannelJoinState = DCJS_EXISTING_CHANNEL_JOIN_CON;
  963. SetState(APPSESS_RESOURCE_CON);
  964. DoResourceRequests();
  965. }
  966. else
  967. {
  968. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: unknown channel join confirm, chid=%x",
  969. (UINT) m_pTempMsg->ChannelConfirm.nChannelID));
  970. }
  971. }
  972. else
  973. {
  974. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: expecting channel join confirm, invalid msg type=%u",
  975. (UINT) m_pTempMsg->eMsgType));
  976. }
  977. break;
  978. case DCJS_NEW_CHANNEL_JOIN_REQ:
  979. if (MCS_CHANNEL_JOIN_CONFIRM == m_pTempMsg->eMsgType)
  980. {
  981. ASSERT(0 == m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID);
  982. m_eDynamicChannelJoinState = DCJS_NEW_CHANNEL_JOIN_CON;
  983. // remember the channel id
  984. m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID = m_pTempMsg->ChannelConfirm.nChannelID;
  985. // try to register this channel
  986. m_eDynamicChannelJoinState = DCJS_REGISTER_CHANNEL_REQ;
  987. rc = m_pApplet->GetAppSap()->RegisterChannel(m_nConfID,
  988. &m_JoinRequest.aResourceReqs[m_nArrayIndex].RegKey,
  989. m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID);
  990. if (T120_NO_ERROR != rc)
  991. {
  992. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: RegistryRetrieveEntry failed, rc=%u", (UINT) rc));
  993. SetError(rc);
  994. AbortJoin();
  995. }
  996. }
  997. else
  998. {
  999. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: expecting channel join confirm, invalid msg type=%u",
  1000. (UINT) m_pTempMsg->eMsgType));
  1001. }
  1002. break;
  1003. case DCJS_RETRIEVE_ENTRY_REQ:
  1004. if (GCC_RETRIEVE_ENTRY_CONFIRM == m_pTempMsg->eMsgType)
  1005. {
  1006. m_eDynamicChannelJoinState = DCJS_RETRIEVE_ENTRY_CON;
  1007. ASSERT(m_nConfID == m_pTempMsg->RegistryConfirm.nConfID);
  1008. if (GCC_RESULT_SUCCESSFUL == m_pTempMsg->RegistryConfirm.nResult)
  1009. {
  1010. ASSERT(GCC_REGISTRY_CHANNEL_ID == m_pTempMsg->RegistryConfirm.pRegItem->item_type);
  1011. ASSERT(0 != m_pTempMsg->RegistryConfirm.pRegItem->channel_id);
  1012. // remember the existing channel ID
  1013. m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID = m_pTempMsg->RegistryConfirm.pRegItem->channel_id;
  1014. // join this channel
  1015. m_eDynamicChannelJoinState = DCJS_EXISTING_CHANNEL_JOIN_REQ;
  1016. rc = m_pMCSAppletSAP->ChannelJoin(m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID);
  1017. if (T120_NO_ERROR != rc)
  1018. {
  1019. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: ChannelJoin(%u) failed, rc=%u",
  1020. (UINT) m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID, (UINT) rc));
  1021. SetError(rc);
  1022. AbortJoin();
  1023. }
  1024. }
  1025. else
  1026. {
  1027. ASSERT(GCC_RESULT_ENTRY_DOES_NOT_EXIST == m_pTempMsg->RegistryConfirm.nResult);
  1028. ASSERT(0 == m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID);
  1029. // allocate a new channel
  1030. m_eDynamicChannelJoinState = DCJS_NEW_CHANNEL_JOIN_REQ;
  1031. rc = m_pMCSAppletSAP->ChannelJoin(0);
  1032. if (T120_NO_ERROR != rc)
  1033. {
  1034. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: ChannelJoin(0) failed, rc=%u", (UINT) rc));
  1035. SetError(rc);
  1036. AbortJoin();
  1037. }
  1038. }
  1039. }
  1040. else
  1041. {
  1042. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: expecting entry retrieve confirm, invalid msg type=%u",
  1043. (UINT) m_pTempMsg->eMsgType));
  1044. }
  1045. break;
  1046. case DCJS_REGISTER_CHANNEL_REQ:
  1047. if (GCC_REGISTER_CHANNEL_CONFIRM == m_pTempMsg->eMsgType)
  1048. {
  1049. ASSERT(0 != m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID);
  1050. m_eDynamicChannelJoinState = DCJS_REGISTER_CHANNEL_CON;
  1051. if (GCC_RESULT_SUCCESSFUL == m_pTempMsg->RegistryConfirm.nResult)
  1052. {
  1053. ASSERT(GCC_REGISTRY_CHANNEL_ID == m_pTempMsg->RegistryConfirm.pRegItem->item_type);
  1054. ASSERT(m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID == m_pTempMsg->RegistryConfirm.pRegItem->channel_id);
  1055. SetState(APPSESS_RESOURCE_CON);
  1056. DoResourceRequests();
  1057. }
  1058. else
  1059. if (GCC_RESULT_ENTRY_ALREADY_EXISTS == m_pTempMsg->RegistryConfirm.nResult)
  1060. {
  1061. ASSERT(GCC_REGISTRY_CHANNEL_ID == m_pTempMsg->RegistryConfirm.pRegItem->item_type);
  1062. // leave the old channel (DON'T CARE ABOUT THE CONFIRM)
  1063. rc = m_pMCSAppletSAP->ChannelLeave(m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID);
  1064. ASSERT(T120_NO_ERROR == rc);
  1065. // remember the new channel id
  1066. m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID = m_pTempMsg->RegistryConfirm.pRegItem->channel_id;
  1067. // join the new channel
  1068. m_eDynamicChannelJoinState = DCJS_EXISTING_CHANNEL_JOIN_REQ;
  1069. rc = m_pMCSAppletSAP->ChannelJoin(m_JoinRequest.aResourceReqs[m_nArrayIndex].nChannelID);
  1070. if (T120_NO_ERROR != rc)
  1071. {
  1072. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: ChannelJoin(0) failed, rc=%u", (UINT) rc));
  1073. SetError(rc);
  1074. AbortJoin();
  1075. }
  1076. }
  1077. else
  1078. {
  1079. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: ChannelJoin(0) failed, result=%u",
  1080. (UINT) m_pTempMsg->RegistryConfirm.nResult));
  1081. SetError(m_pTempMsg->RegistryConfirm.nResult);
  1082. AbortJoin();
  1083. }
  1084. }
  1085. else
  1086. {
  1087. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: expecting channel register confirm, invalid msg type=%u",
  1088. (UINT) m_pTempMsg->eMsgType));
  1089. }
  1090. break;
  1091. default:
  1092. ERROR_OUT(("CAppletSession::DoJoinDynamicChannels: should not get here, state=%u", (UINT) m_eDynamicChannelJoinState));
  1093. break;
  1094. }
  1095. }
  1096. void CAppletSession::AbortJoin(void)
  1097. {
  1098. T120Result eResult = T120_RESULT_CHECK_T120_ERROR;
  1099. T120Error eError = T12_ERROR_CHECK_T120_RESULT;
  1100. switch (m_eErrorType)
  1101. {
  1102. case NONE_CHOSEN:
  1103. ERROR_OUT(("CAppletSession::AbortJoin: NON_CHOSEN, impossible"));
  1104. break;
  1105. case ERROR_CHOSEN:
  1106. eError = m_Error.eError;
  1107. break;
  1108. case RESULT_CHOSEN:
  1109. eResult = m_Error.eResult;
  1110. break;
  1111. default:
  1112. ERROR_OUT(("CAppletSession::AbortJoin: invalid err type=%u", (UINT) m_eErrorType));
  1113. break;
  1114. }
  1115. // let's debug why the join process is aborted.
  1116. WARNING_OUT(("CAppletSession::AbortJoin: eResult=%u, eError=%u", eResult, eError));
  1117. ASSERT(GCC_CONFERENCE_NOT_ESTABLISHED == eError ||
  1118. T12_ERROR_CHECK_T120_RESULT == eError);
  1119. SendJoinResult(eResult, eError);
  1120. }
  1121. void CAppletSession::SendJoinResult(T120Result eResult, T120Error eError)
  1122. {
  1123. T120AppletSessionMsg Msg;
  1124. ::ZeroMemory(&Msg, sizeof(Msg));
  1125. Msg.eMsgType = T120_JOIN_SESSION_CONFIRM;
  1126. Msg.nConfID = m_nConfID;
  1127. Msg.JoinSessionConfirm.eResult = eResult;
  1128. Msg.JoinSessionConfirm.eError = eError;
  1129. Msg.JoinSessionConfirm.pIAppletSession = (IT120AppletSession *) this;
  1130. if (T120_RESULT_SUCCESSFUL == eResult)
  1131. {
  1132. Msg.JoinSessionConfirm.uidMyself = m_uidMyself;
  1133. Msg.JoinSessionConfirm.sidMyself = m_sidMyself;
  1134. Msg.JoinSessionConfirm.eidMyself = m_eidMyself;
  1135. Msg.JoinSessionConfirm.nidMyself = m_nidMyself;
  1136. Msg.JoinSessionConfirm.cResourceReqs = m_JoinRequest.cResourceReqs;
  1137. Msg.JoinSessionConfirm.aResourceReqs = m_JoinRequest.aResourceReqs;
  1138. }
  1139. SendCallbackMessage(&Msg);
  1140. }
  1141. CApplet::CApplet
  1142. (
  1143. T120Error *pRetCode
  1144. )
  1145. :
  1146. CRefCount(MAKE_STAMP_ID('C','A','p','l')),
  1147. m_pfnCallback(NULL),
  1148. m_pAppletContext(NULL),
  1149. m_pAppSap(NULL),
  1150. m_pAutoJoinReq(NULL),
  1151. m_pAutoAppletSession(NULL)
  1152. {
  1153. *pRetCode = ::GCC_CreateAppSap(&m_pAppSap, this, GCC_SapCallback);
  1154. }
  1155. CApplet::~CApplet(void)
  1156. {
  1157. ASSERT(NULL == m_pfnCallback);
  1158. ASSERT(NULL == m_pAppletContext);
  1159. ASSERT(NULL == m_pAppSap);
  1160. }
  1161. void CApplet::ReleaseInterface(void)
  1162. {
  1163. Unadvise();
  1164. if (NULL != m_pAppSap)
  1165. {
  1166. m_pAppSap->ReleaseInterface();
  1167. m_pAppSap = NULL;
  1168. }
  1169. Release();
  1170. }
  1171. void CApplet::Advise
  1172. (
  1173. LPFN_APPLET_CB pfnCallback,
  1174. LPVOID pAppletContext
  1175. )
  1176. {
  1177. ASSERT(NULL == m_pfnCallback);
  1178. ASSERT(NULL == m_pAppletContext);
  1179. m_pfnCallback = pfnCallback;
  1180. m_pAppletContext = pAppletContext;
  1181. // this may incur permit to enroll indication
  1182. g_pGCCController->RegisterApplet(this);
  1183. }
  1184. void CApplet::Unadvise(void)
  1185. {
  1186. m_pfnCallback = NULL;
  1187. m_pAppletContext = NULL;
  1188. if (g_pGCCController)
  1189. {
  1190. g_pGCCController->UnregisterApplet(this);
  1191. }
  1192. }
  1193. T120Error CApplet::RegisterAutoJoin
  1194. (
  1195. T120JoinSessionRequest *pReq
  1196. )
  1197. {
  1198. m_pAutoJoinReq = pReq;
  1199. return T120_NO_ERROR;
  1200. }
  1201. void CApplet::UnregisterAutoJoin(void)
  1202. {
  1203. m_pAutoJoinReq = NULL;
  1204. }
  1205. T120Error CApplet::CreateSession
  1206. (
  1207. IT120AppletSession **ppSession,
  1208. T120ConfID nConfID
  1209. )
  1210. {
  1211. if (NULL != ppSession)
  1212. {
  1213. if (NULL != g_pGCCController->GetConfObject(nConfID))
  1214. {
  1215. if (! FindSessionByConfID(nConfID))
  1216. {
  1217. DBG_SAVE_FILE_LINE
  1218. *ppSession = (IT120AppletSession *) new CAppletSession(this, nConfID);
  1219. if (NULL != *ppSession)
  1220. {
  1221. return T120_NO_ERROR;
  1222. }
  1223. ERROR_OUT(("CApplet::CreateSession: cannot create CAppletSession"));
  1224. return T120_ALLOCATION_FAILURE;
  1225. }
  1226. WARNING_OUT(("CApplet::CreateSession: session already exists for nConfID=%u", (UINT) nConfID));
  1227. return GCC_CONFERENCE_ALREADY_EXISTS;
  1228. }
  1229. WARNING_OUT(("CApplet::CreateSession: invalid conf, nConfID=%u", (UINT) nConfID));
  1230. return GCC_INVALID_CONFERENCE;
  1231. }
  1232. ERROR_OUT(("CApplet::CreateSession: ppSession is null"));
  1233. return T120_INVALID_PARAMETER;
  1234. }
  1235. void CApplet::SendCallbackMessage(T120AppletMsg *pMsg)
  1236. {
  1237. if (NULL != m_pfnCallback)
  1238. {
  1239. pMsg->pAppletContext = m_pAppletContext;
  1240. (*m_pfnCallback)(pMsg);
  1241. }
  1242. }
  1243. void CApplet::GCCCallback
  1244. (
  1245. T120AppletSessionMsg *pMsg
  1246. )
  1247. {
  1248. T120ConfID nConfID = pMsg->nConfID;
  1249. ASSERT(0 != nConfID);
  1250. if (GCC_PERMIT_TO_ENROLL_INDICATION == pMsg->eMsgType)
  1251. {
  1252. T120AppletMsg *p = (T120AppletMsg *) pMsg;
  1253. if (p->PermitToEnrollInd.fPermissionGranted && NULL != m_pAutoJoinReq)
  1254. {
  1255. HandleAutoJoin(nConfID);
  1256. }
  1257. else
  1258. {
  1259. if (! p->PermitToEnrollInd.fPermissionGranted)
  1260. {
  1261. CAppletSession *pAppletSession = FindSessionByConfID(nConfID);
  1262. if (NULL != pAppletSession)
  1263. {
  1264. if (pAppletSession->IsJoining())
  1265. {
  1266. pAppletSession->SetError(GCC_CONFERENCE_NOT_ESTABLISHED);
  1267. pAppletSession->AbortJoin();
  1268. }
  1269. }
  1270. }
  1271. SendCallbackMessage(p);
  1272. }
  1273. }
  1274. else
  1275. {
  1276. CAppletSession *pAppletSession = FindSessionByConfID(nConfID);
  1277. if (NULL != pAppletSession)
  1278. {
  1279. pAppletSession->GCCCallback(pMsg);
  1280. }
  1281. else
  1282. {
  1283. WARNING_OUT(("GCC_SapCallback: cannot find a session (%u) for this gcc message (%u)",
  1284. (UINT) nConfID, (UINT) pMsg->eMsgType));
  1285. }
  1286. }
  1287. }
  1288. void CALLBACK AutoJoinCallbackProc
  1289. (
  1290. T120AppletSessionMsg *pMsg
  1291. )
  1292. {
  1293. switch (pMsg->eMsgType)
  1294. {
  1295. case T120_JOIN_SESSION_CONFIRM:
  1296. if (NULL != pMsg->pAppletContext)
  1297. {
  1298. pMsg->pSessionContext = NULL;
  1299. ((CApplet *) pMsg->pAppletContext)->SendCallbackMessage((T120AppletMsg *) pMsg);
  1300. }
  1301. break;
  1302. default:
  1303. ERROR_OUT(("AutoJoinCallbackProc: invalid msg type=%u", pMsg->eMsgType));
  1304. break;
  1305. }
  1306. }
  1307. void CApplet::HandleAutoJoin
  1308. (
  1309. T120ConfID nConfID
  1310. )
  1311. {
  1312. DBG_SAVE_FILE_LINE
  1313. CAppletSession *pSession = new CAppletSession(this, nConfID);
  1314. if (NULL != pSession)
  1315. {
  1316. T120Error rc;
  1317. pSession->Advise(AutoJoinCallbackProc, this, pSession);
  1318. rc = pSession->Join(m_pAutoJoinReq);
  1319. if (rc != T120_NO_ERROR)
  1320. {
  1321. delete pSession;
  1322. }
  1323. }
  1324. }
  1325. CAppletSession * CSessionList::FindByConfID
  1326. (
  1327. T120ConfID nConfID
  1328. )
  1329. {
  1330. CAppletSession *p;
  1331. Reset();
  1332. while (NULL != (p = Iterate()))
  1333. {
  1334. if (p->GetConfID() == nConfID)
  1335. {
  1336. return p;
  1337. }
  1338. }
  1339. return NULL;
  1340. }
  1341. void CALLBACK GCC_SapCallback
  1342. (
  1343. GCCAppSapMsg *_pMsg
  1344. )
  1345. {
  1346. T120AppletSessionMsg *pMsg = (T120AppletSessionMsg *) _pMsg;
  1347. CApplet *pApplet = (CApplet *) pMsg->pAppletContext;
  1348. ASSERT(NULL != pApplet);
  1349. pApplet->GCCCallback(pMsg);
  1350. }
  1351. void CALLBACK MCS_SapCallback
  1352. (
  1353. UINT nMsg,
  1354. LPARAM Param1,
  1355. LPVOID Param2
  1356. )
  1357. {
  1358. CAppletSession *pAppletSession = (CAppletSession *) Param2;
  1359. ASSERT(NULL != pAppletSession);
  1360. T120AppletSessionMsg Msg;
  1361. ::ZeroMemory(&Msg, sizeof(Msg));
  1362. Msg.eMsgType = (T120MessageType) nMsg;
  1363. // Msg.pAppletContext = NULL;
  1364. // Msg.pSessionContext = NULL;
  1365. // Msg.nConfID = 0;
  1366. // construct MCS message
  1367. switch (Msg.eMsgType)
  1368. {
  1369. // send data
  1370. case MCS_SEND_DATA_INDICATION:
  1371. case MCS_UNIFORM_SEND_DATA_INDICATION:
  1372. Msg.SendDataInd = * (SendDataIndicationPDU *) Param1;
  1373. break;
  1374. // channel confirm
  1375. case MCS_CHANNEL_JOIN_CONFIRM:
  1376. case MCS_CHANNEL_CONVENE_CONFIRM:
  1377. Msg.ChannelConfirm.eResult = (T120Result) HIWORD(Param1);
  1378. Msg.ChannelConfirm.nChannelID = LOWORD(Param1);
  1379. break;
  1380. // channel indication
  1381. case MCS_CHANNEL_LEAVE_INDICATION:
  1382. case MCS_CHANNEL_DISBAND_INDICATION:
  1383. case MCS_CHANNEL_ADMIT_INDICATION:
  1384. case MCS_CHANNEL_EXPEL_INDICATION:
  1385. Msg.ChannelInd.nChannelID = LOWORD(Param1);
  1386. Msg.ChannelInd.eReason = (T120Reason) HIWORD(Param1);
  1387. break;
  1388. // token confirm
  1389. case MCS_TOKEN_GRAB_CONFIRM:
  1390. case MCS_TOKEN_INHIBIT_CONFIRM:
  1391. case MCS_TOKEN_GIVE_CONFIRM:
  1392. case MCS_TOKEN_RELEASE_CONFIRM:
  1393. case MCS_TOKEN_TEST_CONFIRM:
  1394. Msg.TokenConfirm.nTokenID = LOWORD(Param1);
  1395. Msg.TokenConfirm.eResult = (T120Result) HIWORD(Param1);
  1396. break;
  1397. // token indication
  1398. case MCS_TOKEN_GIVE_INDICATION:
  1399. case MCS_TOKEN_PLEASE_INDICATION:
  1400. case MCS_TOKEN_RELEASE_INDICATION:
  1401. Msg.TokenInd.nTokenID = LOWORD(Param1);
  1402. Msg.TokenInd.eReason = (T120Reason) HIWORD(Param1);
  1403. break;
  1404. // user
  1405. case MCS_ATTACH_USER_CONFIRM:
  1406. Msg.AttachUserConfirm.nUserID = LOWORD(Param1);
  1407. Msg.AttachUserConfirm.eResult = (T120Result) HIWORD(Param1);
  1408. break;
  1409. case MCS_DETACH_USER_INDICATION:
  1410. Msg.DetachUserInd.nUserID = LOWORD(Param1);
  1411. Msg.DetachUserInd.eReason = (T120Reason) HIWORD(Param1);
  1412. break;
  1413. default:
  1414. WARNING_OUT(("MCS_SapCallback: Ignore MCS message, type=%u", Msg.eMsgType));
  1415. break;
  1416. }
  1417. pAppletSession->MCSCallback(&Msg);
  1418. }