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.

369 lines
8.6 KiB

  1. //---------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. // Copyright (C) Microsoft Corporation, 1996 - 1997
  5. //
  6. // File: cenumt.cxx
  7. //
  8. // Contents: IIS Object Enumeration Code
  9. //
  10. // CIISTreeEnum::CIISTreeEnum()
  11. // CIISTreeEnum::CIISTreeEnum
  12. // CIISTreeEnum::EnumObjects
  13. // CIISTreeEnum::EnumObjects
  14. //
  15. // History: 25-Feb-97 SophiaC Created.
  16. //----------------------------------------------------------------------------
  17. #include "iis.hxx"
  18. #pragma hdrstop
  19. //+---------------------------------------------------------------------------
  20. //
  21. // Function: CIISEnumVariant::Create
  22. //
  23. // Synopsis:
  24. //
  25. // Arguments: [pCollection]
  26. // [ppEnumVariant]
  27. //
  28. // Returns: HRESULT
  29. //
  30. // Modifies:
  31. //
  32. //
  33. //----------------------------------------------------------------------------
  34. /* INTRINSA suppress=null_pointers, uninitialized */
  35. HRESULT
  36. CIISTreeEnum::Create(
  37. CIISTreeEnum FAR* FAR* ppenumvariant,
  38. BSTR ADsPath,
  39. VARIANT var,
  40. CCredentials& Credentials
  41. )
  42. {
  43. COSERVERINFO csiName;
  44. COSERVERINFO *pcsiParam = &csiName;
  45. IClassFactory * pcsfFactory = NULL;
  46. HRESULT hr = NOERROR;
  47. CIISTreeEnum FAR* penumvariant = NULL;
  48. LPWSTR pszIISPathName = NULL;
  49. OBJECTINFO ObjectInfo;
  50. POBJECTINFO pObjectInfo = NULL;
  51. CLexer Lexer(ADsPath);
  52. *ppenumvariant = NULL;
  53. penumvariant = new CIISTreeEnum();
  54. if (!penumvariant) {
  55. hr = E_OUTOFMEMORY;
  56. BAIL_ON_FAILURE(hr);
  57. }
  58. hr = ADsAllocString( ADsPath, &penumvariant->_ADsPath);
  59. BAIL_ON_FAILURE(hr);
  60. //
  61. // Parse the pathname
  62. //
  63. pObjectInfo = &ObjectInfo;
  64. memset(pObjectInfo, 0, sizeof(OBJECTINFO));
  65. hr = ADsObject(&Lexer, pObjectInfo);
  66. BAIL_ON_FAILURE(hr);
  67. penumvariant->_Credentials = Credentials;
  68. *ppenumvariant = penumvariant;
  69. //
  70. // Store ServerName
  71. //
  72. penumvariant->_pszServerName = AllocADsStr(pObjectInfo->TreeName);
  73. if (!(penumvariant->_pszServerName)) {
  74. hr = E_OUTOFMEMORY;
  75. BAIL_ON_FAILURE(hr);
  76. }
  77. hr = InitServerInfo(Credentials,
  78. penumvariant->_pszServerName,
  79. &(penumvariant->_pAdminBase),
  80. &(penumvariant->_pSchema));
  81. BAIL_ON_FAILURE(hr);
  82. pszIISPathName = AllocADsStr(ADsPath);
  83. if (!pszIISPathName) {
  84. hr = E_OUTOFMEMORY;
  85. BAIL_ON_FAILURE(hr);
  86. }
  87. memset(pszIISPathName, 0, sizeof(pszIISPathName));
  88. hr = BuildIISPathFromADsPath(
  89. pObjectInfo,
  90. pszIISPathName
  91. );
  92. BAIL_ON_FAILURE(hr);
  93. penumvariant->_pszMetaBasePath = AllocADsStr(pszIISPathName);
  94. if (!(penumvariant->_pszMetaBasePath)) {
  95. hr = E_OUTOFMEMORY;
  96. BAIL_ON_FAILURE(hr);
  97. }
  98. error:
  99. if (FAILED(hr)) {
  100. if (penumvariant) {
  101. delete penumvariant;
  102. *ppenumvariant = NULL;
  103. }
  104. }
  105. if (pszIISPathName) {
  106. FreeADsStr(pszIISPathName);
  107. }
  108. FreeObjectInfo(pObjectInfo);
  109. RRETURN(hr);
  110. }
  111. CIISTreeEnum::CIISTreeEnum():
  112. _ADsPath(NULL),
  113. _pszServerName(NULL),
  114. _pSchema(NULL),
  115. _pAdminBase(NULL),
  116. _pszMetaBasePath(NULL)
  117. {
  118. _dwObjectCurrentEntry = 0;
  119. }
  120. CIISTreeEnum::~CIISTreeEnum()
  121. {
  122. if (_ADsPath) {
  123. ADsFreeString(_ADsPath);
  124. }
  125. if (_pszServerName) {
  126. FreeADsStr(_pszServerName);
  127. }
  128. if (_pszMetaBasePath){
  129. FreeADsStr(_pszMetaBasePath);
  130. }
  131. //
  132. // Release everything
  133. //
  134. }
  135. HRESULT
  136. CIISTreeEnum::EnumGenericObjects(
  137. ULONG cElements,
  138. VARIANT FAR* pvar,
  139. ULONG FAR* pcElementFetched
  140. )
  141. {
  142. HRESULT hr = S_OK;
  143. IDispatch *pDispatch = NULL;
  144. DWORD i = 0;
  145. while (i < cElements ) {
  146. hr = GetGenericObject(&pDispatch);
  147. if (FAILED(hr)) {
  148. continue;
  149. }
  150. if (hr == S_FALSE) {
  151. break;
  152. }
  153. VariantInit(&pvar[i]);
  154. pvar[i].vt = VT_DISPATCH;
  155. pvar[i].pdispVal = pDispatch;
  156. (*pcElementFetched)++;
  157. i++;
  158. }
  159. return(hr);
  160. }
  161. /* #pragma INTRINSA suppress=all */
  162. HRESULT
  163. CIISTreeEnum::GetGenericObject(
  164. IDispatch ** ppDispatch
  165. )
  166. {
  167. HRESULT hr = S_OK;
  168. WCHAR NameBuf[MAX_PATH];
  169. WCHAR DataBuf[MAX_PATH];
  170. DWORD dwStatus = 0;
  171. DWORD dwReqdBufferLen;
  172. METADATA_HANDLE hObjHandle = NULL;
  173. METADATA_RECORD mdrData;
  174. *ppDispatch = NULL;
  175. hr = OpenAdminBaseKey(
  176. _Credentials,
  177. _pszServerName,
  178. _pszMetaBasePath,
  179. METADATA_PERMISSION_READ,
  180. &_pAdminBase,
  181. &hObjHandle
  182. );
  183. BAIL_ON_FAILURE(hr);
  184. hr = _pAdminBase->EnumKeys(
  185. hObjHandle,
  186. L"",
  187. (LPWSTR)NameBuf,
  188. _dwObjectCurrentEntry
  189. );
  190. BAIL_ON_FAILURE(hr);
  191. //
  192. // Find out Class Name
  193. //
  194. mdrData.dwMDIdentifier = MD_KEY_TYPE;
  195. mdrData.dwMDDataType = STRING_METADATA;
  196. mdrData.dwMDUserType = ALL_METADATA;
  197. mdrData.dwMDAttributes = METADATA_INHERIT;
  198. mdrData.dwMDDataLen = MAX_PATH;
  199. mdrData.pbMDData = (PBYTE)DataBuf;
  200. hr = _pAdminBase->GetData(
  201. hObjHandle,
  202. (LPWSTR)NameBuf,
  203. &mdrData,
  204. &dwReqdBufferLen
  205. );
  206. if (FAILED(hr)) {
  207. if (hr == MD_ERROR_DATA_NOT_FOUND) {
  208. LPWSTR pszIISPath;
  209. pszIISPath = _wcsupr((LPWSTR)_pszMetaBasePath);
  210. if (wcsstr(_pszMetaBasePath, L"W3SVC") != NULL) {
  211. memcpy((LPWSTR)DataBuf, WEBDIR_CLASS_W,
  212. SIZEOF_WEBDIR_CLASS_W);
  213. }
  214. else if (wcsstr(_pszMetaBasePath, L"MSFTPSVC") != NULL) {
  215. memcpy((LPWSTR)DataBuf, FTPVDIR_CLASS_W,
  216. SIZEOF_FTPVDIR_CLASS_W);
  217. }
  218. else {
  219. memcpy((LPWSTR)DataBuf, DEFAULT_SCHEMA_CLASS_W,
  220. SIZEOF_DEFAULT_CLASS_W);
  221. }
  222. }
  223. else {
  224. BAIL_ON_FAILURE(hr);
  225. }
  226. }
  227. else {
  228. hr = _pSchema->ValidateClassName((LPWSTR)DataBuf);
  229. if (hr == E_ADS_SCHEMA_VIOLATION) {
  230. memcpy((LPWSTR)DataBuf, DEFAULT_SCHEMA_CLASS_W,
  231. SIZEOF_DEFAULT_CLASS_W);
  232. }
  233. }
  234. // Bump up the object count. The instantiation of this object
  235. // may fail; if we come into this function again, we do not want
  236. // to pick up the same object.
  237. //
  238. _dwObjectCurrentEntry++;
  239. hr = CIISGenObject::CreateGenericObject(
  240. _ADsPath,
  241. (LPWSTR)NameBuf,
  242. (LPWSTR)DataBuf,
  243. _Credentials,
  244. ADS_OBJECT_BOUND,
  245. IID_IDispatch,
  246. (void **)ppDispatch
  247. );
  248. BAIL_ON_FAILURE(hr);
  249. error:
  250. if (_pAdminBase && hObjHandle) {
  251. CloseAdminBaseKey(_pAdminBase, hObjHandle);
  252. }
  253. //
  254. // GetTree returns only S_FALSE
  255. //
  256. if (FAILED(hr)) {
  257. hr = S_FALSE;
  258. }
  259. RRETURN(hr);
  260. }
  261. //+---------------------------------------------------------------------------
  262. //
  263. // Function: CIISTreeEnum::Next
  264. //
  265. // Synopsis: Returns cElements number of requested NetOle objects in the
  266. // array supplied in pvar.
  267. //
  268. // Arguments: [cElements] -- The number of elements requested by client
  269. // [pvar] -- ptr to array of VARIANTs to for return objects
  270. // [pcElementFetched] -- if non-NULL, then number of elements
  271. // -- actually returned is placed here
  272. //
  273. // Returns: HRESULT -- S_OK if number of elements requested are returned
  274. // -- S_FALSE if number of elements is < requested
  275. //
  276. // Modifies:
  277. //
  278. // History:
  279. //
  280. //----------------------------------------------------------------------------
  281. STDMETHODIMP
  282. CIISTreeEnum::Next(
  283. ULONG cElements,
  284. VARIANT FAR* pvar,
  285. ULONG FAR* pcElementFetched
  286. )
  287. {
  288. ULONG cElementFetched = 0;
  289. HRESULT hr = S_OK;
  290. hr = EnumGenericObjects(
  291. cElements,
  292. pvar,
  293. &cElementFetched
  294. );
  295. if (pcElementFetched) {
  296. *pcElementFetched = cElementFetched;
  297. }
  298. RRETURN(hr);
  299. }