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.

502 lines
11 KiB

  1. /*++
  2. Copyright (c) 1997 Microsoft Corporation
  3. Module Name:
  4. urlzone.cxx
  5. Abstract:
  6. Glue layer to zone security manager, now residing in urlmon.dll
  7. Author:
  8. Rajeev Dujari (rajeevd) 02-Aug-1997
  9. Contents:
  10. UrlZonesAttach
  11. UrlZonesDetach
  12. GetCredPolicy
  13. --*/
  14. #include <wininetp.h>
  15. #include "urlmon.h"
  16. //
  17. // prototypes
  18. //
  19. typedef HRESULT (*PFNCREATESECMGR)(IServiceProvider * pSP, IInternetSecurityManager **ppSM, DWORD dwReserved);
  20. typedef HRESULT (*PFNCREATEZONEMGR)(IServiceProvider * pSP, IInternetZoneManager **ppZM, DWORD dwReserved);
  21. //
  22. // globals
  23. //
  24. IInternetSecurityManager* g_pSecMgr = NULL;
  25. IInternetZoneManager* g_pZoneMgr = NULL;
  26. static BOOL g_bAttemptedInit = FALSE;
  27. static HINSTANCE g_hInstUrlMon = NULL;
  28. static PFNCREATESECMGR g_pfnCreateSecMgr = NULL;
  29. static PFNCREATEZONEMGR g_pfnCreateZoneMgr = NULL;
  30. //
  31. // Handy class which uses a stack buffer if possible, otherwise allocates.
  32. //
  33. struct FlexBuf
  34. {
  35. BYTE Buf[512];
  36. LPBYTE pbBuf;
  37. FlexBuf()
  38. {
  39. pbBuf = NULL;
  40. }
  41. ~FlexBuf()
  42. {
  43. if (pbBuf != NULL) {
  44. delete [] pbBuf;
  45. }
  46. }
  47. LPBYTE GetPtr (DWORD cbBuf)
  48. {
  49. if (cbBuf < sizeof(Buf))
  50. return Buf;
  51. pbBuf = new BYTE [cbBuf];
  52. return pbBuf;
  53. }
  54. };
  55. struct UnicodeBuf : public FlexBuf
  56. {
  57. LPWSTR Convert (LPCSTR pszUrl)
  58. {
  59. DWORD cbUrl = lstrlenA (pszUrl) + 1;
  60. LPWSTR pwszUrl = (LPWSTR) GetPtr (sizeof(WCHAR) * cbUrl);
  61. if (!pwszUrl)
  62. return NULL;
  63. MultiByteToWideChar
  64. (CP_ACP, 0, pszUrl, cbUrl, pwszUrl, cbUrl);
  65. return pwszUrl;
  66. }
  67. };
  68. //
  69. // Dynaload urlmon and create security manager object on demand.
  70. //
  71. BOOL UrlZonesAttach (void)
  72. {
  73. EnterCriticalSection(&ZoneMgrCritSec);
  74. BOOL bRet = FALSE;
  75. HRESULT hr;
  76. if (g_bAttemptedInit)
  77. {
  78. bRet = (g_pSecMgr != NULL && g_pZoneMgr != NULL);
  79. goto End;
  80. }
  81. g_bAttemptedInit = TRUE;
  82. g_hInstUrlMon = LoadLibraryA(URLMON_DLL);
  83. if (!g_hInstUrlMon)
  84. {
  85. bRet = FALSE;
  86. goto End;
  87. }
  88. g_pfnCreateSecMgr = (PFNCREATESECMGR)
  89. GetProcAddress(g_hInstUrlMon, "CoInternetCreateSecurityManager");
  90. if (!g_pfnCreateSecMgr)
  91. {
  92. bRet = FALSE;
  93. goto End;
  94. }
  95. g_pfnCreateZoneMgr = (PFNCREATEZONEMGR)
  96. GetProcAddress(g_hInstUrlMon, "CoInternetCreateZoneManager");
  97. if (!g_pfnCreateZoneMgr)
  98. {
  99. bRet = FALSE;
  100. goto End;
  101. }
  102. hr = (*g_pfnCreateSecMgr)(NULL, &g_pSecMgr, NULL);
  103. if( hr != S_OK )
  104. {
  105. bRet = FALSE;
  106. goto End;
  107. }
  108. hr = (*g_pfnCreateZoneMgr)(NULL, &g_pZoneMgr, NULL);
  109. bRet = (hr == S_OK);
  110. End:
  111. LeaveCriticalSection(&ZoneMgrCritSec);
  112. return bRet;
  113. }
  114. //
  115. // Clean up upon process detach.
  116. //
  117. STDAPI_(void) UrlZonesDetach (void)
  118. {
  119. EnterCriticalSection(&ZoneMgrCritSec);
  120. if (g_pSecMgr)
  121. {
  122. g_pSecMgr->Release();
  123. g_pSecMgr = NULL;
  124. }
  125. if (g_pZoneMgr)
  126. {
  127. g_pZoneMgr->Release();
  128. g_pZoneMgr = NULL;
  129. }
  130. if (g_hInstUrlMon)
  131. {
  132. FreeLibrary(g_hInstUrlMon);
  133. g_hInstUrlMon = NULL;
  134. }
  135. LeaveCriticalSection(&ZoneMgrCritSec);
  136. }
  137. extern "C" DWORD GetZoneFromUrl(LPCSTR pszUrl);
  138. DWORD GetZoneFromUrl(LPCSTR pszUrl)
  139. {
  140. DWORD dwZone;
  141. dwZone = URLZONE_UNTRUSTED; // null URL indicates restricted zone.
  142. UnicodeBuf ub;
  143. EnterCriticalSection(&ZoneMgrCritSec);
  144. if (!g_pSecMgr && !UrlZonesAttach())
  145. goto err;
  146. LPWSTR pwszUrl;
  147. if (!pszUrl)
  148. pwszUrl = NULL;
  149. else
  150. {
  151. pwszUrl = ub.Convert (pszUrl);
  152. if (!pwszUrl)
  153. goto err;
  154. }
  155. if (pszUrl)
  156. {
  157. // Otherwise determine the zone for this URL.
  158. g_pSecMgr->MapUrlToZone (pwszUrl, &dwZone, 0);
  159. }
  160. err:
  161. LeaveCriticalSection(&ZoneMgrCritSec);
  162. return dwZone;
  163. }
  164. //
  165. // Routine to get the Routine to indicate whether ntlm logon credential is allowed.
  166. //
  167. DWORD GetCredPolicy (LPSTR pszUrl)
  168. {
  169. HRESULT hr;
  170. DWORD dwPolicy;
  171. UnicodeBuf ub;
  172. EnterCriticalSection(&ZoneMgrCritSec);
  173. if (!UrlZonesAttach())
  174. goto err;
  175. LPWSTR pwszUrl;
  176. if (!pszUrl)
  177. pwszUrl = NULL;
  178. else
  179. {
  180. pwszUrl = ub.Convert (pszUrl);
  181. if (!pwszUrl)
  182. goto err;
  183. }
  184. hr = g_pSecMgr->ProcessUrlAction (pwszUrl, URLACTION_CREDENTIALS_USE,
  185. (LPBYTE) &dwPolicy, sizeof(dwPolicy), NULL, 0, PUAF_NOUI, 0);
  186. // Resolve the ambiguous "Prompt if Intranet zone policy".
  187. if (dwPolicy == URLPOLICY_CREDENTIALS_CONDITIONAL_PROMPT)
  188. {
  189. DWORD dwZone;
  190. dwZone = URLZONE_UNTRUSTED; // null URL indicates restricted zone.
  191. if (pszUrl)
  192. {
  193. // Otherwise determine the zone for this URL.
  194. hr = g_pSecMgr->MapUrlToZone (pwszUrl, &dwZone, 0);
  195. if (hr != S_OK)
  196. goto err;
  197. }
  198. if (dwZone == URLZONE_INTRANET)
  199. dwPolicy = URLPOLICY_CREDENTIALS_SILENT_LOGON_OK;
  200. else
  201. dwPolicy = URLPOLICY_CREDENTIALS_MUST_PROMPT_USER;
  202. }
  203. LeaveCriticalSection(&ZoneMgrCritSec);
  204. return dwPolicy;
  205. err:
  206. INET_ASSERT (FALSE);
  207. LeaveCriticalSection(&ZoneMgrCritSec);
  208. return URLPOLICY_CREDENTIALS_MUST_PROMPT_USER;
  209. }
  210. /*
  211. Main-switch for the cookie feature has 3 states.
  212. 1. ALLOW: all cookies are accepted/replayed (including leashed ones)
  213. 2. QUERY: received cookies are subject to P3P evaluation,
  214. leashed cookies are not replayed
  215. 3. DISALLOW:no cookies are accepted/replayed.
  216. */
  217. DWORD GetCookieMainSwitch(DWORD dwZone) {
  218. DWORD dwPolicy = URLPOLICY_DISALLOW;
  219. if (!UrlZonesAttach())
  220. return dwPolicy;
  221. EnterCriticalSection(&ZoneMgrCritSec);
  222. HRESULT hr = g_pZoneMgr->GetZoneActionPolicy(dwZone, URLACTION_COOKIES_ENABLED,
  223. (LPBYTE)&dwPolicy, sizeof(dwPolicy),
  224. URLZONEREG_DEFAULT);
  225. LeaveCriticalSection(&ZoneMgrCritSec);
  226. return SUCCEEDED(hr) ? dwPolicy : URLPOLICY_ALLOW;
  227. }
  228. DWORD GetCookieMainSwitch(LPCSTR pszURL) {
  229. return GetCookieMainSwitch(GetZoneFromUrl(pszURL));
  230. }
  231. DWORD GetCookiePolicy (LPCSTR pszUrl, DWORD dwUrlAction, BOOL fRestricted)
  232. {
  233. if (GlobalSuppressCookiesPolicy)
  234. {
  235. return URLPOLICY_ALLOW;
  236. }
  237. EnterCriticalSection(&ZoneMgrCritSec);
  238. UnicodeBuf ub;
  239. DWORD dwCP;
  240. if (!UrlZonesAttach())
  241. goto err;
  242. // Convert to unicode.
  243. LPWSTR pwszUrl;
  244. pwszUrl = ub.Convert (pszUrl);
  245. if (!pwszUrl)
  246. goto err;
  247. DWORD dwPolicy;
  248. HRESULT hr;
  249. DWORD dwFlags;
  250. dwFlags = PUAF_NOUI;
  251. if (fRestricted)
  252. dwFlags |= PUAF_ENFORCERESTRICTED;
  253. hr = g_pSecMgr->ProcessUrlAction (pwszUrl, dwUrlAction,
  254. (LPBYTE) &dwPolicy, sizeof(dwPolicy), NULL, 0, dwFlags, 0);
  255. if (!SUCCEEDED(hr) )
  256. goto err;
  257. dwCP = GetUrlPolicyPermissions(dwPolicy);
  258. LeaveCriticalSection(&ZoneMgrCritSec);
  259. return dwCP;
  260. err:
  261. LeaveCriticalSection(&ZoneMgrCritSec);
  262. INET_ASSERT (FALSE);
  263. return URLPOLICY_QUERY;
  264. }
  265. DWORD GetClientCertPromptPolicy (LPCSTR pszUrl, BOOL fRestricted /* = FALSE */)
  266. {
  267. EnterCriticalSection(&ZoneMgrCritSec);
  268. UnicodeBuf ub;
  269. DWORD dwCP;
  270. DWORD dwUrlAction = URLACTION_CLIENT_CERT_PROMPT;
  271. DWORD dwFlags;
  272. if (!UrlZonesAttach())
  273. goto err;
  274. // Convert to unicode.
  275. LPWSTR pwszUrl;
  276. pwszUrl = ub.Convert (pszUrl);
  277. if (!pwszUrl)
  278. goto err;
  279. DWORD dwPolicy;
  280. dwFlags = PUAF_NOUI;
  281. if (fRestricted)
  282. dwFlags |= PUAF_ENFORCERESTRICTED;
  283. HRESULT hr;
  284. hr = g_pSecMgr->ProcessUrlAction (pwszUrl, dwUrlAction,
  285. (LPBYTE) &dwPolicy, sizeof(dwPolicy), NULL, 0, dwFlags, 0);
  286. if (!SUCCEEDED(hr) )
  287. goto err;
  288. dwCP = GetUrlPolicyPermissions(dwPolicy);
  289. LeaveCriticalSection(&ZoneMgrCritSec);
  290. return dwCP;
  291. err:
  292. LeaveCriticalSection(&ZoneMgrCritSec);
  293. INET_ASSERT (FALSE);
  294. return URLPOLICY_QUERY;
  295. }
  296. VOID SetStopWarning( LPCSTR pszUrl, DWORD dwPolicy, DWORD dwUrlAction)
  297. {
  298. EnterCriticalSection(&ZoneMgrCritSec);
  299. UnicodeBuf ub;
  300. ZONEATTRIBUTES za = {0};
  301. if (!UrlZonesAttach())
  302. goto err;
  303. // Convert to unicode.
  304. LPWSTR pwszUrl;
  305. pwszUrl = ub.Convert (pszUrl);
  306. if (!pwszUrl)
  307. goto err;
  308. HRESULT hr;
  309. DWORD dwZone;
  310. hr = g_pSecMgr->MapUrlToZone(pwszUrl, &dwZone, 0);
  311. if (!SUCCEEDED(hr) )
  312. goto err;
  313. DWORD dwZonePolicy;
  314. hr = g_pZoneMgr->GetZoneActionPolicy(
  315. dwZone,
  316. dwUrlAction,
  317. (LPBYTE)&dwZonePolicy,
  318. sizeof(dwZonePolicy),
  319. URLZONEREG_DEFAULT );
  320. if (!SUCCEEDED(hr) )
  321. goto err;
  322. // set the policy back with passed value
  323. SetUrlPolicyPermissions(dwZonePolicy, dwPolicy);
  324. hr = g_pZoneMgr->SetZoneActionPolicy(
  325. dwZone,
  326. dwUrlAction,
  327. (LPBYTE) &dwZonePolicy,
  328. sizeof(dwZonePolicy),
  329. URLZONEREG_DEFAULT );
  330. if (!SUCCEEDED(hr) )
  331. goto err;
  332. // change the generic zone setting to 'custom' now we've changed something
  333. za.cbSize = sizeof(ZONEATTRIBUTES);
  334. g_pZoneMgr->GetZoneAttributes(dwZone, &za);
  335. za.dwTemplateCurrentLevel = URLTEMPLATE_CUSTOM;
  336. g_pZoneMgr->SetZoneAttributes(dwZone, &za);
  337. err:
  338. LeaveCriticalSection(&ZoneMgrCritSec);
  339. return;
  340. }
  341. //
  342. // Set and query no cookies mode
  343. //
  344. BOOL IsNoCookies(DWORD dwZone)
  345. {
  346. BOOL fNoCookies = FALSE;
  347. HRESULT hr;
  348. DWORD dwZonePolicy;
  349. EnterCriticalSection(&ZoneMgrCritSec);
  350. if (!UrlZonesAttach())
  351. goto exit;
  352. hr = g_pZoneMgr->GetZoneActionPolicy(
  353. dwZone,
  354. URLACTION_COOKIES_ENABLED,
  355. (LPBYTE)&dwZonePolicy,
  356. sizeof(dwZonePolicy),
  357. URLZONEREG_DEFAULT );
  358. if(SUCCEEDED(hr))
  359. {
  360. dwZonePolicy = GetUrlPolicyPermissions(dwZonePolicy);
  361. if(URLPOLICY_DISALLOW == dwZonePolicy)
  362. {
  363. fNoCookies = TRUE;
  364. }
  365. }
  366. exit:
  367. LeaveCriticalSection(&ZoneMgrCritSec);
  368. return fNoCookies;
  369. }
  370. void SetNoCookies(DWORD dwZone, DWORD dwNewPolicy)
  371. {
  372. DWORD dwZonePolicy;
  373. HRESULT hr;
  374. EnterCriticalSection(&ZoneMgrCritSec);
  375. if (!UrlZonesAttach())
  376. goto exit;
  377. hr = g_pZoneMgr->GetZoneActionPolicy(
  378. dwZone,
  379. URLACTION_COOKIES_ENABLED,
  380. (LPBYTE)&dwZonePolicy,
  381. sizeof(dwZonePolicy),
  382. URLZONEREG_DEFAULT );
  383. if(SUCCEEDED(hr))
  384. {
  385. SetUrlPolicyPermissions(dwZonePolicy, dwNewPolicy);
  386. g_pZoneMgr->SetZoneActionPolicy(
  387. dwZone,
  388. URLACTION_COOKIES_ENABLED,
  389. (LPBYTE)&dwZonePolicy,
  390. sizeof(dwZonePolicy),
  391. URLZONEREG_DEFAULT );
  392. }
  393. exit:
  394. LeaveCriticalSection(&ZoneMgrCritSec);
  395. }