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.

201 lines
4.0 KiB

  1. /* ----------------------------------------------------------------------
  2. Module: ULS.DLL (Service Provider)
  3. File: spstdatt.cpp
  4. Content: This file contains the standard-attribute object.
  5. History:
  6. 10/15/96 Chu, Lon-Chan [lonchanc]
  7. Created.
  8. Copyright (c) Microsoft Corporation 1996-1997
  9. ---------------------------------------------------------------------- */
  10. #include "ulsp.h"
  11. #include "spinc.h"
  12. /* ---------- public methods ----------- */
  13. UlsLdap_CStdAttrs::UlsLdap_CStdAttrs ( VOID )
  14. {
  15. }
  16. UlsLdap_CStdAttrs::~UlsLdap_CStdAttrs ( VOID )
  17. {
  18. }
  19. /* ---------- protected methods ----------- */
  20. HRESULT UlsLdap_CStdAttrs::SetStdAttrs (
  21. ULONG *puRespID,
  22. ULONG *puMsgID,
  23. ULONG uNotifyMsg,
  24. VOID *pInfo,
  25. SERVER_INFO *pServerInfo,
  26. TCHAR *pszDN )
  27. {
  28. MyAssert (puRespID != NULL || puMsgID != NULL);
  29. MyAssert (pInfo != NULL);
  30. MyAssert (pServerInfo != NULL);
  31. MyAssert (pszDN != NULL);
  32. // cache info
  33. //
  34. HRESULT hr = CacheInfo (pInfo);
  35. if (hr != S_OK)
  36. return hr;
  37. // Build modify array for ldap_modify()
  38. //
  39. LDAPMod **ppMod = NULL;
  40. hr = CreateSetStdAttrsModArr (&ppMod);
  41. if (hr != S_OK)
  42. return hr;
  43. MyAssert (ppMod != NULL);
  44. // so far, we are done with local preparation
  45. //
  46. // Get the session object
  47. //
  48. UlsLdap_CSession *pSession = NULL;
  49. hr = g_pSessionContainer->GetSession (&pSession, pServerInfo);
  50. if (hr != S_OK)
  51. {
  52. MemFree (ppMod);
  53. return hr;
  54. }
  55. MyAssert (pSession != NULL);
  56. // Get the ldap session
  57. //
  58. LDAP *ld = pSession->GetLd ();
  59. MyAssert (ld != NULL);
  60. // Send the data over the wire
  61. //
  62. ULONG uMsgID = ldap_modify (ld, pszDN, ppMod);
  63. MemFree (ppMod);
  64. if (uMsgID == -1)
  65. {
  66. hr = ::LdapError2Hresult (ld->ld_errno);
  67. pSession->Disconnect ();
  68. return hr;
  69. }
  70. // If the caller requests a response id,
  71. // then submit this pending item.
  72. // else free up the session object
  73. //
  74. if (puRespID != NULL)
  75. {
  76. // Initialize pending info
  77. //
  78. PENDING_INFO PendingInfo;
  79. ::FillDefPendingInfo (&PendingInfo, ld, uMsgID, INVALID_MSG_ID);
  80. PendingInfo.uLdapResType = LDAP_RES_MODIFY;
  81. PendingInfo.uNotifyMsg = uNotifyMsg;
  82. // Queue it
  83. //
  84. hr = g_pPendingQueue->EnterRequest (pSession, &PendingInfo);
  85. if (hr != S_OK)
  86. {
  87. // If queueing failed, then clean up
  88. //
  89. ldap_abandon (ld, uMsgID);
  90. pSession->Disconnect ();
  91. MyAssert (FALSE);
  92. }
  93. // Return the reponse id
  94. //
  95. *puRespID = PendingInfo.uRespID;
  96. }
  97. else
  98. {
  99. // Free up session (i.e. decrement the reference count)
  100. //
  101. pSession->Disconnect ();
  102. }
  103. if (puMsgID != NULL)
  104. *puMsgID = uMsgID;
  105. return hr;
  106. }
  107. HRESULT
  108. FillDefStdAttrsModArr (
  109. LDAPMod ***pppMod,
  110. DWORD dwFlags,
  111. ULONG cMaxAttrs,
  112. ULONG *pcTotal, // in/out parameter!!!
  113. LONG IsbuModOp,
  114. ULONG cPrefix,
  115. TCHAR *pszPrefix )
  116. {
  117. MyAssert (pppMod != NULL);
  118. MyAssert (pcTotal != NULL);
  119. MyAssert ( (cPrefix == 0 && pszPrefix == NULL) ||
  120. (cPrefix != 0 && pszPrefix != NULL));
  121. // Figure out the num of attributes
  122. //
  123. ULONG cAttrs = 0;
  124. for (ULONG i = 0; i < cMaxAttrs; i++)
  125. {
  126. if (dwFlags & 0x01)
  127. cAttrs++;
  128. dwFlags >>= 1;
  129. }
  130. // Allocate modify list
  131. //
  132. ULONG cTotal = *pcTotal + cPrefix + cAttrs;
  133. ULONG cbMod = IlsCalcModifyListSize (cTotal);
  134. *pppMod = (LDAPMod **) MemAlloc (cbMod);
  135. if (*pppMod == NULL)
  136. return ULS_E_MEMORY;
  137. // Fill in the modify list
  138. //
  139. LDAPMod *pMod;
  140. for (i = 0; i < cTotal; i++)
  141. {
  142. pMod = IlsGetModifyListMod (pppMod, cTotal, i);
  143. (*pppMod)[i] = pMod;
  144. pMod->mod_values = (TCHAR **) (pMod + 1);
  145. if (i < cPrefix)
  146. {
  147. pMod->mod_op = LDAP_MOD_REPLACE;
  148. pMod->mod_type = pszPrefix;
  149. pszPrefix += lstrlen (pszPrefix) + 1;
  150. *(pMod->mod_values) = pszPrefix;
  151. pszPrefix += lstrlen (pszPrefix) + 1;
  152. }
  153. }
  154. // Fix up the last one
  155. //
  156. IlsFixUpModOp ((*pppMod)[0], LDAP_MOD_REPLACE, IsbuModOp);
  157. (*pppMod)[cTotal] = NULL;
  158. // Return the total number of entries if needed
  159. //
  160. if (pcTotal)
  161. *pcTotal = cTotal;
  162. return S_OK;
  163. }
  164. /* ---------- private methods ----------- */