wininet: Add support for INTERNET_OPTION_PER_CONNECTION_OPTION option on session handles.
This commit is contained in:
parent
9aa7f27d82
commit
62027a9c4d
1 changed files with 154 additions and 31 deletions
|
@ -110,6 +110,8 @@ static ULONG connect_timeout = 60000;
|
|||
static const WCHAR szInternetSettings[] =
|
||||
L"Software\\Microsoft\\Windows\\CurrentVersion\\Internet Settings";
|
||||
|
||||
static WCHAR *get_proxy_autoconfig_url(void);
|
||||
|
||||
void *alloc_object(object_header_t *parent, const object_vtbl_t *vtbl, size_t size)
|
||||
{
|
||||
UINT_PTR handle = 0, num;
|
||||
|
@ -985,6 +987,37 @@ static VOID APPINFO_Destroy(object_header_t *hdr)
|
|||
free(lpwai->proxyPassword);
|
||||
}
|
||||
|
||||
static WCHAR *copy_optionW(WCHAR *value)
|
||||
{
|
||||
DWORD len;
|
||||
void *tmp;
|
||||
|
||||
if (!value)
|
||||
return NULL;
|
||||
|
||||
len = (wcslen(value) + 1) * sizeof(WCHAR);
|
||||
if (!(tmp = GlobalAlloc(0, len)))
|
||||
return NULL;
|
||||
|
||||
return memcpy(tmp, value, len);
|
||||
}
|
||||
|
||||
static char *copy_optionA(WCHAR *value)
|
||||
{
|
||||
DWORD len;
|
||||
void *tmp;
|
||||
|
||||
if (!value)
|
||||
return NULL;
|
||||
|
||||
len = WideCharToMultiByte(CP_ACP, 0, value, -1, NULL, 0, NULL, NULL);
|
||||
if (!(tmp = GlobalAlloc(0, len)))
|
||||
return NULL;
|
||||
|
||||
WideCharToMultiByte(CP_ACP, 0, value, -1, tmp, len, NULL, NULL);
|
||||
return tmp;
|
||||
}
|
||||
|
||||
static DWORD APPINFO_QueryOption(object_header_t *hdr, DWORD option, void *buffer, DWORD *size, BOOL unicode)
|
||||
{
|
||||
appinfo_t *ai = (appinfo_t*)hdr;
|
||||
|
@ -1123,6 +1156,80 @@ static DWORD APPINFO_QueryOption(object_header_t *hdr, DWORD option, void *buffe
|
|||
*size = sizeof(ULONG);
|
||||
|
||||
return ERROR_SUCCESS;
|
||||
|
||||
case INTERNET_OPTION_PER_CONNECTION_OPTION: {
|
||||
INTERNET_PER_CONN_OPTION_LISTW *con = buffer;
|
||||
INTERNET_PER_CONN_OPTION_LISTA *conA = buffer;
|
||||
LONG res = ERROR_SUCCESS;
|
||||
WCHAR *url = NULL;
|
||||
int i;
|
||||
|
||||
if (*size < sizeof(INTERNET_PER_CONN_OPTION_LISTW))
|
||||
return ERROR_INSUFFICIENT_BUFFER;
|
||||
|
||||
EnterCriticalSection(&WININET_cs);
|
||||
|
||||
if (global_proxy.flags & PROXY_TYPE_AUTO_DETECT)
|
||||
url = get_proxy_autoconfig_url();
|
||||
|
||||
for (i = 0; i < con->dwOptionCount; i++) {
|
||||
INTERNET_PER_CONN_OPTIONW *optionW = con->pOptions + i;
|
||||
INTERNET_PER_CONN_OPTIONA *optionA = conA->pOptions + i;
|
||||
|
||||
switch (optionW->dwOption) {
|
||||
case INTERNET_PER_CONN_FLAGS:
|
||||
optionW->Value.dwValue = global_proxy.flags;
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_PROXY_SERVER:
|
||||
if (unicode)
|
||||
optionW->Value.pszValue = copy_optionW(global_proxy.proxy);
|
||||
else
|
||||
optionA->Value.pszValue = copy_optionA(global_proxy.proxy);
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_PROXY_BYPASS:
|
||||
if (unicode)
|
||||
optionW->Value.pszValue = copy_optionW(global_proxy.proxyBypass);
|
||||
else
|
||||
optionA->Value.pszValue = copy_optionA(global_proxy.proxyBypass);
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_URL:
|
||||
if (unicode)
|
||||
optionW->Value.pszValue = copy_optionW(global_proxy.autoconf_url);
|
||||
else
|
||||
optionA->Value.pszValue = copy_optionA(global_proxy.autoconf_url);
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_AUTODISCOVERY_FLAGS:
|
||||
optionW->Value.dwValue = AUTO_PROXY_FLAG_ALWAYS_DETECT;
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_LAST_DETECT_URL:
|
||||
if (unicode)
|
||||
optionW->Value.pszValue = copy_optionW(url);
|
||||
else
|
||||
optionA->Value.pszValue = copy_optionA(url);
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_SECONDARY_URL:
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_RELOAD_DELAY_MINS:
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_LAST_DETECT_TIME:
|
||||
FIXME("Unhandled dwOption %ld\n", optionW->dwOption);
|
||||
memset(&optionW->Value, 0, sizeof(optionW->Value));
|
||||
break;
|
||||
|
||||
default:
|
||||
FIXME("Unknown dwOption %ld\n", optionW->dwOption);
|
||||
res = ERROR_INVALID_PARAMETER;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
LeaveCriticalSection(&WININET_cs);
|
||||
return res;
|
||||
}
|
||||
}
|
||||
|
||||
return INET_QueryOption(hdr, option, buffer, size, unicode);
|
||||
|
@ -1150,6 +1257,53 @@ static DWORD APPINFO_SetOption(object_header_t *hdr, DWORD option, void *buf, DW
|
|||
case INTERNET_OPTION_REFRESH:
|
||||
FIXME("INTERNET_OPTION_REFRESH\n");
|
||||
return ERROR_SUCCESS;
|
||||
case INTERNET_OPTION_PER_CONNECTION_OPTION: {
|
||||
INTERNET_PER_CONN_OPTION_LISTW *con = buf;
|
||||
unsigned int i;
|
||||
|
||||
EnterCriticalSection( &WININET_cs );
|
||||
for (i = 0; i < con->dwOptionCount; i++) {
|
||||
INTERNET_PER_CONN_OPTIONW *option = con->pOptions + i;
|
||||
|
||||
switch (option->dwOption) {
|
||||
case INTERNET_PER_CONN_PROXY_SERVER:
|
||||
free(global_proxy.proxy);
|
||||
global_proxy.proxy = wcsdup(option->Value.pszValue);
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_FLAGS:
|
||||
if(option->Value.dwValue & ~(PROXY_TYPE_PROXY | PROXY_TYPE_DIRECT))
|
||||
FIXME("Unhandled flags: 0x%lx\n", option->Value.dwValue);
|
||||
global_proxy.flags = option->Value.dwValue;
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_PROXY_BYPASS:
|
||||
free(global_proxy.proxyBypass);
|
||||
global_proxy.proxyBypass = wcsdup(option->Value.pszValue);
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_URL:
|
||||
free(global_proxy.autoconf_url);
|
||||
global_proxy.autoconf_url = wcsdup(option->Value.pszValue);
|
||||
break;
|
||||
|
||||
case INTERNET_PER_CONN_AUTODISCOVERY_FLAGS:
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_SECONDARY_URL:
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_RELOAD_DELAY_MINS:
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_LAST_DETECT_TIME:
|
||||
case INTERNET_PER_CONN_AUTOCONFIG_LAST_DETECT_URL:
|
||||
FIXME("Unhandled dwOption %ld\n", option->dwOption);
|
||||
break;
|
||||
|
||||
default:
|
||||
FIXME("Unknown dwOption %ld\n", option->dwOption);
|
||||
SetLastError(ERROR_INVALID_PARAMETER);
|
||||
break;
|
||||
}
|
||||
}
|
||||
LeaveCriticalSection( &WININET_cs );
|
||||
return ERROR_SUCCESS;
|
||||
}
|
||||
}
|
||||
|
||||
return INET_SetOption(hdr, option, buf, size);
|
||||
|
@ -2759,37 +2913,6 @@ static WCHAR *get_proxy_autoconfig_url(void)
|
|||
return ret;
|
||||
}
|
||||
|
||||
static WCHAR *copy_optionW(WCHAR *value)
|
||||
{
|
||||
DWORD len;
|
||||
void *tmp;
|
||||
|
||||
if (!value)
|
||||
return NULL;
|
||||
|
||||
len = (wcslen(value) + 1) * sizeof(WCHAR);
|
||||
if (!(tmp = GlobalAlloc(0, len)))
|
||||
return NULL;
|
||||
|
||||
return memcpy(tmp, value, len);
|
||||
}
|
||||
|
||||
static char *copy_optionA(WCHAR *value)
|
||||
{
|
||||
DWORD len;
|
||||
void *tmp;
|
||||
|
||||
if (!value)
|
||||
return NULL;
|
||||
|
||||
len = WideCharToMultiByte(CP_ACP, 0, value, -1, NULL, 0, NULL, NULL);
|
||||
if (!(tmp = GlobalAlloc(0, len)))
|
||||
return NULL;
|
||||
|
||||
WideCharToMultiByte(CP_ACP, 0, value, -1, tmp, len, NULL, NULL);
|
||||
return tmp;
|
||||
}
|
||||
|
||||
static DWORD query_global_option(DWORD option, void *buffer, DWORD *size, BOOL unicode)
|
||||
{
|
||||
/* FIXME: This function currently handles more options than it should. Options requiring
|
||||
|
|
Loading…
Add table
Reference in a new issue