
Question:
I configured internet explorer to use a local PAC file: <img alt="ie proxy settings" class="b-lazy" data-src="https://i.stack.imgur.com/eBkAY.png" data-original="https://i.stack.imgur.com/eBkAY.png" src="https://etrip.eimg.top/images/2019/05/07/timg.gif" />
It works just fine. But when I try to call InternetGetProxyInfo()
, it fails with ERROR_CAN_NOT_COMPLETE
. What can be the problem?
#ifndef WINVER // Allow use of features specific to Windows XP or later.
#define WINVER 0x0501 // Change this to the appropriate value to target other versions of Windows.
#endif
#ifndef _WIN32_WINNT // Allow use of features specific to Windows XP or later.
#define _WIN32_WINNT 0x0501 // Change this to the appropriate value to target other versions of Windows.
#endif
#include <winsock2.h>
#include <windows.h>
#include <wininet.h>
#include <tchar.h>
#define URL "http://www.yandex.ru/"
#define HOST "www.yandex.ru"
int _tmain(int argc, _TCHAR* argv[])
{
char proxyBuffer[1024];
char *str = proxyBuffer;
DWORD nb = 1024;
DWORD dw;
BOOL b;
pfnInternetGetProxyInfo pIGPI; // Function-pointer instance
/* code from MSDN: */
{
HMODULE hModJS; // Handle for loading the DLL
hModJS = LoadLibrary( TEXT("jsproxy.dll") );
if (!hModJS)
{
_tprintf( TEXT("\nLoadLibrary failed to load jsproxy.dll with error: %d\n"),
GetLastError( ) );
return( FALSE );
}
pIGPI = (pfnInternetGetProxyInfo)
GetProcAddress( hModJS, "InternetGetProxyInfo" );
if (!pIGPI)
{
_tprintf( TEXT("\nGetProcAddress failed to find InternetGetProxyInfo, error: %d\n"),
GetLastError( ) );
return( FALSE );
}
// The pIGPI function pointer can now be used to call InternetGetProxyInfo.
}
InternetInitializeAutoProxyDll(0); /* wininet.dll version of this function */
SetLastError(0);
b = pIGPI(URL,sizeof(URL),HOST,sizeof(HOST), &str, &nb);
dw = GetLastError();
SetLastError(0);
b = pIGPI(URL,sizeof(URL)-1,HOST,sizeof(HOST)-1, &str, &nb);
dw = GetLastError();
return 0;
}
Please don't tell me to use other API, it's an educational, not practical question.
Answer1:There are 2 ways:
<ul><li>easy: call InternetOpenUrl()
with a dummy URL to let wininet
initialize jsproxy:
#define URL "https://yandex.ru:777"
#define HOST "yandex.ru"
HINTERNET hInternet = InternetOpen(_T("try-wininet"), INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0);
HINTERNET hUrl = InternetOpenUrl(hInternet, _T("http://0.0.0.0"), NULL, 0, 0, 20);
InternetCloseHandle(hUrl);
InternetCloseHandle(hInternet);
InternetGetProxyInfo(URL,sizeof(URL)-1,HOST,sizeof(HOST)-1, &str, &nb);
GlobalFree(str);
</li>
<li>hard: call InternetInitializeAutoProxyDll()
in jsproxy. But to prepare the arguments, you have to do everything yourself: read the settings from the registry, parse them, detect and download the PAC file and provide an implementation of AutoProxyHelperVtbl
that contains such functions as GetIPAddress()
, IsInNet()
, etc.
InternetGetProxyInfo()
fails when there's no PAC script configured, although some proxy server is set in the bottom of the dialog. In this case you should call InternetQueryOption(NULL, INTERNET_OPTION_PROXY,...)