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.

951 lines
35 KiB

  1. //+----------------------------------------------------------------------------
  2. //
  3. // File: cmproxy.cpp
  4. //
  5. // Module: CMPROXY.DLL (TOOL)
  6. //
  7. // Synopsis: Main source for IE proxy setting connect action
  8. //
  9. // Copyright (c) 1999 Microsoft Corporation
  10. //
  11. // Author: quintinb Created 10/27/99
  12. //
  13. //+----------------------------------------------------------------------------
  14. #include "pch.h"
  15. const CHAR* const c_pszInternetSettingsPath = "Software\\Microsoft\\Windows\\CurrentVersion\\Internet Settings";
  16. const CHAR* const c_pszProxyEnable = "ProxyEnable";
  17. const CHAR* const c_pszProxyServer = "ProxyServer";
  18. const CHAR* const c_pszProxyOverride = "ProxyOverride";
  19. const CHAR* const c_pszManualProxySection = "Manual Proxy";
  20. const CHAR* const c_pszAutoProxySection = "Automatic Proxy";
  21. const CHAR* const c_pszAutoConfigScript = "AutoConfigScript";
  22. const CHAR* const c_pszAutoProxyEnable = "AutoProxyEnable";
  23. const CHAR* const c_pszAutoConfigScriptEnable = "AutoConfigScriptEnable";
  24. const CHAR* const c_pszUseVpnName = "UseVpnName";
  25. const CHAR* const c_pszEmpty = "";
  26. //
  27. // Typedefs and Function Pointers for the Wininet APIs that we use.
  28. //
  29. typedef BOOL (WINAPI* pfnInternetQueryOptionSpec)(HINTERNET, DWORD, LPVOID, LPDWORD);
  30. typedef BOOL (WINAPI* pfnInternetSetOptionSpec)(HINTERNET, DWORD, LPVOID, DWORD);
  31. pfnInternetQueryOptionSpec g_pfnInternetQueryOption = NULL;
  32. pfnInternetSetOptionSpec g_pfnInternetSetOption = NULL;
  33. //+----------------------------------------------------------------------------
  34. //
  35. // Function: SetIE5ProxySettings
  36. //
  37. // Synopsis: This function sets the IE5, per connection proxy settings using
  38. // the given connection, enabled value, proxy server, and override
  39. // settings.
  40. //
  41. // Arguments: LPSTR pszConnection - Connection name to set the proxy settings for
  42. // BOOL bManualProxy - whether the manual proxy is enabled or not
  43. // BOOL bAutomaticProxy - whether the auto proxy detection is enabled
  44. // BOOL bAutoConfigScript - whether an auto config script should be used
  45. // LPSTR pszProxyServer - proxy server name in the proxyserver:port format
  46. // LPSTR pszProxyOverride - a semi-colon seperated list of
  47. // realms to bypass the proxy for
  48. // LPSTR pszAutoConfigScript - auto config URL
  49. //
  50. // Returns: HRESULT - Standard COM return codes
  51. //
  52. // History: quintinb Created 10/27/99
  53. //
  54. //+----------------------------------------------------------------------------
  55. HRESULT SetIE5ProxySettings(LPSTR pszConnection, BOOL bManualProxy, BOOL bAutomaticProxy, BOOL bAutoConfigScript,
  56. LPSTR pszProxyServer, LPSTR pszProxyOverride, LPSTR pszAutoConfigScript)
  57. {
  58. //
  59. // Check Inputs, note allow pszConnection to be NULL (to set the LAN connection)
  60. //
  61. if ((NULL == g_pfnInternetSetOption) || (NULL == pszProxyServer) ||
  62. (NULL == pszProxyOverride) || (NULL == pszAutoConfigScript))
  63. {
  64. return E_INVALIDARG;
  65. }
  66. HRESULT hr = S_OK;
  67. INTERNET_PER_CONN_OPTION_LIST PerConnOptionList;
  68. DWORD dwSize = sizeof(PerConnOptionList);
  69. PerConnOptionList.dwSize = sizeof(PerConnOptionList);
  70. PerConnOptionList.pszConnection = pszConnection;
  71. PerConnOptionList.dwOptionCount = 4;
  72. PerConnOptionList.dwOptionError = 0;
  73. PerConnOptionList.pOptions = (INTERNET_PER_CONN_OPTION*)CmMalloc(4*sizeof(INTERNET_PER_CONN_OPTION));
  74. if(NULL == PerConnOptionList.pOptions)
  75. {
  76. return HRESULT_FROM_WIN32(ERROR_NOT_ENOUGH_MEMORY);
  77. }
  78. //
  79. // set flags
  80. //
  81. PerConnOptionList.pOptions[0].dwOption = INTERNET_PER_CONN_FLAGS;
  82. PerConnOptionList.pOptions[0].Value.dwValue = PROXY_TYPE_DIRECT;
  83. if (bManualProxy)
  84. {
  85. PerConnOptionList.pOptions[0].Value.dwValue |= PROXY_TYPE_PROXY;
  86. }
  87. if (bAutomaticProxy)
  88. {
  89. PerConnOptionList.pOptions[0].Value.dwValue |= PROXY_TYPE_AUTO_DETECT;
  90. }
  91. if (bAutoConfigScript)
  92. {
  93. PerConnOptionList.pOptions[0].Value.dwValue |= PROXY_TYPE_AUTO_PROXY_URL;
  94. }
  95. //
  96. // set proxy name
  97. //
  98. PerConnOptionList.pOptions[1].dwOption = INTERNET_PER_CONN_PROXY_SERVER;
  99. PerConnOptionList.pOptions[1].Value.pszValue = pszProxyServer;
  100. //
  101. // set proxy override
  102. //
  103. PerConnOptionList.pOptions[2].dwOption = INTERNET_PER_CONN_PROXY_BYPASS;
  104. PerConnOptionList.pOptions[2].Value.pszValue = pszProxyOverride;
  105. //
  106. // set auto config URL
  107. //
  108. PerConnOptionList.pOptions[3].dwOption = INTERNET_PER_CONN_AUTOCONFIG_URL;
  109. PerConnOptionList.pOptions[3].Value.pszValue = pszAutoConfigScript;
  110. //
  111. // tell wininet
  112. //
  113. if (!g_pfnInternetSetOption(NULL, INTERNET_OPTION_PER_CONNECTION_OPTION, &PerConnOptionList, dwSize))
  114. {
  115. hr = HRESULT_FROM_WIN32(GetLastError());
  116. }
  117. CmFree(PerConnOptionList.pOptions);
  118. return hr;
  119. }
  120. //+----------------------------------------------------------------------------
  121. //
  122. // Function: SetIE4ProxySettings
  123. //
  124. // Synopsis: This function sets the IE4 proxy settings (global to a machine) using
  125. // the given connection, enabled value, proxy server, and override
  126. // settings.
  127. //
  128. // Arguments: LPSTR pszConnection - ignored (exists to have same prototype as IE5 version)
  129. // BOOL bManualProxy - whether the manual proxy is enabled or not
  130. // BOOL bAutomaticProxy - ignored (exists to have same prototype as IE5 version)
  131. // BOOL bAutoConfigScript - ignored (exists to have same prototype as IE5 version)
  132. // LPSTR pszProxyServer - proxy server name in the proxyserver:port format
  133. // LPSTR pszProxyOverride - a semi-colon seperated list of
  134. // realms to bypass the proxy for
  135. // LPSTR pszAutoConfigScript - ignored (exists to have same prototype as IE5 version)
  136. //
  137. // Returns: HRESULT - Standard COM return codes
  138. //
  139. // History: quintinb Created 10/27/99
  140. //
  141. //+----------------------------------------------------------------------------
  142. HRESULT SetIE4ProxySettings(LPSTR pszConnection, BOOL bManualProxy, BOOL bAutomaticProxy, BOOL bAutoConfigScript,
  143. LPSTR pszProxyServer, LPSTR pszProxyOverride, LPSTR pszAutoConfigScript)
  144. {
  145. //
  146. // Check Inputs, note that we don't allow the strings to be NULL but they could
  147. // be empty. Also note that pszConnection is ignored because IE4 proxy settings are global.
  148. //
  149. if ((NULL == pszProxyServer) || (NULL == pszProxyOverride))
  150. {
  151. return E_INVALIDARG;
  152. }
  153. DWORD dwTemp;
  154. HKEY hKey = NULL;
  155. HRESULT hr = S_OK;
  156. //
  157. // Now Create/Open the Internet Settings key
  158. //
  159. LONG lResult = RegCreateKeyEx(HKEY_CURRENT_USER, c_pszInternetSettingsPath, 0, NULL,
  160. REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, &hKey, &dwTemp);
  161. hr = HRESULT_FROM_WIN32(lResult);
  162. if (SUCCEEDED(hr))
  163. {
  164. //
  165. // Set the proxy values
  166. //
  167. dwTemp = bManualProxy ? 1 : 0; // use a true 1 or 0 value.
  168. lResult = RegSetValueEx(hKey, c_pszProxyEnable, 0, REG_DWORD, (CONST BYTE*)&dwTemp, sizeof(DWORD));
  169. hr = HRESULT_FROM_WIN32(lResult);
  170. if (SUCCEEDED(hr))
  171. {
  172. lResult = RegSetValueEx(hKey, c_pszProxyServer, 0, REG_SZ, (CONST BYTE*)pszProxyServer, lstrlen(pszProxyServer)+1);
  173. hr = HRESULT_FROM_WIN32(lResult);
  174. if (SUCCEEDED(hr))
  175. {
  176. lResult = RegSetValueEx(hKey, c_pszProxyOverride, 0, REG_SZ, (CONST BYTE*)pszProxyOverride, lstrlen(pszProxyOverride)+1);
  177. hr = HRESULT_FROM_WIN32(lResult);
  178. }
  179. }
  180. }
  181. return hr;
  182. }
  183. //+----------------------------------------------------------------------------
  184. //
  185. // Function: GetIE5ProxySettings
  186. //
  187. // Synopsis: Gets the IE5, per connection, proxy settings for the given connection.
  188. // Please note that the strings allocated for the proxy server and the
  189. // proxy override values must be freed by the caller.
  190. //
  191. // Arguments: LPSTR pszConnection - connection name to get the proxy settings for
  192. // LPBOOL pbManualProxy - bool pointer to hold whether the manual
  193. // proxy is enabled or not
  194. // LPBOOL pbAutomaticProxy - bool pointer to hold whether automatic
  195. // proxy detection is enabled or not
  196. // LPBOOL pbAutoConfigScript - bool pointer to hold whether an auto
  197. // config script should be used or not
  198. // LPSTR* ppszProxyServer - string pointer to hold the retrieved
  199. // proxy server string
  200. // LPSTR* ppszProxyOverride - string pointer to hold the retrieved
  201. // proxy server string
  202. // LPSTR* ppszAutoConfigScript - string pointer to hold the retrieved
  203. // auto config script
  204. //
  205. // Returns: HRESULT - Standard COM return codes
  206. //
  207. // History: quintinb Created 10/27/99
  208. //
  209. //+----------------------------------------------------------------------------
  210. HRESULT GetIE5ProxySettings(LPSTR pszConnection, LPBOOL pbManualProxy, LPBOOL pbAutomaticProxy, LPBOOL pbAutoConfigScript,
  211. LPSTR* ppszProxyServer, LPSTR* ppszProxyOverride, LPSTR* ppszAutoConfigScript)
  212. {
  213. //
  214. // Check Inputs, note that pszConnection can be NULL. It will set the LAN connection in that case.
  215. //
  216. if ((NULL == pbManualProxy) || (NULL == pbAutomaticProxy) || (NULL == pbAutoConfigScript) ||
  217. (NULL == ppszProxyServer) || (NULL == ppszProxyOverride) || (NULL == ppszAutoConfigScript) ||
  218. (NULL == g_pfnInternetQueryOption))
  219. {
  220. return E_INVALIDARG;
  221. }
  222. //
  223. // Zero the output params
  224. //
  225. *pbManualProxy = FALSE;
  226. *pbAutomaticProxy = FALSE;
  227. *pbAutoConfigScript = FALSE;
  228. *ppszProxyServer = CmStrCpyAlloc(c_pszEmpty);
  229. *ppszProxyOverride = CmStrCpyAlloc(c_pszEmpty);
  230. *ppszAutoConfigScript = CmStrCpyAlloc(c_pszEmpty);
  231. //
  232. // Setup the Option List Struct
  233. //
  234. HRESULT hr = S_OK;
  235. INTERNET_PER_CONN_OPTION_LIST PerConnOptionList;
  236. PerConnOptionList.dwSize = sizeof(PerConnOptionList);
  237. PerConnOptionList.pszConnection = pszConnection;
  238. PerConnOptionList.dwOptionError = 0;
  239. PerConnOptionList.dwOptionCount = 4;
  240. PerConnOptionList.pOptions = (INTERNET_PER_CONN_OPTION*)CmMalloc(4*sizeof(INTERNET_PER_CONN_OPTION));
  241. if(NULL == PerConnOptionList.pOptions)
  242. {
  243. return HRESULT_FROM_WIN32(ERROR_NOT_ENOUGH_MEMORY);
  244. }
  245. //
  246. // set flags we want info about
  247. //
  248. PerConnOptionList.pOptions[0].dwOption = INTERNET_PER_CONN_FLAGS;
  249. PerConnOptionList.pOptions[1].dwOption = INTERNET_PER_CONN_PROXY_SERVER;
  250. PerConnOptionList.pOptions[2].dwOption = INTERNET_PER_CONN_PROXY_BYPASS;
  251. PerConnOptionList.pOptions[3].dwOption = INTERNET_PER_CONN_AUTOCONFIG_URL;
  252. DWORD dwSize = sizeof(PerConnOptionList);
  253. //
  254. // Get the Options
  255. //
  256. if (!g_pfnInternetQueryOption(NULL, INTERNET_OPTION_PER_CONNECTION_OPTION, &PerConnOptionList, &dwSize))
  257. {
  258. hr = HRESULT_FROM_WIN32(GetLastError());
  259. }
  260. if (SUCCEEDED(hr))
  261. {
  262. //
  263. // Parse the returned options to find the options we are interested in
  264. //
  265. for (DWORD dwIndex=0; dwIndex < PerConnOptionList.dwOptionCount; dwIndex++)
  266. {
  267. switch(PerConnOptionList.pOptions[dwIndex].dwOption)
  268. {
  269. case INTERNET_PER_CONN_FLAGS:
  270. if (PROXY_TYPE_PROXY & PerConnOptionList.pOptions[dwIndex].Value.dwValue)
  271. {
  272. *pbManualProxy = TRUE;
  273. }
  274. if (PROXY_TYPE_AUTO_PROXY_URL & PerConnOptionList.pOptions[dwIndex].Value.dwValue)
  275. {
  276. *pbAutoConfigScript = TRUE;
  277. }
  278. if (PROXY_TYPE_AUTO_DETECT & PerConnOptionList.pOptions[dwIndex].Value.dwValue)
  279. {
  280. *pbAutomaticProxy = TRUE;
  281. }
  282. break;
  283. case INTERNET_PER_CONN_PROXY_SERVER:
  284. if (NULL != PerConnOptionList.pOptions[dwIndex].Value.pszValue)
  285. {
  286. CmFree(*ppszProxyServer);
  287. *ppszProxyServer = CmStrCpyAlloc(PerConnOptionList.pOptions[dwIndex].Value.pszValue);
  288. LocalFree(PerConnOptionList.pOptions[dwIndex].Value.pszValue);
  289. }
  290. break;
  291. case INTERNET_PER_CONN_PROXY_BYPASS:
  292. if (NULL != PerConnOptionList.pOptions[dwIndex].Value.pszValue)
  293. {
  294. CmFree(*ppszProxyOverride);
  295. *ppszProxyOverride = CmStrCpyAlloc(PerConnOptionList.pOptions[dwIndex].Value.pszValue);
  296. LocalFree(PerConnOptionList.pOptions[dwIndex].Value.pszValue);
  297. }
  298. break;
  299. case INTERNET_PER_CONN_AUTOCONFIG_URL:
  300. if (NULL != PerConnOptionList.pOptions[dwIndex].Value.pszValue)
  301. {
  302. CmFree(*ppszAutoConfigScript);
  303. *ppszAutoConfigScript = CmStrCpyAlloc(PerConnOptionList.pOptions[dwIndex].Value.pszValue);
  304. LocalFree(PerConnOptionList.pOptions[dwIndex].Value.pszValue);
  305. }
  306. break;
  307. default:
  308. break;
  309. }
  310. }
  311. CmFree(PerConnOptionList.pOptions);
  312. }
  313. return hr;
  314. }
  315. //+----------------------------------------------------------------------------
  316. //
  317. // Function: GetIE4ProxySettings
  318. //
  319. // Synopsis: Gets the IE4, per machine, proxy settings.
  320. // Please note that the strings allocated for the proxy server and the
  321. // proxy override values must be freed by the caller.
  322. //
  323. // Arguments: LPSTR pszConnection - ignored (exists for prototype consistency with the IE5 version)
  324. // LPBOOL pbManualProxy - bool pointer to hold whether the manual
  325. // proxy is enabled or not
  326. // LPBOOL pbAutomaticProxy - ignored (not supported by IE4)
  327. // LPBOOL pbAutoConfigScript - ignored (not supported by IE4)
  328. // LPSTR* ppszProxyServer - string pointer to hold the retrieved
  329. // proxy server string
  330. // LPSTR* ppszProxyOverride - string pointer to hold the retrieved
  331. // proxy server string
  332. // LPSTR* ppszAutoConfigScript - ignored (not supported by IE4)
  333. //
  334. // Returns: HRESULT - Standard COM return codes
  335. //
  336. // History: quintinb Created 10/27/99
  337. //
  338. //+----------------------------------------------------------------------------
  339. HRESULT GetIE4ProxySettings(LPSTR pszConnection, LPBOOL pbManualProxy, LPBOOL pbAutomaticProxy, LPBOOL pbAutoConfigScript,
  340. LPSTR* ppszProxyServer, LPSTR* ppszProxyOverride, LPSTR* ppszAutoConfigScript)
  341. {
  342. //
  343. // Check Inputs, note that we don't allow the pointers to be NULL but they could
  344. // be empty. Also note that pszConnection is ignored because IE4 proxy settings are global.
  345. //
  346. if ((NULL == pbManualProxy) || (NULL == ppszProxyServer) || (NULL == ppszProxyOverride))
  347. {
  348. return E_INVALIDARG;
  349. }
  350. DWORD dwTemp;
  351. DWORD dwSize;
  352. DWORD dwType;
  353. HKEY hKey = NULL;
  354. HRESULT hr = S_OK;
  355. //
  356. // Zero the output params
  357. //
  358. *pbManualProxy = FALSE;
  359. *pbAutomaticProxy = FALSE;
  360. *pbAutoConfigScript = FALSE;
  361. *ppszProxyServer = CmStrCpyAlloc(c_pszEmpty);
  362. *ppszProxyOverride = CmStrCpyAlloc(c_pszEmpty);
  363. *ppszAutoConfigScript = CmStrCpyAlloc(c_pszEmpty);
  364. //
  365. // Now Create/Open the Internet Settings key
  366. //
  367. LONG lResult = RegOpenKeyEx(HKEY_CURRENT_USER, c_pszInternetSettingsPath, 0, KEY_READ, &hKey);
  368. hr = HRESULT_FROM_WIN32(lResult);
  369. if (SUCCEEDED(hr))
  370. {
  371. //
  372. // get whether the proxy is enabled or not
  373. //
  374. dwSize = sizeof(DWORD);
  375. lResult = RegQueryValueEx(hKey, c_pszProxyEnable, 0, &dwType, (LPBYTE)pbManualProxy, &dwSize);
  376. hr = HRESULT_FROM_WIN32(lResult);
  377. if (SUCCEEDED(hr))
  378. {
  379. //
  380. // get the proxy server value
  381. //
  382. lResult = ERROR_INSUFFICIENT_BUFFER;
  383. dwSize = MAX_PATH;
  384. do
  385. {
  386. //
  387. // Alloc a Buffer
  388. //
  389. CmFree(*ppszProxyServer);
  390. *ppszProxyServer = (CHAR*)CmMalloc(dwSize);
  391. if (*ppszProxyServer)
  392. {
  393. lResult = RegQueryValueEx(hKey, c_pszProxyServer, 0, &dwType,
  394. (LPBYTE)*ppszProxyServer, &dwSize);
  395. }
  396. else
  397. {
  398. lResult = ERROR_NOT_ENOUGH_MEMORY;
  399. }
  400. hr = HRESULT_FROM_WIN32(lResult);
  401. dwSize = 2*dwSize;
  402. } while ((ERROR_INSUFFICIENT_BUFFER == lResult) && (dwSize < 1024*1024));
  403. if (SUCCEEDED(hr))
  404. {
  405. //
  406. // get the proxy override value
  407. //
  408. lResult = ERROR_INSUFFICIENT_BUFFER;
  409. dwSize = MAX_PATH;
  410. do
  411. {
  412. //
  413. // Alloc a Buffer
  414. //
  415. CmFree(*ppszProxyOverride);
  416. *ppszProxyOverride = (CHAR*)CmMalloc(dwSize);
  417. if (*ppszProxyOverride)
  418. {
  419. lResult = RegQueryValueEx(hKey, c_pszProxyOverride, 0, &dwType,
  420. (LPBYTE)*ppszProxyOverride, &dwSize);
  421. }
  422. else
  423. {
  424. lResult = ERROR_NOT_ENOUGH_MEMORY;
  425. }
  426. hr = HRESULT_FROM_WIN32(lResult);
  427. dwSize = 2*dwSize;
  428. } while ((ERROR_INSUFFICIENT_BUFFER == lResult) && (dwSize < 1024*1024));
  429. }
  430. }
  431. }
  432. else
  433. {
  434. if (ERROR_FILE_NOT_FOUND == lResult)
  435. {
  436. //
  437. // No Proxy settings to get.
  438. //
  439. hr = S_FALSE;
  440. }
  441. }
  442. return hr;
  443. }
  444. //+----------------------------------------------------------------------------
  445. //
  446. // Function: ReadProxySettingsFromFile
  447. //
  448. // Synopsis: Reads the proxy settings from the given proxy file and stores them
  449. // in the provided pointers. Please note that the buffers allocated
  450. // by GetString and stored in ppszProxyOverride, ppszProxyServer, and
  451. // ppszAutoConfigScript must be freed by the caller. Please see the above
  452. // format guide for specifics.
  453. //
  454. // Arguments: LPCSTR pszSourceFile - file to read the proxy settings from.
  455. // LPBOOL pbManualProxy - determines if the manual proxy is enabled or not
  456. // LPBOOL pbAutomaticProxy - determines if automatic proxy detection is enabled or not
  457. // LPBOOL pbAutoConfigScript - determines if an automatic config script should be used
  458. // LPSTR* ppszProxyServer - string pointer to hold the Proxy server value
  459. // (in server:port format)
  460. // LPSTR* ppszProxyOverride - string pointer to hold the Proxy override values
  461. // (a semi-colon seperated list)
  462. // LPSTR* ppszAutoConfigScript - URL for an automatic config script
  463. // LPBOOL pbUseVpnName - whether the alternate connectoid name should
  464. // be used (the VPN connectoid name)
  465. //
  466. // Returns: BOOL - TRUE if the settings were successfully read
  467. //
  468. // History: quintinb Created 10/27/99
  469. //
  470. //+----------------------------------------------------------------------------
  471. BOOL ReadProxySettingsFromFile(LPCSTR pszSourceFile, LPBOOL pbManualProxy, LPBOOL pbAutomaticProxy, LPBOOL pbAutoConfigScript,
  472. LPSTR* ppszProxyServer, LPSTR* ppszProxyOverride, LPSTR* ppszAutoConfigScript, LPBOOL pbUseVpnName)
  473. {
  474. //
  475. // Check input params
  476. //
  477. if ((NULL == ppszProxyOverride) || (NULL == ppszProxyServer) || (NULL == ppszAutoConfigScript) ||
  478. (NULL == pbAutomaticProxy) || (NULL == pbAutoConfigScript) || (NULL == pbManualProxy) ||
  479. (NULL == pbUseVpnName) || (NULL == pszSourceFile) || ('\0' == pszSourceFile[0]))
  480. {
  481. return FALSE;
  482. }
  483. //
  484. // Get the Manual proxy settings
  485. //
  486. *pbManualProxy = GetPrivateProfileInt(c_pszManualProxySection, c_pszProxyEnable, 0, pszSourceFile);
  487. GetString(c_pszManualProxySection, c_pszProxyServer, ppszProxyServer, pszSourceFile);
  488. if (NULL == *ppszProxyServer)
  489. {
  490. return FALSE;
  491. }
  492. GetString(c_pszManualProxySection, c_pszProxyOverride, ppszProxyOverride, pszSourceFile);
  493. if (NULL == *ppszProxyOverride)
  494. {
  495. return FALSE;
  496. }
  497. //
  498. // If this is a backup file, we will have the UseVpnName flag to tell us which connectoid name
  499. // is appropriate. Lets look it up. Note that we default to using the standard connectoid.
  500. //
  501. *pbUseVpnName = GetPrivateProfileInt(c_pszManualProxySection, c_pszUseVpnName, 0, pszSourceFile);
  502. //
  503. // Get the Auto proxy settings
  504. //
  505. *pbAutomaticProxy = GetPrivateProfileInt(c_pszAutoProxySection, c_pszAutoProxyEnable, 0, pszSourceFile); //"Automatically detect settings" checkbox
  506. *pbAutoConfigScript = GetPrivateProfileInt(c_pszAutoProxySection, c_pszAutoConfigScriptEnable, 0, pszSourceFile);//"Use automatic configuration script" checkbox
  507. GetString(c_pszAutoProxySection, c_pszAutoConfigScript, ppszAutoConfigScript, pszSourceFile);
  508. return TRUE;
  509. }
  510. //+----------------------------------------------------------------------------
  511. //
  512. // Function: WriteProxySettingsToFile
  513. //
  514. // Synopsis: Writes the specified settings to the given backup proxy filename.
  515. // Please see the above format guide for specifics.
  516. //
  517. // Arguments: LPCSTR pszBackupFile - backup file to write the current settings to
  518. // BOOL bManualProxy -- bool to tell if the manual proxy is enabled.
  519. // BOOL bAutomaticProxy -- bool to tell if auto proxy detection is enabled.
  520. // BOOL bAutoConfigScript -- bool to tell if an auto config
  521. // script should be used.
  522. // LPSTR pszProxyServer - proxy server string in server:port format
  523. // LPSTR pszProxyOverride - semi-colon seperated list of realms for
  524. // which the proxy server should be bypassed.
  525. // BOOL bUseVpnName - value to write to the UseVpnName file, see format doc above.
  526. //
  527. // Returns: BOOL - TRUE if the values were written successfully
  528. //
  529. // History: quintinb Created 10/27/99
  530. //
  531. //+----------------------------------------------------------------------------
  532. BOOL WriteProxySettingsToFile(LPCSTR pszBackupFile, BOOL bManualProxy, BOOL bAutomaticProxy, BOOL bAutoConfigScript,
  533. LPSTR pszProxyServer, LPSTR pszProxyOverride, LPSTR pszAutoConfigScript, BOOL bUseVpnName)
  534. {
  535. //
  536. // Check inputs
  537. //
  538. if ((NULL == pszBackupFile) || ('\0' == pszBackupFile[0]) || (NULL == pszProxyServer) ||
  539. (NULL == pszProxyOverride) || (NULL == pszAutoConfigScript))
  540. {
  541. return FALSE;
  542. }
  543. BOOL bReturn = TRUE;
  544. CHAR szTemp[MAX_PATH];
  545. //
  546. // Write the Manual Proxy Settings
  547. //
  548. wsprintf(szTemp, "%d", bManualProxy);
  549. if (!WritePrivateProfileString(c_pszManualProxySection, c_pszProxyEnable, szTemp, pszBackupFile))
  550. {
  551. CMTRACE1("CmProxy -- WriteProxySettingsToFile failed, GLE %d", GetLastError());
  552. bReturn = FALSE;
  553. }
  554. if (!WritePrivateProfileString(c_pszManualProxySection, c_pszProxyServer, pszProxyServer, pszBackupFile))
  555. {
  556. CMTRACE1("CmProxy -- WriteProxySettingsToFile failed, GLE %d", GetLastError());
  557. bReturn = FALSE;
  558. }
  559. if (!WritePrivateProfileString(c_pszManualProxySection, c_pszProxyOverride, pszProxyOverride, pszBackupFile))
  560. {
  561. CMTRACE1("CmProxy -- WriteProxySettingsToFile failed, GLE %d", GetLastError());
  562. bReturn = FALSE;
  563. }
  564. wsprintf(szTemp, "%d", bUseVpnName);
  565. if (!WritePrivateProfileString(c_pszManualProxySection, c_pszUseVpnName, szTemp, pszBackupFile))
  566. {
  567. CMTRACE1("CmProxy -- WriteProxySettingsToFile failed, GLE %d", GetLastError());
  568. bReturn = FALSE;
  569. }
  570. //
  571. // Write the Automatic Proxy Settings
  572. //
  573. wsprintf(szTemp, "%d", bAutomaticProxy);
  574. if (!WritePrivateProfileString(c_pszAutoProxySection, c_pszAutoProxyEnable, szTemp, pszBackupFile))
  575. {
  576. CMTRACE1("CmProxy -- WriteProxySettingsToFile failed, GLE %d", GetLastError());
  577. bReturn = FALSE;
  578. }
  579. wsprintf(szTemp, "%d", bAutoConfigScript);
  580. if (!WritePrivateProfileString(c_pszAutoProxySection, c_pszAutoConfigScriptEnable, szTemp, pszBackupFile))
  581. {
  582. CMTRACE1("CmProxy -- WriteProxySettingsToFile failed, GLE %d", GetLastError());
  583. bReturn = FALSE;
  584. }
  585. if (!WritePrivateProfileString(c_pszAutoProxySection, c_pszAutoConfigScript, pszAutoConfigScript, pszBackupFile))
  586. {
  587. CMTRACE1("CmProxy -- WriteProxySettingsToFile failed, GLE %d", GetLastError());
  588. bReturn = FALSE;
  589. }
  590. return bReturn;
  591. }
  592. //+----------------------------------------------------------------------------
  593. //
  594. // Function: SetProxy
  595. //
  596. // Synopsis: Proxy entry point for setting the IE4 and IE5 style proxies. Since
  597. // this is a Connection Manager connect action it uses the CM connect
  598. // action format (see CMAK docs for more info). Thus the parameters
  599. // to the dll are passed via a string which contains parameters (see the
  600. // cmproxy spec for a list of the parameter values).
  601. //
  602. // Arguments: HWND hWnd - Window handle of caller
  603. // HINSTANCE hInst - Instance handle of caller
  604. // LPSTR pszArgs - Argument string
  605. // int nShow - Unused
  606. //
  607. // Returns: DWORD WINAPI - Error code
  608. //
  609. // History: quintinb Created 10/27/99
  610. //
  611. //+----------------------------------------------------------------------------
  612. HRESULT WINAPI SetProxy(HWND hWnd, HINSTANCE hInst, LPSTR pszArgs, int nShow)
  613. {
  614. //
  615. // First figure out if we have IE4 or IE5 available.
  616. //
  617. typedef HRESULT (WINAPI *pfnSetProxySettings)(LPSTR, BOOL, BOOL, BOOL, LPSTR, LPSTR, LPSTR);
  618. typedef HRESULT (WINAPI *pfnGetProxySettings)(LPSTR, LPBOOL, LPBOOL, LPBOOL, LPSTR*, LPSTR*, LPSTR*);
  619. pfnSetProxySettings SetProxySettings = NULL;
  620. pfnGetProxySettings GetProxySettings = NULL;
  621. BOOL bIE5 = FALSE;
  622. BOOL bManualProxy;
  623. BOOL bAutomaticProxy;
  624. BOOL bAutoConfigScript;
  625. BOOL bUseVpnName = FALSE;
  626. DLLVERSIONINFO VersionInfo;
  627. HINSTANCE hWinInet = NULL;
  628. LPSTR pszProxyServer = NULL;
  629. LPSTR pszProxyOverride = NULL;
  630. LPSTR pszAutoConfigScript = NULL;
  631. LPSTR pszSourceFile = NULL;
  632. LPSTR pszBackupFile = NULL;
  633. LPSTR pszConnectionName = NULL;
  634. LPSTR pszProfileDirPath = NULL;
  635. LPSTR pszAltName = NULL;
  636. LPSTR* CmArgV = NULL;
  637. if (SUCCEEDED(GetBrowserVersion(&VersionInfo)))
  638. {
  639. if (5 <= VersionInfo.dwMajorVersion)
  640. {
  641. //
  642. // Set the function pointers to use the IE5 versions of the functions
  643. //
  644. SetProxySettings = SetIE5ProxySettings;
  645. GetProxySettings = GetIE5ProxySettings;
  646. bIE5 = TRUE;
  647. }
  648. else if ((4 == VersionInfo.dwMajorVersion) &&
  649. ((71 == VersionInfo.dwMinorVersion) || (72 == VersionInfo.dwMinorVersion)))
  650. {
  651. //
  652. // Use the IE4 version of the proxy functions
  653. //
  654. SetProxySettings = SetIE4ProxySettings;
  655. GetProxySettings = GetIE4ProxySettings;
  656. }
  657. else
  658. {
  659. //
  660. // We don't work with IE versions less than 4 so lets return right here
  661. // without setting anything.
  662. //
  663. CMTRACE("CMPROXY--Unable to set the proxy settings because of insufficient IE version.");
  664. return TRUE;
  665. }
  666. //
  667. // If we have IE5, then we need to load wininet.dll.
  668. //
  669. if (bIE5)
  670. {
  671. hWinInet = LoadLibrary("wininet.dll");
  672. if (hWinInet)
  673. {
  674. //
  675. // Okay, lets get the procedure addresses for InternetSetOption and InternetQueryOption
  676. //
  677. g_pfnInternetQueryOption = (pfnInternetQueryOptionSpec)GetProcAddress(hWinInet, "InternetQueryOptionA");
  678. g_pfnInternetSetOption = (pfnInternetSetOptionSpec)GetProcAddress(hWinInet, "InternetSetOptionA");
  679. if ((NULL == g_pfnInternetQueryOption) || (NULL == g_pfnInternetSetOption))
  680. {
  681. FreeLibrary(hWinInet);
  682. return FALSE;
  683. }
  684. }
  685. }
  686. //
  687. // Parse out the command line parameters
  688. //
  689. // command line is of the form: /profile %PROFILE% /DialRasEntry %DIALRASENTRY% /TunnelRasEntry %TUNNELRASENTRYNAME% /source_filename Proxy.txt /backup_filename backup.txt
  690. CmArgV = GetCmArgV(pszArgs);
  691. int i = 0;
  692. if (!CmArgV)
  693. {
  694. goto exit;
  695. }
  696. while (CmArgV[i])
  697. {
  698. if (0 == lstrcmpi(CmArgV[i], "/source_filename") && CmArgV[i+1])
  699. {
  700. pszSourceFile = CmStrCpyAlloc(CmArgV[i+1]);
  701. i = i+2;
  702. }
  703. else if (0 == lstrcmpi(CmArgV[i], "/backup_filename") && CmArgV[i+1])
  704. {
  705. pszBackupFile = CmStrCpyAlloc(CmArgV[i+1]);
  706. i = i+2;
  707. }
  708. else if (0 == lstrcmpi(CmArgV[i], "/DialRasEntry") && CmArgV[i+1])
  709. {
  710. pszConnectionName = (CmArgV[i+1]);
  711. i = i+2;
  712. }
  713. else if (0 == lstrcmpi(CmArgV[i], "/TunnelRasEntry") && CmArgV[i+1])
  714. {
  715. pszAltName = (CmArgV[i+1]);
  716. i = i+2;
  717. }
  718. else if (0 == lstrcmpi(CmArgV[i], "/profile") && CmArgV[i+1])
  719. {
  720. pszProfileDirPath = (CmArgV[i+1]);
  721. i = i+2;
  722. }
  723. else
  724. {
  725. //
  726. // Unknown option. Lets trace it out and try to continue. We will do param
  727. // verification next so if we don't have enough info to operate correctly we will work there.
  728. //
  729. CMTRACE1("Unknown option: %s", CmArgV[i]);
  730. i++;
  731. }
  732. }
  733. //
  734. // Verify that we have at least a source file and a name.
  735. //
  736. if ((pszSourceFile) && (pszConnectionName))
  737. {
  738. //
  739. // Lets parse the cmp path into the profile dir and append it to the filename.
  740. //
  741. if (pszProfileDirPath)
  742. {
  743. LPSTR pszTemp = CmStrrchr(pszProfileDirPath, '.');
  744. if (pszTemp)
  745. {
  746. *pszTemp = '\\';
  747. *(pszTemp+1) = '\0';
  748. pszTemp = CmStrCpyAlloc(pszProfileDirPath);
  749. CmStrCatAlloc(&pszTemp, pszSourceFile);
  750. CmFree(pszSourceFile);
  751. pszSourceFile = pszTemp;
  752. if (pszBackupFile)
  753. {
  754. pszTemp = CmStrCpyAlloc(pszProfileDirPath);
  755. CmStrCatAlloc(&pszTemp, pszBackupFile);
  756. CmFree(pszBackupFile);
  757. pszBackupFile = pszTemp;
  758. }
  759. }
  760. }
  761. //
  762. // If we have a direct connection or if this is a double dial connection on Win9x then we
  763. // will want to use pszAltName instead of pszConnectionName. This is because in the Win9x case,
  764. // the tunnel connectoid has "Tunnel" appended to it since all of the connectoids are stored in
  765. // the registry and we cannot have two connectoids with the same name. If this is a direct
  766. // connection this is also important because pszConnectoid will come through as "NULL" and the
  767. // Tunnel connectoid name will be the important one. Also, in these cases we need to set
  768. // bWriteOutUseVpnName to TRUE in order to write this flag out for the disconnect action.
  769. //
  770. BOOL bWriteOutUseVpnName = FALSE;
  771. if (pszConnectionName && pszAltName && bIE5)
  772. {
  773. if ((0 == lstrcmpi(pszConnectionName, TEXT("NULL"))) || OS_W9X)
  774. {
  775. //
  776. // Then we have a direct connection or a double dial connection on 9x
  777. //
  778. if (UseVpnName(pszAltName))
  779. {
  780. pszConnectionName = pszAltName;
  781. pszAltName = NULL;
  782. bWriteOutUseVpnName = TRUE;
  783. }
  784. }
  785. }
  786. //
  787. // If we have a backup filename specified then we need to read the current Proxy settings
  788. // and save them out to the given filename.
  789. //
  790. if (NULL != pszBackupFile)
  791. {
  792. if (SUCCEEDED(GetProxySettings(pszConnectionName, &bManualProxy, &bAutomaticProxy, &bAutoConfigScript,
  793. &pszProxyServer, &pszProxyOverride, &pszAutoConfigScript)))
  794. {
  795. BOOL bSuccess = WriteProxySettingsToFile(pszBackupFile, bManualProxy, bAutomaticProxy, bAutoConfigScript,
  796. pszProxyServer, pszProxyOverride, pszAutoConfigScript,
  797. bWriteOutUseVpnName);
  798. if (!bSuccess)
  799. {
  800. CMTRACE("Unable to save settings to backup file, exiting!");
  801. goto exit;
  802. }
  803. CmFree(pszProxyServer); pszProxyServer = NULL;
  804. CmFree(pszProxyOverride); pszProxyOverride = NULL;
  805. CmFree(pszAutoConfigScript); pszAutoConfigScript = NULL;
  806. }
  807. }
  808. //
  809. // Now we need to read the proxy settings to apply out of the given file
  810. //
  811. if (ReadProxySettingsFromFile(pszSourceFile, &bManualProxy, &bAutomaticProxy, &bAutoConfigScript, &pszProxyServer,
  812. &pszProxyOverride, &pszAutoConfigScript, &bUseVpnName))
  813. {
  814. //
  815. // Finally write the proxy settings.
  816. //
  817. if (SUCCEEDED(SetProxySettings(pszConnectionName, bManualProxy, bAutomaticProxy, bAutoConfigScript,
  818. pszProxyServer, pszProxyOverride, pszAutoConfigScript)))
  819. {
  820. CMTRACE1("CmProxy -- Set proxy settings successfully for %s.", pszConnectionName);
  821. }
  822. }
  823. }
  824. }
  825. exit:
  826. CmFree(pszProxyServer);
  827. CmFree(pszProxyOverride);
  828. CmFree(pszAutoConfigScript);
  829. CmFree(pszSourceFile);
  830. CmFree(pszBackupFile);
  831. CmFree(CmArgV);
  832. if (hWinInet)
  833. {
  834. FreeLibrary(hWinInet);
  835. }
  836. //
  837. // Always return S_OK because failing to set the proxy shouldn't stop the connection
  838. // process.
  839. //
  840. return S_OK;
  841. }