1 /* 2 * Wininet - HTTP tests 3 * 4 * Copyright 2002 Aric Stewart 5 * Copyright 2004 Mike McCormack 6 * Copyright 2005 Hans Leidekker 7 * 8 * This library is free software; you can redistribute it and/or 9 * modify it under the terms of the GNU Lesser General Public 10 * License as published by the Free Software Foundation; either 11 * version 2.1 of the License, or (at your option) any later version. 12 * 13 * This library is distributed in the hope that it will be useful, 14 * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 16 * Lesser General Public License for more details. 17 * 18 * You should have received a copy of the GNU Lesser General Public 19 * License along with this library; if not, write to the Free Software 20 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 21 */ 22 23 #include <stdarg.h> 24 #include <stdio.h> 25 #include <stdlib.h> 26 #include <limits.h> 27 28 #include "windef.h" 29 #include "winbase.h" 30 #include "wininet.h" 31 #include "winineti.h" 32 #include "winsock2.h" 33 34 #include "wine/test.h" 35 36 /* Undocumented security flags */ 37 #define _SECURITY_FLAG_CERT_REV_FAILED 0x00800000 38 #define _SECURITY_FLAG_CERT_INVALID_CA 0x01000000 39 #define _SECURITY_FLAG_CERT_INVALID_CN 0x02000000 40 #define _SECURITY_FLAG_CERT_INVALID_DATE 0x04000000 41 42 #define TEST_URL "http://test.winehq.org/tests/hello.html" 43 44 static BOOL first_connection_to_test_url = TRUE; 45 static BOOL https_support = TRUE; 46 47 /* Adapted from dlls/urlmon/tests/protocol.c */ 48 49 #define SET_EXPECT2(status, num) \ 50 expect[status] = num 51 52 #define SET_EXPECT(status) \ 53 SET_EXPECT2(status, 1) 54 55 #define SET_OPTIONAL2(status, num) \ 56 optional[status] = num 57 58 #define SET_OPTIONAL(status) \ 59 SET_OPTIONAL2(status, 1) 60 61 /* SET_WINE_ALLOW's should be used with an appropriate 62 * todo_wine CHECK_NOTIFIED at a later point in the code */ 63 #define SET_WINE_ALLOW2(status, num) \ 64 wine_allow[status] = num 65 66 #define SET_WINE_ALLOW(status) \ 67 SET_WINE_ALLOW2(status, 1) 68 69 #define CHECK_EXPECT(status) \ 70 do { \ 71 if (!expect[status] && !optional[status] && wine_allow[status]) \ 72 { \ 73 todo_wine ok(expect[status], "unexpected status %d (%s)\n", status, \ 74 status < MAX_INTERNET_STATUS && status_string[status] ? \ 75 status_string[status] : "unknown"); \ 76 wine_allow[status]--; \ 77 } \ 78 else \ 79 { \ 80 ok(expect[status] || optional[status], "unexpected status %d (%s)\n", status, \ 81 status < MAX_INTERNET_STATUS && status_string[status] ? \ 82 status_string[status] : "unknown"); \ 83 if (expect[status]) expect[status]--; \ 84 else if(optional[status]) optional[status]--; \ 85 } \ 86 notified[status]++; \ 87 }while(0) 88 89 /* CLEAR_NOTIFIED used in cases when notification behavior 90 * differs between Windows versions */ 91 #define CLEAR_NOTIFIED(status) \ 92 expect[status] = optional[status] = wine_allow[status] = notified[status] = 0; 93 94 #define CHECK_NOTIFIED2(status, num) \ 95 do { \ 96 ok(notified[status] + optional[status] == (num), \ 97 "expected status %d (%s) %d times, received %d times\n", \ 98 status, status < MAX_INTERNET_STATUS && status_string[status] ? \ 99 status_string[status] : "unknown", (num), notified[status]); \ 100 CLEAR_NOTIFIED(status); \ 101 }while(0) 102 103 #define CHECK_NOTIFIED(status) \ 104 CHECK_NOTIFIED2(status, 1) 105 106 #define CHECK_NOT_NOTIFIED(status) \ 107 CHECK_NOTIFIED2(status, 0) 108 109 #define MAX_INTERNET_STATUS (INTERNET_STATUS_COOKIE_HISTORY+1) 110 static int expect[MAX_INTERNET_STATUS], optional[MAX_INTERNET_STATUS], 111 wine_allow[MAX_INTERNET_STATUS], notified[MAX_INTERNET_STATUS]; 112 static const char *status_string[MAX_INTERNET_STATUS]; 113 114 static HANDLE complete_event, conn_close_event, conn_wait_event, server_req_rec_event, request_sent_event; 115 static DWORD req_error; 116 static BOOL is_ie7plus = TRUE; 117 118 #define TESTF_REDIRECT 0x01 119 #define TESTF_COMPRESSED 0x02 120 #define TESTF_CHUNKED 0x04 121 122 typedef struct { 123 const char *url; 124 const char *redirected_url; 125 const char *host; 126 const char *path; 127 const char *headers; 128 DWORD flags; 129 const char *post_data; 130 const char *content; 131 } test_data_t; 132 133 static const test_data_t test_data[] = { 134 { 135 "http://test.winehq.org/tests/data.php", 136 "http://test.winehq.org/tests/data.php", 137 "test.winehq.org", 138 "/tests/data.php", 139 "", 140 TESTF_CHUNKED 141 }, 142 { 143 "http://test.winehq.org/tests/redirect", 144 "http://test.winehq.org/tests/hello.html", 145 "test.winehq.org", 146 "/tests/redirect", 147 "", 148 TESTF_REDIRECT 149 }, 150 { 151 "http://test.winehq.org/tests/gzip.php", 152 "http://test.winehq.org/tests/gzip.php", 153 "test.winehq.org", 154 "/tests/gzip.php", 155 "Accept-Encoding: gzip, deflate", 156 TESTF_COMPRESSED 157 }, 158 { 159 "http://test.winehq.org/tests/post.php", 160 "http://test.winehq.org/tests/post.php", 161 "test.winehq.org", 162 "/tests/post.php", 163 "Content-Type: application/x-www-form-urlencoded", 164 0, 165 "mode=Test", 166 "mode => Test\n" 167 } 168 }; 169 170 static INTERNET_STATUS_CALLBACK (WINAPI *pInternetSetStatusCallbackA)(HINTERNET ,INTERNET_STATUS_CALLBACK); 171 static INTERNET_STATUS_CALLBACK (WINAPI *pInternetSetStatusCallbackW)(HINTERNET ,INTERNET_STATUS_CALLBACK); 172 static BOOL (WINAPI *pInternetGetSecurityInfoByURLA)(LPSTR,PCCERT_CHAIN_CONTEXT*,DWORD*); 173 174 static BOOL is_lang_english(void) 175 { 176 static HMODULE hkernel32 = NULL; 177 static LANGID (WINAPI *pGetThreadUILanguage)(void) = NULL; 178 static LANGID (WINAPI *pGetUserDefaultUILanguage)(void) = NULL; 179 180 if (!hkernel32) 181 { 182 hkernel32 = GetModuleHandleA("kernel32.dll"); 183 pGetThreadUILanguage = (void*)GetProcAddress(hkernel32, "GetThreadUILanguage"); 184 pGetUserDefaultUILanguage = (void*)GetProcAddress(hkernel32, "GetUserDefaultUILanguage"); 185 } 186 if (pGetThreadUILanguage) 187 return PRIMARYLANGID(pGetThreadUILanguage()) == LANG_ENGLISH; 188 if (pGetUserDefaultUILanguage) 189 return PRIMARYLANGID(pGetUserDefaultUILanguage()) == LANG_ENGLISH; 190 191 return PRIMARYLANGID(GetUserDefaultLangID()) == LANG_ENGLISH; 192 } 193 194 static int strcmp_wa(LPCWSTR strw, const char *stra) 195 { 196 WCHAR buf[512]; 197 MultiByteToWideChar(CP_ACP, 0, stra, -1, buf, ARRAY_SIZE(buf)); 198 return lstrcmpW(strw, buf); 199 } 200 201 static BOOL proxy_active(void) 202 { 203 HKEY internet_settings; 204 DWORD proxy_enable; 205 DWORD size; 206 207 if (RegOpenKeyExA(HKEY_CURRENT_USER, "Software\\Microsoft\\Windows\\CurrentVersion\\Internet Settings", 208 0, KEY_QUERY_VALUE, &internet_settings) != ERROR_SUCCESS) 209 return FALSE; 210 211 size = sizeof(DWORD); 212 if (RegQueryValueExA(internet_settings, "ProxyEnable", NULL, NULL, (LPBYTE) &proxy_enable, &size) != ERROR_SUCCESS) 213 proxy_enable = 0; 214 215 RegCloseKey(internet_settings); 216 217 return proxy_enable != 0; 218 } 219 220 static void init_events(void) 221 { 222 complete_event = CreateEventW(NULL, FALSE, FALSE, NULL); 223 conn_close_event = CreateEventW(NULL, FALSE, FALSE, NULL); 224 conn_wait_event = CreateEventW(NULL, FALSE, FALSE, NULL); 225 server_req_rec_event = CreateEventW(NULL, FALSE, FALSE, NULL); 226 request_sent_event = CreateEventW(NULL, FALSE, FALSE, NULL); 227 } 228 229 static void free_events(void) 230 { 231 CloseHandle(complete_event); 232 CloseHandle(conn_close_event); 233 CloseHandle(conn_wait_event); 234 CloseHandle(server_req_rec_event); 235 CloseHandle(request_sent_event); 236 } 237 238 static void reset_events(void) 239 { 240 ResetEvent(complete_event); 241 ResetEvent(conn_close_event); 242 ResetEvent(conn_wait_event); 243 ResetEvent(server_req_rec_event); 244 ResetEvent(request_sent_event); 245 } 246 247 #define test_status_code(a,b) _test_status_code(__LINE__,a,b, FALSE) 248 #define test_status_code_todo(a,b) _test_status_code(__LINE__,a,b, TRUE) 249 static void _test_status_code(unsigned line, HINTERNET req, DWORD excode, BOOL is_todo) 250 { 251 DWORD code, size, index; 252 char exbuf[12], bufa[10]; 253 WCHAR bufw[10]; 254 BOOL res; 255 256 code = 0xdeadbeef; 257 size = sizeof(code); 258 res = HttpQueryInfoA(req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &code, &size, NULL); 259 ok_(__FILE__,line)(res, "[1] HttpQueryInfoA(HTTP_QUERY_STATUS_CODE|number) failed: %u\n", GetLastError()); 260 todo_wine_if (is_todo) 261 ok_(__FILE__,line)(code == excode, "code = %d, expected %d\n", code, excode); 262 ok_(__FILE__,line)(size == sizeof(code), "size = %u\n", size); 263 264 code = 0xdeadbeef; 265 index = 0; 266 size = sizeof(code); 267 res = HttpQueryInfoA(req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &code, &size, &index); 268 ok_(__FILE__,line)(res, "[2] HttpQueryInfoA(HTTP_QUERY_STATUS_CODE|number index) failed: %u\n", GetLastError()); 269 ok_(__FILE__,line)(!index, "index = %d, expected 0\n", index); 270 ok_(__FILE__,line)(size == sizeof(code), "size = %u\n", size); 271 272 sprintf(exbuf, "%u", excode); 273 274 size = sizeof(bufa); 275 res = HttpQueryInfoA(req, HTTP_QUERY_STATUS_CODE, bufa, &size, NULL); 276 ok_(__FILE__,line)(res, "[3] HttpQueryInfoA(HTTP_QUERY_STATUS_CODE) failed: %u\n", GetLastError()); 277 todo_wine_if (is_todo) 278 ok_(__FILE__,line)(!strcmp(bufa, exbuf), "unexpected status code %s, expected %s\n", bufa, exbuf); 279 ok_(__FILE__,line)(size == strlen(exbuf), "unexpected size %d for \"%s\"\n", size, exbuf); 280 281 size = 0; 282 res = HttpQueryInfoA(req, HTTP_QUERY_STATUS_CODE, NULL, &size, NULL); 283 ok_(__FILE__,line)(!res && GetLastError() == ERROR_INSUFFICIENT_BUFFER, 284 "[4] HttpQueryInfoA(HTTP_QUERY_STATUS_CODE) failed: %u\n", GetLastError()); 285 ok_(__FILE__,line)(size == strlen(exbuf)+1, "unexpected size %d for \"%s\"\n", size, exbuf); 286 287 size = sizeof(bufw); 288 res = HttpQueryInfoW(req, HTTP_QUERY_STATUS_CODE, bufw, &size, NULL); 289 ok_(__FILE__,line)(res, "[5] HttpQueryInfoW(HTTP_QUERY_STATUS_CODE) failed: %u\n", GetLastError()); 290 todo_wine_if (is_todo) 291 ok_(__FILE__,line)(!strcmp_wa(bufw, exbuf), "unexpected status code %s, expected %s\n", bufa, exbuf); 292 ok_(__FILE__,line)(size == strlen(exbuf)*sizeof(WCHAR), "unexpected size %d for \"%s\"\n", size, exbuf); 293 294 size = 0; 295 res = HttpQueryInfoW(req, HTTP_QUERY_STATUS_CODE, bufw, &size, NULL); 296 ok_(__FILE__,line)(!res && GetLastError() == ERROR_INSUFFICIENT_BUFFER, 297 "[6] HttpQueryInfoW(HTTP_QUERY_STATUS_CODE) failed: %u\n", GetLastError()); 298 ok_(__FILE__,line)(size == (strlen(exbuf)+1)*sizeof(WCHAR), "unexpected size %d for \"%s\"\n", size, exbuf); 299 300 if(0) { 301 size = sizeof(bufw); 302 res = HttpQueryInfoW(req, HTTP_QUERY_STATUS_CODE, NULL, &size, NULL); 303 ok(!res && GetLastError() == ERROR_INVALID_PARAMETER, "HttpQueryInfo(HTTP_QUERY_STATUS_CODE) failed: %u\n", GetLastError()); 304 ok(size == sizeof(bufw), "unexpected size %d\n", size); 305 } 306 307 code = 0xdeadbeef; 308 index = 1; 309 size = sizeof(code); 310 res = HttpQueryInfoA(req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &code, &size, &index); 311 ok_(__FILE__,line)(!res && GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, 312 "[7] HttpQueryInfoA failed: %x(%d)\n", res, GetLastError()); 313 314 code = 0xdeadbeef; 315 size = sizeof(code); 316 res = HttpQueryInfoA(req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_REQUEST_HEADERS, &code, &size, NULL); 317 ok_(__FILE__,line)(!res && GetLastError() == ERROR_HTTP_INVALID_QUERY_REQUEST, 318 "[8] HttpQueryInfoA failed: %x(%d)\n", res, GetLastError()); 319 } 320 321 #define test_request_flags(a,b) _test_request_flags(__LINE__,a,b,FALSE) 322 #define test_request_flags_todo(a,b) _test_request_flags(__LINE__,a,b,TRUE) 323 static void _test_request_flags(unsigned line, HINTERNET req, DWORD exflags, BOOL is_todo) 324 { 325 DWORD flags, size; 326 BOOL res; 327 328 flags = 0xdeadbeef; 329 size = sizeof(flags); 330 res = InternetQueryOptionW(req, INTERNET_OPTION_REQUEST_FLAGS, &flags, &size); 331 ok_(__FILE__,line)(res, "InternetQueryOptionW(INTERNET_OPTION_REQUEST_FLAGS) failed: %u\n", GetLastError()); 332 333 /* FIXME: Remove once we have INTERNET_REQFLAG_CACHE_WRITE_DISABLED implementation */ 334 flags &= ~INTERNET_REQFLAG_CACHE_WRITE_DISABLED; 335 todo_wine_if (is_todo) 336 ok_(__FILE__,line)(flags == exflags, "flags = %x, expected %x\n", flags, exflags); 337 } 338 339 #define test_request_url(a,b) _test_request_url(__LINE__,a,b) 340 static void _test_request_url(unsigned line, HINTERNET req, const char *expected_url) 341 { 342 char buf[INTERNET_MAX_URL_LENGTH]; 343 DWORD size = sizeof(buf); 344 BOOL res; 345 346 res = InternetQueryOptionA(req, INTERNET_OPTION_URL, buf, &size); 347 ok_(__FILE__,line)(res, "InternetQueryOptionA(INTERNET_OPTION_URL) failed: %u\n", GetLastError()); 348 ok_(__FILE__,line)(size == strlen(expected_url), "size = %u\n", size); 349 ok_(__FILE__,line)(!strcmp(buf, expected_url), "unexpected URL %s, expected %s\n", buf, expected_url); 350 } 351 352 #define test_http_version(a) _test_http_version(__LINE__,a) 353 static void _test_http_version(unsigned line, HINTERNET req) 354 { 355 HTTP_VERSION_INFO v = {0xdeadbeef, 0xdeadbeef}; 356 DWORD size; 357 BOOL res; 358 359 size = sizeof(v); 360 res = InternetQueryOptionW(req, INTERNET_OPTION_HTTP_VERSION, &v, &size); 361 ok_(__FILE__,line)(res, "InternetQueryOptionW(INTERNET_OPTION_HTTP_VERSION) failed: %u\n", GetLastError()); 362 ok_(__FILE__,line)(v.dwMajorVersion == 1, "dwMajorVersion = %d\n", v.dwMajorVersion); 363 ok_(__FILE__,line)(v.dwMinorVersion == 1, "dwMinorVersion = %d\n", v.dwMinorVersion); 364 } 365 366 static int close_handle_cnt; 367 368 static VOID WINAPI callback( 369 HINTERNET hInternet, 370 DWORD_PTR dwContext, 371 DWORD dwInternetStatus, 372 LPVOID lpvStatusInformation, 373 DWORD dwStatusInformationLength 374 ) 375 { 376 ros_skip_flaky 377 CHECK_EXPECT(dwInternetStatus); 378 switch (dwInternetStatus) 379 { 380 case INTERNET_STATUS_RESOLVING_NAME: 381 if(winetest_debug > 1) 382 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_RESOLVING_NAME \"%s\" %d\n", 383 GetCurrentThreadId(), hInternet, dwContext, 384 (LPCSTR)lpvStatusInformation,dwStatusInformationLength); 385 *(LPSTR)lpvStatusInformation = '\0'; 386 break; 387 case INTERNET_STATUS_NAME_RESOLVED: 388 if(winetest_debug > 1) 389 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_NAME_RESOLVED \"%s\" %d\n", 390 GetCurrentThreadId(), hInternet, dwContext, 391 (LPCSTR)lpvStatusInformation,dwStatusInformationLength); 392 *(LPSTR)lpvStatusInformation = '\0'; 393 break; 394 case INTERNET_STATUS_CONNECTING_TO_SERVER: 395 if(winetest_debug > 1) 396 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_CONNECTING_TO_SERVER \"%s\" %d\n", 397 GetCurrentThreadId(), hInternet, dwContext, 398 (LPCSTR)lpvStatusInformation,dwStatusInformationLength); 399 ok(dwStatusInformationLength == strlen(lpvStatusInformation)+1, "unexpected size %u\n", 400 dwStatusInformationLength); 401 *(LPSTR)lpvStatusInformation = '\0'; 402 break; 403 case INTERNET_STATUS_CONNECTED_TO_SERVER: 404 if(winetest_debug > 1) 405 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_CONNECTED_TO_SERVER \"%s\" %d\n", 406 GetCurrentThreadId(), hInternet, dwContext, 407 (LPCSTR)lpvStatusInformation,dwStatusInformationLength); 408 ok(dwStatusInformationLength == strlen(lpvStatusInformation)+1, "unexpected size %u\n", 409 dwStatusInformationLength); 410 *(LPSTR)lpvStatusInformation = '\0'; 411 break; 412 case INTERNET_STATUS_SENDING_REQUEST: 413 if(winetest_debug > 1) 414 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_SENDING_REQUEST %p %d\n", 415 GetCurrentThreadId(), hInternet, dwContext, 416 lpvStatusInformation,dwStatusInformationLength); 417 break; 418 case INTERNET_STATUS_REQUEST_SENT: 419 ok(dwStatusInformationLength == sizeof(DWORD), 420 "info length should be sizeof(DWORD) instead of %d\n", 421 dwStatusInformationLength); 422 if(winetest_debug > 1) 423 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_REQUEST_SENT 0x%x %d\n", 424 GetCurrentThreadId(), hInternet, dwContext, 425 *(DWORD *)lpvStatusInformation,dwStatusInformationLength); 426 break; 427 case INTERNET_STATUS_RECEIVING_RESPONSE: 428 if(winetest_debug > 1) 429 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_RECEIVING_RESPONSE %p %d\n", 430 GetCurrentThreadId(), hInternet, dwContext, 431 lpvStatusInformation,dwStatusInformationLength); 432 break; 433 case INTERNET_STATUS_RESPONSE_RECEIVED: 434 ok(dwStatusInformationLength == sizeof(DWORD), 435 "info length should be sizeof(DWORD) instead of %d\n", 436 dwStatusInformationLength); 437 if(winetest_debug > 1) 438 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_RESPONSE_RECEIVED 0x%x %d\n", 439 GetCurrentThreadId(), hInternet, dwContext, 440 *(DWORD *)lpvStatusInformation,dwStatusInformationLength); 441 break; 442 case INTERNET_STATUS_CTL_RESPONSE_RECEIVED: 443 if(winetest_debug > 1) 444 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_CTL_RESPONSE_RECEIVED %p %d\n", 445 GetCurrentThreadId(), hInternet,dwContext, 446 lpvStatusInformation,dwStatusInformationLength); 447 break; 448 case INTERNET_STATUS_PREFETCH: 449 if(winetest_debug > 1) 450 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_PREFETCH %p %d\n", 451 GetCurrentThreadId(), hInternet, dwContext, 452 lpvStatusInformation,dwStatusInformationLength); 453 break; 454 case INTERNET_STATUS_CLOSING_CONNECTION: 455 if(winetest_debug > 1) 456 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_CLOSING_CONNECTION %p %d\n", 457 GetCurrentThreadId(), hInternet, dwContext, 458 lpvStatusInformation,dwStatusInformationLength); 459 break; 460 case INTERNET_STATUS_CONNECTION_CLOSED: 461 if(winetest_debug > 1) 462 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_CONNECTION_CLOSED %p %d\n", 463 GetCurrentThreadId(), hInternet, dwContext, 464 lpvStatusInformation,dwStatusInformationLength); 465 break; 466 case INTERNET_STATUS_HANDLE_CREATED: 467 ok(dwStatusInformationLength == sizeof(HINTERNET), 468 "info length should be sizeof(HINTERNET) instead of %d\n", 469 dwStatusInformationLength); 470 if(winetest_debug > 1) 471 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_HANDLE_CREATED %p %d\n", 472 GetCurrentThreadId(), hInternet, dwContext, 473 *(HINTERNET *)lpvStatusInformation,dwStatusInformationLength); 474 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 475 SET_EXPECT(INTERNET_STATUS_DETECTING_PROXY); 476 break; 477 case INTERNET_STATUS_HANDLE_CLOSING: 478 ok(dwStatusInformationLength == sizeof(HINTERNET), 479 "info length should be sizeof(HINTERNET) instead of %d\n", 480 dwStatusInformationLength); 481 if(winetest_debug > 1) 482 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_HANDLE_CLOSING %p %d\n", 483 GetCurrentThreadId(), hInternet, dwContext, 484 *(HINTERNET *)lpvStatusInformation, dwStatusInformationLength); 485 if(!InterlockedDecrement(&close_handle_cnt)) 486 SetEvent(complete_event); 487 break; 488 case INTERNET_STATUS_REQUEST_COMPLETE: 489 { 490 INTERNET_ASYNC_RESULT *iar = (INTERNET_ASYNC_RESULT *)lpvStatusInformation; 491 ok(dwStatusInformationLength == sizeof(INTERNET_ASYNC_RESULT), 492 "info length should be sizeof(INTERNET_ASYNC_RESULT) instead of %d\n", 493 dwStatusInformationLength); 494 ok(iar->dwResult == 1 || iar->dwResult == 0, "iar->dwResult = %ld\n", iar->dwResult); 495 if(winetest_debug > 1) 496 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_REQUEST_COMPLETE {%ld,%d} %d\n", 497 GetCurrentThreadId(), hInternet, dwContext, 498 iar->dwResult,iar->dwError,dwStatusInformationLength); 499 req_error = iar->dwError; 500 if(!close_handle_cnt) 501 SetEvent(complete_event); 502 break; 503 } 504 case INTERNET_STATUS_REDIRECT: 505 if(winetest_debug > 1) 506 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_REDIRECT \"%s\" %d\n", 507 GetCurrentThreadId(), hInternet, dwContext, 508 (LPCSTR)lpvStatusInformation, dwStatusInformationLength); 509 *(LPSTR)lpvStatusInformation = '\0'; 510 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 511 SET_EXPECT(INTERNET_STATUS_DETECTING_PROXY); 512 break; 513 case INTERNET_STATUS_INTERMEDIATE_RESPONSE: 514 if(winetest_debug > 1) 515 trace("%04x:Callback %p 0x%lx INTERNET_STATUS_INTERMEDIATE_RESPONSE %p %d\n", 516 GetCurrentThreadId(), hInternet, dwContext, 517 lpvStatusInformation, dwStatusInformationLength); 518 break; 519 default: 520 if(winetest_debug > 1) 521 trace("%04x:Callback %p 0x%lx %d %p %d\n", 522 GetCurrentThreadId(), hInternet, dwContext, dwInternetStatus, 523 lpvStatusInformation, dwStatusInformationLength); 524 } 525 } 526 527 typedef struct { 528 HINTERNET session; 529 HINTERNET connection; 530 HINTERNET request; 531 } test_request_t; 532 533 #define open_simple_request(a,b,c,d,e) _open_simple_request(__LINE__,a,b,c,d,e) 534 static void _open_simple_request(unsigned line, test_request_t *req, const char *host, 535 int port, const char *verb, const char *url) 536 { 537 req->session = InternetOpenA(NULL, INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 538 ok_(__FILE__,line)(req->session != NULL, "InternetOpenA failed: %u\n", GetLastError()); 539 540 req->connection = InternetConnectA(req->session, host, port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 541 ok_(__FILE__,line)(req->connection != NULL, "InternetConnectA failed: %u\n", GetLastError()); 542 543 req->request = HttpOpenRequestA(req->connection, verb, url, NULL, NULL, NULL, 0, 0); 544 ok_(__FILE__,line)(req->request != NULL, "HttpOpenRequest failed: %u\n", GetLastError()); 545 } 546 547 #define close_request(a) _close_request(__LINE__,a) 548 static void _close_request(unsigned line, test_request_t *req) 549 { 550 BOOL ret; 551 552 ret = InternetCloseHandle(req->request); 553 ok_(__FILE__,line)(ret, "InternetCloseHandle(request) failed: %u\n", GetLastError()); 554 ret = InternetCloseHandle(req->connection); 555 ok_(__FILE__,line)(ret, "InternetCloseHandle(connection) failed: %u\n", GetLastError()); 556 ret = InternetCloseHandle(req->session); 557 ok_(__FILE__,line)(ret, "InternetCloseHandle(session) failed: %u\n", GetLastError()); 558 } 559 560 #define receive_simple_request(a,b,c) _receive_simple_request(__LINE__,a,b,c) 561 static DWORD _receive_simple_request(unsigned line, HINTERNET req, char *buf, size_t buf_size) 562 { 563 DWORD read = 0; 564 BOOL ret; 565 566 ret = InternetReadFile(req, buf, buf_size, &read); 567 ok_(__FILE__,line)(ret, "InternetReadFile failed: %u\n", GetLastError()); 568 569 return read; 570 } 571 572 static void close_async_handle(HINTERNET handle, int handle_cnt) 573 { 574 BOOL res; 575 576 close_handle_cnt = handle_cnt; 577 578 SET_EXPECT2(INTERNET_STATUS_HANDLE_CLOSING, handle_cnt); 579 res = InternetCloseHandle(handle); 580 ok(res, "InternetCloseHandle failed: %u\n", GetLastError()); 581 WaitForSingleObject(complete_event, INFINITE); 582 CHECK_NOTIFIED2(INTERNET_STATUS_HANDLE_CLOSING, handle_cnt); 583 } 584 585 static void InternetReadFile_test(int flags, const test_data_t *test) 586 { 587 char *post_data = NULL; 588 BOOL res, on_async = TRUE; 589 CHAR buffer[4000]; 590 WCHAR wbuffer[4000]; 591 DWORD length, length2, index, exlen = 0, post_len = 0; 592 const char *types[2] = { "*", NULL }; 593 HINTERNET hi, hic = 0, hor = 0; 594 DWORD contents_length, accepts_ranges; 595 BOOL not_supported; 596 597 trace("Starting InternetReadFile test with flags 0x%x on url %s\n",flags,test->url); 598 reset_events(); 599 600 trace("InternetOpenA <--\n"); 601 hi = InternetOpenA((test->flags & TESTF_COMPRESSED) ? "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0)" : "", 602 INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, flags); 603 ok((hi != 0x0),"InternetOpen failed with error %u\n", GetLastError()); 604 trace("InternetOpenA -->\n"); 605 606 if (hi == 0x0) goto abort; 607 608 pInternetSetStatusCallbackA(hi,&callback); 609 610 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 611 612 trace("InternetConnectA <--\n"); 613 hic=InternetConnectA(hi, test->host, INTERNET_INVALID_PORT_NUMBER, 614 NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 615 ok((hic != 0x0),"InternetConnect failed with error %u\n", GetLastError()); 616 trace("InternetConnectA -->\n"); 617 618 if (hic == 0x0) goto abort; 619 620 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 621 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 622 623 trace("HttpOpenRequestA <--\n"); 624 hor = HttpOpenRequestA(hic, test->post_data ? "POST" : "GET", test->path, NULL, NULL, types, 625 INTERNET_FLAG_KEEP_CONNECTION | INTERNET_FLAG_RELOAD, 626 0xdeadbead); 627 if (hor == 0x0 && GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED) { 628 /* 629 * If the internet name can't be resolved we are probably behind 630 * a firewall or in some other way not directly connected to the 631 * Internet. Not enough reason to fail the test. Just ignore and 632 * abort. 633 */ 634 } else { 635 ok((hor != 0x0),"HttpOpenRequest failed with error %u\n", GetLastError()); 636 } 637 trace("HttpOpenRequestA -->\n"); 638 639 if (hor == 0x0) goto abort; 640 641 test_request_flags(hor, INTERNET_REQFLAG_NO_HEADERS); 642 test_request_url(hor, test->url); 643 644 length = sizeof(buffer); 645 res = HttpQueryInfoA(hor, HTTP_QUERY_RAW_HEADERS, buffer, &length, 0x0); 646 ok(res, "HttpQueryInfoA(HTTP_QUERY_RAW_HEADERS) failed with error %d\n", GetLastError()); 647 ok(length == 0 || (length == 1 && !*buffer) /* win10 */, "HTTP_QUERY_RAW_HEADERS: expected length 0, but got %d\n", length); 648 ok(!strcmp(buffer, ""), "HTTP_QUERY_RAW_HEADERS: expected string \"\", but got \"%s\"\n", buffer); 649 650 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 651 CHECK_NOT_NOTIFIED(INTERNET_STATUS_RESOLVING_NAME); 652 CHECK_NOT_NOTIFIED(INTERNET_STATUS_NAME_RESOLVED); 653 SET_OPTIONAL2(INTERNET_STATUS_COOKIE_SENT,2); 654 SET_OPTIONAL2(INTERNET_STATUS_COOKIE_RECEIVED,2); 655 if (first_connection_to_test_url) 656 { 657 SET_EXPECT(INTERNET_STATUS_RESOLVING_NAME); 658 SET_EXPECT(INTERNET_STATUS_NAME_RESOLVED); 659 } 660 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 661 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 662 SET_EXPECT2(INTERNET_STATUS_SENDING_REQUEST, (test->flags & TESTF_REDIRECT) ? 2 : 1); 663 SET_EXPECT2(INTERNET_STATUS_REQUEST_SENT, (test->flags & TESTF_REDIRECT) ? 2 : 1); 664 SET_EXPECT2(INTERNET_STATUS_RECEIVING_RESPONSE, (test->flags & TESTF_REDIRECT) ? 2 : 1); 665 SET_EXPECT2(INTERNET_STATUS_RESPONSE_RECEIVED, (test->flags & TESTF_REDIRECT) ? 2 : 1); 666 if(test->flags & TESTF_REDIRECT) { 667 SET_OPTIONAL2(INTERNET_STATUS_CLOSING_CONNECTION, 2); 668 SET_OPTIONAL2(INTERNET_STATUS_CONNECTION_CLOSED, 2); 669 } 670 SET_EXPECT(INTERNET_STATUS_REDIRECT); 671 SET_OPTIONAL(INTERNET_STATUS_CONNECTING_TO_SERVER); 672 SET_OPTIONAL(INTERNET_STATUS_CONNECTED_TO_SERVER); 673 if (flags & INTERNET_FLAG_ASYNC) 674 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 675 676 if(test->flags & TESTF_COMPRESSED) { 677 BOOL b = TRUE; 678 679 res = InternetSetOptionA(hor, INTERNET_OPTION_HTTP_DECODING, &b, sizeof(b)); 680 ok(res || broken(!res && GetLastError() == ERROR_INTERNET_INVALID_OPTION), 681 "InternetSetOption failed: %u\n", GetLastError()); 682 if(!res) 683 goto abort; 684 } 685 686 test_status_code(hor, 0); 687 688 trace("HttpSendRequestA -->\n"); 689 if(test->post_data) { 690 post_len = strlen(test->post_data); 691 post_data = HeapAlloc(GetProcessHeap(), 0, post_len); 692 memcpy(post_data, test->post_data, post_len); 693 } 694 SetLastError(0xdeadbeef); 695 res = HttpSendRequestA(hor, test->headers, -1, post_data, post_len); 696 if (flags & INTERNET_FLAG_ASYNC) 697 ok(!res && (GetLastError() == ERROR_IO_PENDING), 698 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 699 else 700 ok(res || (GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED), 701 "Synchronous HttpSendRequest returning 0, error %u\n", GetLastError()); 702 trace("HttpSendRequestA <--\n"); 703 704 if (flags & INTERNET_FLAG_ASYNC) { 705 WaitForSingleObject(complete_event, INFINITE); 706 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 707 } 708 HeapFree(GetProcessHeap(), 0, post_data); 709 710 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 711 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_RECEIVED); 712 if (first_connection_to_test_url) 713 { 714 if (! proxy_active()) 715 { 716 CHECK_NOTIFIED(INTERNET_STATUS_RESOLVING_NAME); 717 CHECK_NOTIFIED(INTERNET_STATUS_NAME_RESOLVED); 718 } 719 else 720 { 721 CLEAR_NOTIFIED(INTERNET_STATUS_RESOLVING_NAME); 722 CLEAR_NOTIFIED(INTERNET_STATUS_NAME_RESOLVED); 723 } 724 } 725 else 726 { 727 CHECK_NOT_NOTIFIED(INTERNET_STATUS_RESOLVING_NAME); 728 CHECK_NOT_NOTIFIED(INTERNET_STATUS_NAME_RESOLVED); 729 } 730 CHECK_NOTIFIED2(INTERNET_STATUS_SENDING_REQUEST, (test->flags & TESTF_REDIRECT) ? 2 : 1); 731 CHECK_NOTIFIED2(INTERNET_STATUS_REQUEST_SENT, (test->flags & TESTF_REDIRECT) ? 2 : 1); 732 CHECK_NOTIFIED2(INTERNET_STATUS_RECEIVING_RESPONSE, (test->flags & TESTF_REDIRECT) ? 2 : 1); 733 CHECK_NOTIFIED2(INTERNET_STATUS_RESPONSE_RECEIVED, (test->flags & TESTF_REDIRECT) ? 2 : 1); 734 if(test->flags & TESTF_REDIRECT) 735 CHECK_NOTIFIED(INTERNET_STATUS_REDIRECT); 736 if (flags & INTERNET_FLAG_ASYNC) 737 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 738 /* Sent on WinXP only if first_connection_to_test_url is TRUE, on Win98 always sent */ 739 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 740 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 741 742 test_request_flags(hor, 0); 743 744 length = 100; 745 res = InternetQueryOptionA(hor,INTERNET_OPTION_URL,buffer,&length); 746 ok(res, "InternetQueryOptionA(INTERNET_OPTION_URL) failed with error %d\n", GetLastError()); 747 748 length = sizeof(buffer)-2; 749 memset(buffer, 0x77, sizeof(buffer)); 750 SetLastError(0xdeadbeef); 751 res = HttpQueryInfoA(hor,HTTP_QUERY_RAW_HEADERS,buffer,&length,0x0); 752 ok(res, "HttpQueryInfoA(HTTP_QUERY_RAW_HEADERS) failed with error %d\n", GetLastError()); 753 ok(GetLastError() == 0 || 754 broken(GetLastError() == 0xdeadbeef /* XP/W2K3 */), "Last Error not reset %u\n", GetLastError()); 755 /* show that the function writes data past the length returned */ 756 ok(buffer[length-2], "Expected any header character, got 0x00\n"); 757 ok(!buffer[length-1], "Expected 0x00, got %02X\n", buffer[length-1]); 758 ok(!buffer[length], "Expected 0x00, got %02X\n", buffer[length]); 759 ok(buffer[length+1] == 0x77, "Expected 0x77, got %02X\n", buffer[length+1]); 760 761 length2 = length; 762 res = HttpQueryInfoA(hor,HTTP_QUERY_RAW_HEADERS,buffer,&length2,0x0); 763 ok(!res, "Expected 0x00, got %d\n", res); 764 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "Unexpected last error: %d\n", GetLastError()); 765 ok(length2 == length+1, "Expected %d, got %d\n", length+1, length2); 766 /* the in length of the buffer must be +1 but the length returned does not count this */ 767 length2 = length+1; 768 memset(buffer, 0x77, sizeof(buffer)); 769 res = HttpQueryInfoA(hor,HTTP_QUERY_RAW_HEADERS,buffer,&length2,0x0); 770 ok(res, "HttpQueryInfoA(HTTP_QUERY_RAW_HEADERS) failed with error %d\n", GetLastError()); 771 ok(buffer[length2] == 0x00, "Expected 0x00, got %02X\n", buffer[length2]); 772 ok(buffer[length2+1] == 0x77, "Expected 0x77, got %02X\n", buffer[length2+1]); 773 ok(length2 == length, "Value should not have changed: %d != %d\n", length2, length); 774 775 length = sizeof(wbuffer)-2*sizeof(WCHAR); 776 memset(wbuffer, 0x77, sizeof(wbuffer)); 777 res = HttpQueryInfoW(hor, HTTP_QUERY_RAW_HEADERS, wbuffer, &length, 0x0); 778 ok(res, "HttpQueryInfoW(HTTP_QUERY_RAW_HEADERS) failed with error %d\n", GetLastError()); 779 ok(length % sizeof(WCHAR) == 0, "Expected that length is a multiple of sizeof(WCHAR), got %d.\n", length); 780 length /= sizeof(WCHAR); 781 /* show that the function writes data past the length returned */ 782 ok(wbuffer[length-2], "Expected any header character, got 0x0000\n"); 783 ok(!wbuffer[length-1], "Expected 0x0000, got %04X\n", wbuffer[length-1]); 784 ok(!wbuffer[length], "Expected 0x0000, got %04X\n", wbuffer[length]); 785 ok(wbuffer[length+1] == 0x7777 || broken(wbuffer[length+1] != 0x7777), 786 "Expected 0x7777, got %04X\n", wbuffer[length+1]); 787 788 length2 = length*sizeof(WCHAR); 789 res = HttpQueryInfoW(hor,HTTP_QUERY_RAW_HEADERS,wbuffer,&length2,0x0); 790 ok(!res, "Expected 0x00, got %d\n", res); 791 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "Unexpected last error: %d\n", GetLastError()); 792 ok(length2 % sizeof(WCHAR) == 0, "Expected that length is a multiple of sizeof(WCHAR), got %d.\n", length2); 793 length2 /= sizeof(WCHAR); 794 ok(length2 == length+1, "Expected %d, got %d\n", length+1, length2); 795 /* the in length of the buffer must be +1 but the length returned does not count this */ 796 length2 = (length+1)*sizeof(WCHAR); 797 memset(wbuffer, 0x77, sizeof(wbuffer)); 798 res = HttpQueryInfoW(hor,HTTP_QUERY_RAW_HEADERS,wbuffer,&length2,0x0); 799 ok(res, "HttpQueryInfoW(HTTP_QUERY_RAW_HEADERS) failed with error %d\n", GetLastError()); 800 ok(length2 % sizeof(WCHAR) == 0, "Expected that length is a multiple of sizeof(WCHAR), got %d.\n", length2); 801 length2 /= sizeof(WCHAR); 802 ok(!wbuffer[length2], "Expected 0x0000, got %04X\n", wbuffer[length2]); 803 ok(wbuffer[length2+1] == 0x7777, "Expected 0x7777, got %04X\n", wbuffer[length2+1]); 804 ok(length2 == length, "Value should not have changed: %d != %d\n", length2, length); 805 806 test_request_url(hor, test->redirected_url); 807 808 index = 0; 809 length = 0; 810 SetLastError(0xdeadbeef); 811 ok(HttpQueryInfoA(hor,HTTP_QUERY_CONTENT_LENGTH,NULL,&length,&index) == FALSE,"Query worked\n"); 812 if(test->flags & TESTF_COMPRESSED) 813 ok(GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, 814 "expected ERROR_HTTP_HEADER_NOT_FOUND, got %u\n", GetLastError()); 815 ok(index == 0, "Index was incremented\n"); 816 817 index = 0; 818 length = 16; 819 res = HttpQueryInfoA(hor,HTTP_QUERY_CONTENT_LENGTH,&buffer,&length,&index); 820 trace("Option HTTP_QUERY_CONTENT_LENGTH -> %i %s (%u)\n",res,buffer,GetLastError()); 821 if(test->flags & TESTF_COMPRESSED) 822 { 823 ok(!res && GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, 824 "expected ERROR_HTTP_HEADER_NOT_FOUND, got %x (%u)\n", res, GetLastError()); 825 contents_length = 0; 826 } 827 else 828 { 829 contents_length = atoi(buffer); 830 } 831 ok(!res || index == 1, "Index was not incremented although result is %x (index = %u)\n", res, index); 832 833 length = 64; 834 *buffer = 0; 835 res = HttpQueryInfoA(hor,HTTP_QUERY_ACCEPT_RANGES,&buffer,&length,0x0); 836 trace("Option HTTP_QUERY_ACCEPT_RANGES -> %i %s (%u)\n",res,buffer,GetLastError()); 837 accepts_ranges = res && !strcmp(buffer, "bytes"); 838 839 length = 100; 840 res = HttpQueryInfoA(hor,HTTP_QUERY_CONTENT_TYPE,buffer,&length,0x0); 841 buffer[length]=0; 842 trace("Option HTTP_QUERY_CONTENT_TYPE -> %i %s\n",res,buffer); 843 844 length = 100; 845 res = HttpQueryInfoA(hor,HTTP_QUERY_CONTENT_ENCODING,buffer,&length,0x0); 846 buffer[length]=0; 847 trace("Option HTTP_QUERY_CONTENT_ENCODING -> %i %s\n",res,buffer); 848 849 SetLastError(0xdeadbeef); 850 length = InternetSetFilePointer(hor, 0, NULL, FILE_END, 0); 851 not_supported = length == INVALID_SET_FILE_POINTER 852 && GetLastError() == ERROR_INTERNET_INVALID_OPERATION; 853 if (accepts_ranges) 854 todo_wine ok((length == contents_length && (GetLastError() == ERROR_SUCCESS 855 || broken(GetLastError() == 0xdeadbeef))) || broken(not_supported), 856 "Got unexpected length %#x, GetLastError() %u, contents_length %u, accepts_ranges %#x.\n", 857 length, GetLastError(), contents_length, accepts_ranges); 858 else 859 ok(not_supported, "Got unexpected length %#x, GetLastError() %u.\n", length, GetLastError()); 860 861 if (length != INVALID_SET_FILE_POINTER) 862 { 863 SetLastError(0xdeadbeef); 864 length = InternetSetFilePointer(hor, 0, NULL, FILE_BEGIN, 0); 865 ok(!length && (GetLastError() == ERROR_SUCCESS || broken(GetLastError() == 0xdeadbeef)), 866 "Got unexpected length %#x, GetLastError() %u.\n", length, GetLastError()); 867 } 868 869 SetLastError(0xdeadbeef); 870 res = InternetReadFile(NULL, buffer, 100, &length); 871 ok(!res, "InternetReadFile should have failed\n"); 872 ok(GetLastError() == ERROR_INVALID_HANDLE, 873 "InternetReadFile should have set last error to ERROR_INVALID_HANDLE instead of %u\n", 874 GetLastError()); 875 876 length = 100; 877 if(winetest_debug > 1) 878 trace("Entering Query loop\n"); 879 880 while (TRUE) 881 { 882 if (flags & INTERNET_FLAG_ASYNC) 883 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 884 885 /* IE11 calls those in InternetQueryDataAvailable call. */ 886 SET_OPTIONAL(INTERNET_STATUS_RECEIVING_RESPONSE); 887 SET_OPTIONAL(INTERNET_STATUS_RESPONSE_RECEIVED); 888 889 length = 0; 890 res = InternetQueryDataAvailable(hor,&length,0x0,0x0); 891 892 CLEAR_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 893 894 if (flags & INTERNET_FLAG_ASYNC) 895 { 896 if (res) 897 { 898 CHECK_NOT_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 899 if(exlen) { 900 ok(length >= exlen, "length %u < exlen %u\n", length, exlen); 901 exlen = 0; 902 } 903 } 904 else if (GetLastError() == ERROR_IO_PENDING) 905 { 906 if(winetest_debug > 1) 907 trace("pending\n"); 908 /* on some tests, InternetQueryDataAvailable returns non-zero length and ERROR_IO_PENDING */ 909 if(!(test->flags & TESTF_CHUNKED)) 910 ok(!length, "InternetQueryDataAvailable returned ERROR_IO_PENDING and %u length\n", length); 911 WaitForSingleObject(complete_event, INFINITE); 912 exlen = length; 913 ok(exlen, "length = 0\n"); 914 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 915 CLEAR_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 916 ok(req_error, "req_error = 0\n"); 917 continue; 918 }else { 919 ok(0, "InternetQueryDataAvailable failed: %u\n", GetLastError()); 920 } 921 }else { 922 ok(res, "InternetQueryDataAvailable failed: %u\n", GetLastError()); 923 } 924 CLEAR_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 925 926 if(winetest_debug > 1) 927 trace("length %u\n", length); 928 if(test->flags & TESTF_CHUNKED) 929 ok(length <= 8192, "length = %d, expected <= 8192\n", length); 930 if (length) 931 { 932 char *buffer; 933 buffer = HeapAlloc(GetProcessHeap(),0,length+1); 934 935 res = InternetReadFile(hor,buffer,length,&length); 936 937 buffer[length]=0; 938 939 if(winetest_debug > 1) 940 trace("ReadFile -> %s %i\n", res ? "TRUE" : "FALSE", length); 941 942 if(test->content) 943 ok(!strcmp(buffer, test->content), "buffer = '%s', expected '%s'\n", buffer, test->content); 944 HeapFree(GetProcessHeap(),0,buffer); 945 }else { 946 ok(!on_async, "Returned zero size in response to request complete\n"); 947 break; 948 } 949 on_async = FALSE; 950 } 951 if(test->flags & TESTF_REDIRECT) { 952 CHECK_NOTIFIED2(INTERNET_STATUS_CLOSING_CONNECTION, 2); 953 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTION_CLOSED, 2); 954 } 955 abort: 956 if(winetest_debug > 1) 957 trace("aborting\n"); 958 close_async_handle(hi, 2); 959 first_connection_to_test_url = FALSE; 960 } 961 962 static void InternetReadFile_chunked_test(void) 963 { 964 BOOL res; 965 CHAR buffer[4000]; 966 DWORD length, got; 967 const char *types[2] = { "*", NULL }; 968 HINTERNET hi, hic = 0, hor = 0; 969 970 trace("Starting InternetReadFile chunked test\n"); 971 972 trace("InternetOpenA <--\n"); 973 hi = InternetOpenA("", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0); 974 ok((hi != 0x0),"InternetOpen failed with error %u\n", GetLastError()); 975 trace("InternetOpenA -->\n"); 976 977 if (hi == 0x0) goto abort; 978 979 trace("InternetConnectA <--\n"); 980 hic=InternetConnectA(hi, "test.winehq.org", INTERNET_INVALID_PORT_NUMBER, 981 NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 982 ok((hic != 0x0),"InternetConnect failed with error %u\n", GetLastError()); 983 trace("InternetConnectA -->\n"); 984 985 if (hic == 0x0) goto abort; 986 987 trace("HttpOpenRequestA <--\n"); 988 hor = HttpOpenRequestA(hic, "GET", "/tests/chunked", NULL, NULL, types, 989 INTERNET_FLAG_KEEP_CONNECTION | INTERNET_FLAG_RELOAD, 990 0xdeadbead); 991 if (hor == 0x0 && GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED) { 992 /* 993 * If the internet name can't be resolved we are probably behind 994 * a firewall or in some other way not directly connected to the 995 * Internet. Not enough reason to fail the test. Just ignore and 996 * abort. 997 */ 998 } else { 999 ok((hor != 0x0),"HttpOpenRequest failed with error %u\n", GetLastError()); 1000 } 1001 trace("HttpOpenRequestA -->\n"); 1002 1003 if (hor == 0x0) goto abort; 1004 1005 trace("HttpSendRequestA -->\n"); 1006 SetLastError(0xdeadbeef); 1007 res = HttpSendRequestA(hor, "", -1, NULL, 0); 1008 ok(res || (GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED), 1009 "Synchronous HttpSendRequest returning 0, error %u\n", GetLastError()); 1010 trace("HttpSendRequestA <--\n"); 1011 1012 test_request_flags(hor, 0); 1013 1014 length = 100; 1015 res = HttpQueryInfoA(hor,HTTP_QUERY_CONTENT_TYPE,buffer,&length,0x0); 1016 buffer[length]=0; 1017 trace("Option CONTENT_TYPE -> %i %s\n",res,buffer); 1018 1019 SetLastError( 0xdeadbeef ); 1020 length = 100; 1021 res = HttpQueryInfoA(hor,HTTP_QUERY_TRANSFER_ENCODING,buffer,&length,0x0); 1022 buffer[length]=0; 1023 trace("Option TRANSFER_ENCODING -> %i %s\n",res,buffer); 1024 ok( res || ( proxy_active() && GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND ), 1025 "Failed to get TRANSFER_ENCODING option, error %u\n", GetLastError() ); 1026 ok( !strcmp( buffer, "chunked" ) || ( ! res && proxy_active() && GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND ), 1027 "Wrong transfer encoding '%s'\n", buffer ); 1028 1029 SetLastError( 0xdeadbeef ); 1030 length = 16; 1031 res = HttpQueryInfoA(hor,HTTP_QUERY_CONTENT_LENGTH,&buffer,&length,0x0); 1032 ok( !res, "Found CONTENT_LENGTH option '%s'\n", buffer ); 1033 ok( GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, "Wrong error %u\n", GetLastError() ); 1034 1035 length = 100; 1036 trace("Entering Query loop\n"); 1037 1038 while (TRUE) 1039 { 1040 res = InternetQueryDataAvailable(hor,&length,0x0,0x0); 1041 ok(!(!res && length != 0),"InternetQueryDataAvailable failed with non-zero length\n"); 1042 ok(res, "InternetQueryDataAvailable failed, error %d\n", GetLastError()); 1043 trace("got %u available\n",length); 1044 if (length) 1045 { 1046 char *buffer = HeapAlloc(GetProcessHeap(),0,length+1); 1047 1048 SetLastError(0xdeadbeef); 1049 res = InternetReadFile(hor,buffer,length,&got); 1050 ok(GetLastError() == 0 || 1051 broken(GetLastError() == 0xdeadbeef /* XP/W2K3 */), "Last Error not reset %u\n", GetLastError()); 1052 1053 buffer[got]=0; 1054 trace("ReadFile -> %i %i\n",res,got); 1055 ok( length == got, "only got %u of %u available\n", got, length ); 1056 ok( buffer[got-1] == '\n', "received partial line '%s'\n", buffer ); 1057 1058 HeapFree(GetProcessHeap(),0,buffer); 1059 if (!got) break; 1060 } 1061 if (length == 0) 1062 { 1063 got = 0xdeadbeef; 1064 SetLastError(0xdeadbeef); 1065 res = InternetReadFile( hor, buffer, 1, &got ); 1066 ok( res, "InternetReadFile failed: %u\n", GetLastError() ); 1067 ok(GetLastError() == 0 || 1068 broken(GetLastError() == 0xdeadbeef /* XP/W2K3 */), "Last Error not reset %u\n", GetLastError()); 1069 ok( !got, "got %u\n", got ); 1070 break; 1071 } 1072 } 1073 abort: 1074 trace("aborting\n"); 1075 if (hor != 0x0) { 1076 res = InternetCloseHandle(hor); 1077 ok (res, "InternetCloseHandle of handle opened by HttpOpenRequestA failed\n"); 1078 } 1079 if (hi != 0x0) { 1080 res = InternetCloseHandle(hi); 1081 ok (res, "InternetCloseHandle of handle opened by InternetOpenA failed\n"); 1082 } 1083 } 1084 1085 static void InternetReadFileExA_test(int flags) 1086 { 1087 DWORD rc; 1088 DWORD length; 1089 const char *types[2] = { "*", NULL }; 1090 HINTERNET hi, hic = 0, hor = 0; 1091 INTERNET_BUFFERSA inetbuffers; 1092 1093 trace("Starting InternetReadFileExA test with flags 0x%x\n",flags); 1094 reset_events(); 1095 1096 trace("InternetOpenA <--\n"); 1097 hi = InternetOpenA("", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, flags); 1098 ok((hi != 0x0),"InternetOpen failed with error %u\n", GetLastError()); 1099 trace("InternetOpenA -->\n"); 1100 1101 if (hi == 0x0) goto abort; 1102 1103 pInternetSetStatusCallbackA(hi,&callback); 1104 1105 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 1106 1107 trace("InternetConnectA <--\n"); 1108 hic=InternetConnectA(hi, "test.winehq.org", INTERNET_INVALID_PORT_NUMBER, 1109 NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 1110 ok((hic != 0x0),"InternetConnect failed with error %u\n", GetLastError()); 1111 trace("InternetConnectA -->\n"); 1112 1113 if (hic == 0x0) goto abort; 1114 1115 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 1116 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 1117 1118 trace("HttpOpenRequestA <--\n"); 1119 hor = HttpOpenRequestA(hic, "GET", "/tests/redirect", NULL, NULL, types, 1120 INTERNET_FLAG_KEEP_CONNECTION | INTERNET_FLAG_RELOAD, 1121 0xdeadbead); 1122 if (hor == 0x0 && GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED) { 1123 /* 1124 * If the internet name can't be resolved we are probably behind 1125 * a firewall or in some other way not directly connected to the 1126 * Internet. Not enough reason to fail the test. Just ignore and 1127 * abort. 1128 */ 1129 } else { 1130 ok((hor != 0x0),"HttpOpenRequest failed with error %u\n", GetLastError()); 1131 } 1132 trace("HttpOpenRequestA -->\n"); 1133 1134 if (hor == 0x0) goto abort; 1135 1136 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 1137 CHECK_NOT_NOTIFIED(INTERNET_STATUS_RESOLVING_NAME); 1138 CHECK_NOT_NOTIFIED(INTERNET_STATUS_NAME_RESOLVED); 1139 if (first_connection_to_test_url) 1140 { 1141 SET_EXPECT(INTERNET_STATUS_RESOLVING_NAME); 1142 SET_EXPECT(INTERNET_STATUS_NAME_RESOLVED); 1143 } 1144 SET_OPTIONAL2(INTERNET_STATUS_COOKIE_SENT, 2); 1145 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 1146 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 1147 SET_EXPECT2(INTERNET_STATUS_SENDING_REQUEST, 2); 1148 SET_EXPECT2(INTERNET_STATUS_REQUEST_SENT, 2); 1149 SET_EXPECT2(INTERNET_STATUS_RECEIVING_RESPONSE, 2); 1150 SET_EXPECT2(INTERNET_STATUS_RESPONSE_RECEIVED, 2); 1151 SET_OPTIONAL2(INTERNET_STATUS_CLOSING_CONNECTION, 2); 1152 SET_OPTIONAL2(INTERNET_STATUS_CONNECTION_CLOSED, 2); 1153 SET_EXPECT(INTERNET_STATUS_REDIRECT); 1154 SET_OPTIONAL(INTERNET_STATUS_CONNECTING_TO_SERVER); 1155 SET_OPTIONAL(INTERNET_STATUS_CONNECTED_TO_SERVER); 1156 if (flags & INTERNET_FLAG_ASYNC) 1157 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 1158 else 1159 SET_WINE_ALLOW(INTERNET_STATUS_REQUEST_COMPLETE); 1160 1161 trace("HttpSendRequestA -->\n"); 1162 SetLastError(0xdeadbeef); 1163 rc = HttpSendRequestA(hor, "", -1, NULL, 0); 1164 if (flags & INTERNET_FLAG_ASYNC) 1165 ok(((rc == 0)&&(GetLastError() == ERROR_IO_PENDING)), 1166 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 1167 else 1168 ok((rc != 0) || GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED, 1169 "Synchronous HttpSendRequest returning 0, error %u\n", GetLastError()); 1170 trace("HttpSendRequestA <--\n"); 1171 1172 if (!rc && (GetLastError() == ERROR_IO_PENDING)) { 1173 WaitForSingleObject(complete_event, INFINITE); 1174 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 1175 } 1176 1177 if (first_connection_to_test_url) 1178 { 1179 CHECK_NOTIFIED(INTERNET_STATUS_RESOLVING_NAME); 1180 CHECK_NOTIFIED(INTERNET_STATUS_NAME_RESOLVED); 1181 } 1182 else 1183 { 1184 CHECK_NOT_NOTIFIED(INTERNET_STATUS_RESOLVING_NAME); 1185 CHECK_NOT_NOTIFIED(INTERNET_STATUS_NAME_RESOLVED); 1186 } 1187 CHECK_NOTIFIED2(INTERNET_STATUS_SENDING_REQUEST, 2); 1188 CHECK_NOTIFIED2(INTERNET_STATUS_REQUEST_SENT, 2); 1189 CHECK_NOTIFIED2(INTERNET_STATUS_RECEIVING_RESPONSE, 2); 1190 CHECK_NOTIFIED2(INTERNET_STATUS_RESPONSE_RECEIVED, 2); 1191 CHECK_NOTIFIED2(INTERNET_STATUS_CLOSING_CONNECTION, 2); 1192 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTION_CLOSED, 2); 1193 CHECK_NOTIFIED(INTERNET_STATUS_REDIRECT); 1194 if (flags & INTERNET_FLAG_ASYNC) 1195 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 1196 else 1197 todo_wine CHECK_NOT_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 1198 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 1199 /* Sent on WinXP only if first_connection_to_test_url is TRUE, on Win98 always sent */ 1200 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 1201 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 1202 1203 if(is_ie7plus) { 1204 rc = InternetReadFileExW(hor, NULL, 0, 0xdeadcafe); 1205 ok(!rc && (GetLastError() == ERROR_INVALID_PARAMETER), 1206 "InternetReadFileEx should have failed with ERROR_INVALID_PARAMETER instead of %s, %u\n", 1207 rc ? "TRUE" : "FALSE", GetLastError()); 1208 } 1209 1210 /* tests invalid dwStructSize */ 1211 inetbuffers.dwStructSize = sizeof(inetbuffers)+1; 1212 inetbuffers.lpcszHeader = NULL; 1213 inetbuffers.dwHeadersLength = 0; 1214 inetbuffers.dwBufferLength = 10; 1215 inetbuffers.lpvBuffer = HeapAlloc(GetProcessHeap(), 0, 10); 1216 inetbuffers.dwOffsetHigh = 1234; 1217 inetbuffers.dwOffsetLow = 5678; 1218 rc = InternetReadFileExA(hor, &inetbuffers, 0, 0xdeadcafe); 1219 ok(!rc && (GetLastError() == ERROR_INVALID_PARAMETER), 1220 "InternetReadFileEx should have failed with ERROR_INVALID_PARAMETER instead of %s, %u\n", 1221 rc ? "TRUE" : "FALSE", GetLastError()); 1222 HeapFree(GetProcessHeap(), 0, inetbuffers.lpvBuffer); 1223 1224 test_request_flags(hor, 0); 1225 1226 /* tests to see whether lpcszHeader is used - it isn't */ 1227 inetbuffers.dwStructSize = sizeof(inetbuffers); 1228 inetbuffers.lpcszHeader = (LPCSTR)0xdeadbeef; 1229 inetbuffers.dwHeadersLength = 255; 1230 inetbuffers.dwBufferLength = 0; 1231 inetbuffers.lpvBuffer = NULL; 1232 inetbuffers.dwOffsetHigh = 1234; 1233 inetbuffers.dwOffsetLow = 5678; 1234 rc = InternetReadFileExA(hor, &inetbuffers, 0, 0xdeadcafe); 1235 ok(rc, "InternetReadFileEx failed with error %u\n", GetLastError()); 1236 trace("read %i bytes\n", inetbuffers.dwBufferLength); 1237 1238 rc = InternetReadFileExA(NULL, &inetbuffers, 0, 0xdeadcafe); 1239 ok(!rc && (GetLastError() == ERROR_INVALID_HANDLE), 1240 "InternetReadFileEx should have failed with ERROR_INVALID_HANDLE instead of %s, %u\n", 1241 rc ? "TRUE" : "FALSE", GetLastError()); 1242 1243 length = 0; 1244 trace("Entering Query loop\n"); 1245 1246 while (TRUE) 1247 { 1248 inetbuffers.dwStructSize = sizeof(inetbuffers); 1249 inetbuffers.dwBufferLength = 1024; 1250 inetbuffers.lpvBuffer = HeapAlloc(GetProcessHeap(), 0, inetbuffers.dwBufferLength+1); 1251 inetbuffers.dwOffsetHigh = 1234; 1252 inetbuffers.dwOffsetLow = 5678; 1253 1254 SET_WINE_ALLOW(INTERNET_STATUS_RECEIVING_RESPONSE); 1255 SET_WINE_ALLOW(INTERNET_STATUS_RESPONSE_RECEIVED); 1256 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 1257 rc = InternetReadFileExA(hor, &inetbuffers, IRF_ASYNC | IRF_USE_CONTEXT, 0xcafebabe); 1258 if (!rc) 1259 { 1260 if (GetLastError() == ERROR_IO_PENDING) 1261 { 1262 trace("InternetReadFileEx -> PENDING\n"); 1263 ok(flags & INTERNET_FLAG_ASYNC, 1264 "Should not get ERROR_IO_PENDING without INTERNET_FLAG_ASYNC\n"); 1265 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 1266 WaitForSingleObject(complete_event, INFINITE); 1267 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 1268 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 1269 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 1270 } 1271 else 1272 { 1273 trace("InternetReadFileEx -> FAILED %u\n", GetLastError()); 1274 break; 1275 } 1276 } 1277 else 1278 { 1279 trace("InternetReadFileEx -> SUCCEEDED\n"); 1280 CHECK_NOT_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 1281 if (inetbuffers.dwBufferLength) 1282 { 1283 CHECK_NOT_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 1284 CHECK_NOT_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 1285 } 1286 else 1287 { 1288 /* Win98 still sends these when 0 bytes are read, WinXP does not */ 1289 CLEAR_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 1290 CLEAR_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 1291 } 1292 } 1293 1294 trace("read %i bytes\n", inetbuffers.dwBufferLength); 1295 ((char *)inetbuffers.lpvBuffer)[inetbuffers.dwBufferLength] = '\0'; 1296 1297 ok(inetbuffers.dwOffsetHigh == 1234 && inetbuffers.dwOffsetLow == 5678, 1298 "InternetReadFileEx sets offsets to 0x%x%08x\n", 1299 inetbuffers.dwOffsetHigh, inetbuffers.dwOffsetLow); 1300 1301 HeapFree(GetProcessHeap(), 0, inetbuffers.lpvBuffer); 1302 1303 if (!inetbuffers.dwBufferLength) 1304 break; 1305 1306 length += inetbuffers.dwBufferLength; 1307 } 1308 ok(length > 0, "failed to read any of the document\n"); 1309 trace("Finished. Read %d bytes\n", length); 1310 1311 abort: 1312 close_async_handle(hi, 2); 1313 first_connection_to_test_url = FALSE; 1314 } 1315 1316 static void InternetOpenUrlA_test(void) 1317 { 1318 HINTERNET myhinternet, myhttp; 1319 char buffer[0x400]; 1320 DWORD size, readbytes, totalbytes=0; 1321 BOOL ret; 1322 1323 ret = DeleteUrlCacheEntryA(TEST_URL); 1324 ok(ret || GetLastError() == ERROR_FILE_NOT_FOUND, 1325 "DeleteUrlCacheEntry returned %x, GetLastError() = %d\n", ret, GetLastError()); 1326 1327 myhinternet = InternetOpenA("Winetest",0,NULL,NULL,INTERNET_FLAG_NO_CACHE_WRITE); 1328 ok((myhinternet != 0), "InternetOpen failed, error %u\n",GetLastError()); 1329 size = 0x400; 1330 ret = InternetCanonicalizeUrlA(TEST_URL, buffer, &size,ICU_BROWSER_MODE); 1331 ok( ret, "InternetCanonicalizeUrl failed, error %u\n",GetLastError()); 1332 1333 SetLastError(0); 1334 myhttp = InternetOpenUrlA(myhinternet, TEST_URL, 0, 0, 1335 INTERNET_FLAG_RELOAD|INTERNET_FLAG_NO_CACHE_WRITE|INTERNET_FLAG_TRANSFER_BINARY,0); 1336 if (GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED) 1337 return; /* WinXP returns this when not connected to the net */ 1338 ok((myhttp != 0),"InternetOpenUrl failed, error %u\n",GetLastError()); 1339 ret = InternetReadFile(myhttp, buffer,0x400,&readbytes); 1340 ok( ret, "InternetReadFile failed, error %u\n",GetLastError()); 1341 totalbytes += readbytes; 1342 while (readbytes && InternetReadFile(myhttp, buffer,0x400,&readbytes)) 1343 totalbytes += readbytes; 1344 trace("read 0x%08x bytes\n",totalbytes); 1345 1346 InternetCloseHandle(myhttp); 1347 InternetCloseHandle(myhinternet); 1348 1349 ret = DeleteUrlCacheEntryA(TEST_URL); 1350 ok(!ret && GetLastError() == ERROR_FILE_NOT_FOUND, "INTERNET_FLAG_NO_CACHE_WRITE flag doesn't work\n"); 1351 } 1352 1353 static void HttpSendRequestEx_test(void) 1354 { 1355 HINTERNET hSession; 1356 HINTERNET hConnect; 1357 HINTERNET hRequest; 1358 1359 INTERNET_BUFFERSA BufferIn; 1360 DWORD dwBytesWritten, dwBytesRead, error; 1361 CHAR szBuffer[256]; 1362 int i; 1363 BOOL ret; 1364 1365 static char szPostData[] = "mode=Test"; 1366 static const char szContentType[] = "Content-Type: application/x-www-form-urlencoded"; 1367 1368 hSession = InternetOpenA("Wine Regression Test", 1369 INTERNET_OPEN_TYPE_PRECONFIG,NULL,NULL,0); 1370 ok( hSession != NULL ,"Unable to open Internet session\n"); 1371 hConnect = InternetConnectA(hSession, "test.winehq.org", 1372 INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 1373 0); 1374 ok( hConnect != NULL, "Unable to connect to http://test.winehq.org\n"); 1375 hRequest = HttpOpenRequestA(hConnect, "POST", "/tests/post.php", 1376 NULL, NULL, NULL, INTERNET_FLAG_NO_CACHE_WRITE, 0); 1377 if (!hRequest && GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED) 1378 { 1379 skip( "Network unreachable, skipping test\n" ); 1380 goto done; 1381 } 1382 ok( hRequest != NULL, "Failed to open request handle err %u\n", GetLastError()); 1383 1384 test_request_flags(hRequest, INTERNET_REQFLAG_NO_HEADERS); 1385 1386 BufferIn.dwStructSize = sizeof(BufferIn); 1387 BufferIn.Next = (INTERNET_BUFFERSA*)0xdeadcab; 1388 BufferIn.lpcszHeader = szContentType; 1389 BufferIn.dwHeadersLength = sizeof(szContentType)-1; 1390 BufferIn.dwHeadersTotal = sizeof(szContentType)-1; 1391 BufferIn.lpvBuffer = szPostData; 1392 BufferIn.dwBufferLength = 3; 1393 BufferIn.dwBufferTotal = sizeof(szPostData)-1; 1394 BufferIn.dwOffsetLow = 0; 1395 BufferIn.dwOffsetHigh = 0; 1396 1397 SetLastError(0xdeadbeef); 1398 ret = HttpSendRequestExA(hRequest, &BufferIn, NULL, 0 ,0); 1399 error = GetLastError(); 1400 ok(ret, "HttpSendRequestEx Failed with error %u\n", error); 1401 ok(error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", error); 1402 1403 test_request_flags(hRequest, INTERNET_REQFLAG_NO_HEADERS); 1404 1405 for (i = 3; szPostData[i]; i++) 1406 ok(InternetWriteFile(hRequest, &szPostData[i], 1, &dwBytesWritten), 1407 "InternetWriteFile failed\n"); 1408 1409 test_request_flags(hRequest, INTERNET_REQFLAG_NO_HEADERS); 1410 1411 ok(HttpEndRequestA(hRequest, NULL, 0, 0), "HttpEndRequest Failed\n"); 1412 1413 test_request_flags(hRequest, 0); 1414 1415 ok(InternetReadFile(hRequest, szBuffer, 255, &dwBytesRead), 1416 "Unable to read response\n"); 1417 szBuffer[dwBytesRead] = 0; 1418 1419 ok(dwBytesRead == 13,"Read %u bytes instead of 13\n",dwBytesRead); 1420 ok(strncmp(szBuffer,"mode => Test\n",dwBytesRead)==0 || broken(proxy_active()),"Got string %s\n",szBuffer); 1421 1422 ok(InternetCloseHandle(hRequest), "Close request handle failed\n"); 1423 done: 1424 ok(InternetCloseHandle(hConnect), "Close connect handle failed\n"); 1425 ok(InternetCloseHandle(hSession), "Close session handle failed\n"); 1426 } 1427 1428 static void InternetOpenRequest_test(void) 1429 { 1430 HINTERNET session, connect, request; 1431 static const char *types[] = { "*", "", NULL }; 1432 static const WCHAR slash[] = {'/', 0}, any[] = {'*', 0}, empty[] = {0}; 1433 static const WCHAR *typesW[] = { any, empty, NULL }; 1434 BOOL ret; 1435 1436 session = InternetOpenA("Wine Regression Test", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0); 1437 ok(session != NULL ,"Unable to open Internet session\n"); 1438 1439 connect = InternetConnectA(session, NULL, INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, 1440 INTERNET_SERVICE_HTTP, 0, 0); 1441 ok(connect == NULL, "InternetConnectA should have failed\n"); 1442 ok(GetLastError() == ERROR_INVALID_PARAMETER, "InternetConnectA with NULL server named should have failed with ERROR_INVALID_PARAMETER instead of %d\n", GetLastError()); 1443 1444 connect = InternetConnectA(session, "", INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, 1445 INTERNET_SERVICE_HTTP, 0, 0); 1446 ok(connect == NULL, "InternetConnectA should have failed\n"); 1447 ok(GetLastError() == ERROR_INVALID_PARAMETER, "InternetConnectA with blank server named should have failed with ERROR_INVALID_PARAMETER instead of %d\n", GetLastError()); 1448 1449 connect = InternetConnectA(session, "test.winehq.org", INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, 1450 INTERNET_SERVICE_HTTP, 0, 0); 1451 ok(connect != NULL, "Unable to connect to http://test.winehq.org with error %d\n", GetLastError()); 1452 1453 request = HttpOpenRequestA(connect, NULL, "/", NULL, NULL, types, INTERNET_FLAG_NO_CACHE_WRITE, 0); 1454 if (!request && GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED) 1455 { 1456 skip( "Network unreachable, skipping test\n" ); 1457 goto done; 1458 } 1459 ok(request != NULL, "Failed to open request handle err %u\n", GetLastError()); 1460 1461 ret = HttpSendRequestW(request, NULL, 0, NULL, 0); 1462 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 1463 ok(InternetCloseHandle(request), "Close request handle failed\n"); 1464 1465 request = HttpOpenRequestW(connect, NULL, slash, NULL, NULL, typesW, INTERNET_FLAG_NO_CACHE_WRITE, 0); 1466 ok(request != NULL, "Failed to open request handle err %u\n", GetLastError()); 1467 1468 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 1469 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 1470 ok(InternetCloseHandle(request), "Close request handle failed\n"); 1471 1472 done: 1473 ok(InternetCloseHandle(connect), "Close connect handle failed\n"); 1474 ok(InternetCloseHandle(session), "Close session handle failed\n"); 1475 } 1476 1477 static void test_cache_read(void) 1478 { 1479 HINTERNET session, connection, req; 1480 FILETIME now, tomorrow, yesterday; 1481 BYTE content[1000], buf[2000]; 1482 char file_path[MAX_PATH]; 1483 ULARGE_INTEGER li; 1484 HANDLE file; 1485 DWORD size; 1486 unsigned i; 1487 BOOL res; 1488 1489 static const char cache_only_url[] = "http://test.winehq.org/tests/cache-only"; 1490 BYTE cache_headers[] = "HTTP/1.1 200 OK\r\n\r\n"; 1491 1492 trace("Testing cache read...\n"); 1493 reset_events(); 1494 1495 for(i = 0; i < sizeof(content); i++) 1496 content[i] = '0' + (i%10); 1497 1498 GetSystemTimeAsFileTime(&now); 1499 li.u.HighPart = now.dwHighDateTime; 1500 li.u.LowPart = now.dwLowDateTime; 1501 li.QuadPart += (LONGLONG)10000000 * 3600 * 24; 1502 tomorrow.dwHighDateTime = li.u.HighPart; 1503 tomorrow.dwLowDateTime = li.u.LowPart; 1504 li.QuadPart -= (LONGLONG)10000000 * 3600 * 24 * 2; 1505 yesterday.dwHighDateTime = li.u.HighPart; 1506 yesterday.dwLowDateTime = li.u.LowPart; 1507 1508 res = CreateUrlCacheEntryA(cache_only_url, sizeof(content), "", file_path, 0); 1509 ok(res, "CreateUrlCacheEntryA failed: %u\n", GetLastError()); 1510 1511 file = CreateFileA(file_path, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); 1512 ok(file != INVALID_HANDLE_VALUE, "CreateFile failed\n"); 1513 1514 WriteFile(file, content, sizeof(content), &size, NULL); 1515 CloseHandle(file); 1516 1517 res = CommitUrlCacheEntryA(cache_only_url, file_path, tomorrow, yesterday, NORMAL_CACHE_ENTRY, 1518 cache_headers, sizeof(cache_headers)-1, "", 0); 1519 ok(res, "CommitUrlCacheEntryA failed: %u\n", GetLastError()); 1520 1521 session = InternetOpenA("", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, INTERNET_FLAG_ASYNC); 1522 ok(session != NULL,"InternetOpen failed with error %u\n", GetLastError()); 1523 1524 pInternetSetStatusCallbackA(session, callback); 1525 1526 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 1527 connection = InternetConnectA(session, "test.winehq.org", INTERNET_DEFAULT_HTTP_PORT, 1528 NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 1529 ok(connection != NULL,"InternetConnect failed with error %u\n", GetLastError()); 1530 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 1531 1532 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 1533 req = HttpOpenRequestA(connection, "GET", "/tests/cache-only", NULL, NULL, NULL, 0, 0xdeadbead); 1534 ok(req != NULL, "HttpOpenRequest failed: %u\n", GetLastError()); 1535 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 1536 1537 SET_WINE_ALLOW(INTERNET_STATUS_CONNECTING_TO_SERVER); 1538 SET_WINE_ALLOW(INTERNET_STATUS_CONNECTED_TO_SERVER); 1539 SET_WINE_ALLOW(INTERNET_STATUS_SENDING_REQUEST); 1540 SET_WINE_ALLOW(INTERNET_STATUS_REQUEST_SENT); 1541 SET_WINE_ALLOW(INTERNET_STATUS_RECEIVING_RESPONSE); 1542 SET_WINE_ALLOW(INTERNET_STATUS_RESPONSE_RECEIVED); 1543 SET_WINE_ALLOW(INTERNET_STATUS_REQUEST_COMPLETE); 1544 1545 res = HttpSendRequestA(req, NULL, -1, NULL, 0); 1546 todo_wine 1547 ok(res, "HttpSendRequest failed: %u\n", GetLastError()); 1548 1549 if(res) { 1550 size = 0; 1551 res = InternetQueryDataAvailable(req, &size, 0, 0); 1552 ok(res, "InternetQueryDataAvailable failed: %u\n", GetLastError()); 1553 ok(size == sizeof(content), "size = %u\n", size); 1554 1555 size = sizeof(buf); 1556 res = InternetReadFile(req, buf, sizeof(buf), &size); 1557 ok(res, "InternetReadFile failed: %u\n", GetLastError()); 1558 ok(size == sizeof(content), "size = %u\n", size); 1559 ok(!memcmp(content, buf, sizeof(content)), "unexpected content\n"); 1560 } 1561 1562 close_async_handle(session, 2); 1563 1564 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 1565 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 1566 CLEAR_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 1567 CLEAR_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 1568 CLEAR_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 1569 CLEAR_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 1570 CLEAR_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 1571 1572 res = DeleteUrlCacheEntryA(cache_only_url); 1573 ok(res, "DeleteUrlCacheEntryA failed: %u\n", GetLastError()); 1574 } 1575 1576 static void test_http_cache(void) 1577 { 1578 HINTERNET session, connect, request; 1579 char file_name[MAX_PATH], url[INTERNET_MAX_URL_LENGTH]; 1580 DWORD size, file_size; 1581 BYTE buf[100]; 1582 HANDLE file; 1583 BOOL ret; 1584 FILETIME filetime_zero = {0}; 1585 1586 static const char cached_content[] = "data read from cache"; 1587 static const char *types[] = { "*", "", NULL }; 1588 1589 session = InternetOpenA("Wine Regression Test", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0); 1590 ok(session != NULL ,"Unable to open Internet session\n"); 1591 1592 connect = InternetConnectA(session, "test.winehq.org", INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, 1593 INTERNET_SERVICE_HTTP, 0, 0); 1594 ok(connect != NULL, "Unable to connect to http://test.winehq.org with error %d\n", GetLastError()); 1595 1596 request = HttpOpenRequestA(connect, NULL, "/tests/hello.html", NULL, NULL, types, INTERNET_FLAG_NEED_FILE, 0); 1597 if (!request && GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED) 1598 { 1599 skip( "Network unreachable, skipping test\n" ); 1600 1601 ok(InternetCloseHandle(connect), "Close connect handle failed\n"); 1602 ok(InternetCloseHandle(session), "Close session handle failed\n"); 1603 1604 return; 1605 } 1606 ok(request != NULL, "Failed to open request handle err %u\n", GetLastError()); 1607 1608 size = sizeof(url); 1609 ret = InternetQueryOptionA(request, INTERNET_OPTION_URL, url, &size); 1610 ok(ret, "InternetQueryOptionA(INTERNET_OPTION_URL) failed: %u\n", GetLastError()); 1611 ok(!strcmp(url, "http://test.winehq.org/tests/hello.html"), "Wrong URL %s\n", url); 1612 1613 size = sizeof(file_name); 1614 ret = InternetQueryOptionA(request, INTERNET_OPTION_DATAFILE_NAME, file_name, &size); 1615 ok(!ret, "InternetQueryOptionA(INTERNET_OPTION_DATAFILE_NAME) succeeded\n"); 1616 ok(GetLastError() == ERROR_INTERNET_ITEM_NOT_FOUND, "GetLastError()=%u\n", GetLastError()); 1617 ok(!size, "size = %d\n", size); 1618 1619 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 1620 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 1621 1622 size = sizeof(file_name); 1623 ret = InternetQueryOptionA(request, INTERNET_OPTION_DATAFILE_NAME, file_name, &size); 1624 ok(ret, "InternetQueryOptionA(INTERNET_OPTION_DATAFILE_NAME) failed: %u\n", GetLastError()); 1625 1626 file = CreateFileA(file_name, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 1627 FILE_ATTRIBUTE_NORMAL, NULL); 1628 ok(file != INVALID_HANDLE_VALUE, "Could not create file: %u\n", GetLastError()); 1629 file_size = GetFileSize(file, NULL); 1630 ok(file_size == 106, "file size = %u\n", file_size); 1631 1632 size = sizeof(buf); 1633 ret = InternetReadFile(request, buf, sizeof(buf), &size); 1634 ok(ret, "InternetReadFile failed: %u\n", GetLastError()); 1635 ok(size == 100, "size = %u\n", size); 1636 1637 file_size = GetFileSize(file, NULL); 1638 ok(file_size == 106, "file size = %u\n", file_size); 1639 CloseHandle(file); 1640 1641 ret = DeleteFileA(file_name); 1642 ok(!ret && GetLastError() == ERROR_SHARING_VIOLATION, "Deleting file returned %x(%u)\n", ret, GetLastError()); 1643 1644 ok(InternetCloseHandle(request), "Close request handle failed\n"); 1645 1646 file = CreateFileA(file_name, GENERIC_WRITE, FILE_SHARE_READ|FILE_SHARE_WRITE, NULL, OPEN_EXISTING, 1647 FILE_ATTRIBUTE_NORMAL, NULL); 1648 ok(file != INVALID_HANDLE_VALUE, "Could not create file: %u\n", GetLastError()); 1649 ret = WriteFile(file, cached_content, sizeof(cached_content), &size, NULL); 1650 ok(ret && size, "WriteFile failed: %d, %d\n", ret, size); 1651 ret = CommitUrlCacheEntryA(url, file_name, filetime_zero, filetime_zero, NORMAL_CACHE_ENTRY, NULL, 0, NULL, 0); 1652 ok(ret, "CommitUrlCacheEntry failed: %d\n", GetLastError()); 1653 CloseHandle(file); 1654 1655 /* Send the same request, requiring it to be retrieved from the cache */ 1656 request = HttpOpenRequestA(connect, "GET", "/tests/hello.html", NULL, NULL, NULL, INTERNET_FLAG_FROM_CACHE, 0); 1657 1658 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 1659 ok(ret, "HttpSendRequest failed\n"); 1660 1661 size = sizeof(buf); 1662 ret = InternetReadFile(request, buf, sizeof(buf), &size); 1663 ok(ret, "InternetReadFile failed: %u\n", GetLastError()); 1664 ok(size == 100, "size = %u\n", size); 1665 buf[99] = 0; 1666 todo_wine ok(!strcmp((char*)buf, cached_content), "incorrect page data: %s\n", (char*)buf); 1667 1668 ok(InternetCloseHandle(request), "Close request handle failed\n"); 1669 1670 DeleteUrlCacheEntryA(url); 1671 request = HttpOpenRequestA(connect, "GET", "/tests/hello.html", NULL, NULL, NULL, INTERNET_FLAG_FROM_CACHE, 0); 1672 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 1673 todo_wine ok(!ret, "HttpSendRequest succeeded\n"); 1674 if(!ret) 1675 ok(GetLastError() == ERROR_FILE_NOT_FOUND, "GetLastError() = %d\n", GetLastError()); 1676 ok(InternetCloseHandle(request), "Close request handle failed\n"); 1677 1678 request = HttpOpenRequestA(connect, NULL, "/", NULL, NULL, types, INTERNET_FLAG_NO_CACHE_WRITE, 0); 1679 ok(request != NULL, "Failed to open request handle err %u\n", GetLastError()); 1680 1681 size = sizeof(file_name); 1682 ret = InternetQueryOptionA(request, INTERNET_OPTION_DATAFILE_NAME, file_name, &size); 1683 ok(!ret, "InternetQueryOptionA(INTERNET_OPTION_DATAFILE_NAME) succeeded\n"); 1684 ok(GetLastError() == ERROR_INTERNET_ITEM_NOT_FOUND, "GetLastError()=%u\n", GetLastError()); 1685 ok(!size, "size = %d\n", size); 1686 1687 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 1688 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 1689 1690 size = sizeof(file_name); 1691 file_name[0] = 0; 1692 ret = InternetQueryOptionA(request, INTERNET_OPTION_DATAFILE_NAME, file_name, &size); 1693 if (ret) 1694 { 1695 file = CreateFileA(file_name, GENERIC_READ, FILE_SHARE_READ|FILE_SHARE_WRITE, NULL, OPEN_EXISTING, 1696 FILE_ATTRIBUTE_NORMAL, NULL); 1697 ok(file != INVALID_HANDLE_VALUE, "Could not create file: %u\n", GetLastError()); 1698 CloseHandle(file); 1699 } 1700 else 1701 { 1702 /* < IE8 */ 1703 ok(file_name[0] == 0, "Didn't expect a file name\n"); 1704 } 1705 1706 ok(InternetCloseHandle(request), "Close request handle failed\n"); 1707 ok(InternetCloseHandle(connect), "Close connect handle failed\n"); 1708 ok(InternetCloseHandle(session), "Close session handle failed\n"); 1709 1710 test_cache_read(); 1711 } 1712 1713 static void InternetLockRequestFile_test(void) 1714 { 1715 char file_name[MAX_PATH]; 1716 test_request_t req; 1717 HANDLE lock, lock2; 1718 DWORD size; 1719 BOOL ret; 1720 1721 open_simple_request(&req, "test.winehq.org", INTERNET_DEFAULT_HTTP_PORT, NULL, "/tests/hello.html"); 1722 1723 size = sizeof(file_name); 1724 ret = InternetQueryOptionA(req.request, INTERNET_OPTION_DATAFILE_NAME, file_name, &size); 1725 ok(!ret, "InternetQueryOptionA(INTERNET_OPTION_DATAFILE_NAME) succeeded\n"); 1726 ok(GetLastError() == ERROR_INTERNET_ITEM_NOT_FOUND, "GetLastError()=%u\n", GetLastError()); 1727 ok(!size, "size = %d\n", size); 1728 1729 lock = NULL; 1730 ret = InternetLockRequestFile(req.request, &lock); 1731 ok(!ret && GetLastError() == ERROR_FILE_NOT_FOUND, "InternetLockRequestFile returned: %x(%u)\n", ret, GetLastError()); 1732 1733 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 1734 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 1735 1736 size = sizeof(file_name); 1737 ret = InternetQueryOptionA(req.request, INTERNET_OPTION_DATAFILE_NAME, file_name, &size); 1738 ok(ret, "InternetQueryOptionA(INTERNET_OPTION_DATAFILE_NAME) failed: %u\n", GetLastError()); 1739 1740 ret = InternetLockRequestFile(req.request, &lock); 1741 ok(ret, "InternetLockRequestFile returned: %x(%u)\n", ret, GetLastError()); 1742 ok(lock != NULL, "lock == NULL\n"); 1743 1744 ret = InternetLockRequestFile(req.request, &lock2); 1745 ok(ret, "InternetLockRequestFile returned: %x(%u)\n", ret, GetLastError()); 1746 ok(lock == lock2, "lock != lock2\n"); 1747 1748 ret = InternetUnlockRequestFile(lock2); 1749 ok(ret, "InternetUnlockRequestFile failed: %u\n", GetLastError()); 1750 1751 ret = DeleteFileA(file_name); 1752 ok(!ret && GetLastError() == ERROR_SHARING_VIOLATION, "Deleting file returned %x(%u)\n", ret, GetLastError()); 1753 1754 ok(InternetCloseHandle(req.request), "Close request handle failed\n"); 1755 1756 ret = DeleteFileA(file_name); 1757 ok(!ret && GetLastError() == ERROR_SHARING_VIOLATION, "Deleting file returned %x(%u)\n", ret, GetLastError()); 1758 1759 ret = InternetUnlockRequestFile(lock); 1760 ok(ret, "InternetUnlockRequestFile failed: %u\n", GetLastError()); 1761 1762 ret = DeleteFileA(file_name); 1763 ok(ret, "Deleting file returned %x(%u)\n", ret, GetLastError()); 1764 } 1765 1766 static void HttpHeaders_test(void) 1767 { 1768 HINTERNET hSession; 1769 HINTERNET hConnect; 1770 HINTERNET hRequest; 1771 CHAR buffer[256]; 1772 WCHAR wbuffer[256]; 1773 DWORD len = 256; 1774 DWORD oldlen; 1775 DWORD index = 0; 1776 BOOL ret; 1777 1778 hSession = InternetOpenA("Wine Regression Test", 1779 INTERNET_OPEN_TYPE_PRECONFIG,NULL,NULL,0); 1780 ok( hSession != NULL ,"Unable to open Internet session\n"); 1781 hConnect = InternetConnectA(hSession, "test.winehq.org", 1782 INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 1783 0); 1784 ok( hConnect != NULL, "Unable to connect to http://test.winehq.org\n"); 1785 hRequest = HttpOpenRequestA(hConnect, "POST", "/tests/post.php", 1786 NULL, NULL, NULL, INTERNET_FLAG_NO_CACHE_WRITE, 0); 1787 if (!hRequest && GetLastError() == ERROR_INTERNET_NAME_NOT_RESOLVED) 1788 { 1789 skip( "Network unreachable, skipping test\n" ); 1790 goto done; 1791 } 1792 ok( hRequest != NULL, "Failed to open request handle\n"); 1793 1794 index = 0; 1795 len = sizeof(buffer); 1796 strcpy(buffer,"Warning"); 1797 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1798 buffer,&len,&index)==0,"Warning hearder reported as Existing\n"); 1799 1800 ok(HttpAddRequestHeadersA(hRequest,"Warning:test1",-1,HTTP_ADDREQ_FLAG_ADD), 1801 "Failed to add new header\n"); 1802 1803 index = 0; 1804 len = sizeof(buffer); 1805 strcpy(buffer,"Warning"); 1806 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1807 buffer,&len,&index),"Unable to query header\n"); 1808 ok(index == 1, "Index was not incremented\n"); 1809 ok(strcmp(buffer,"test1")==0, "incorrect string was returned(%s)\n",buffer); 1810 ok(len == 5, "Invalid length (exp. 5, got %d)\n", len); 1811 ok((len < sizeof(buffer)) && (buffer[len] == 0), "Buffer not NULL-terminated\n"); /* len show only 5 characters but the buffer is NULL-terminated*/ 1812 len = sizeof(buffer); 1813 strcpy(buffer,"Warning"); 1814 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1815 buffer,&len,&index)==0,"Second Index Should Not Exist\n"); 1816 1817 index = 0; 1818 len = 5; /* could store the string but not the NULL terminator */ 1819 strcpy(buffer,"Warning"); 1820 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1821 buffer,&len,&index) == FALSE,"Query succeeded on a too small buffer\n"); 1822 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "Unexpected last error: %d\n", GetLastError()); 1823 ok(index == 0, "Index was incremented\n"); 1824 ok(strcmp(buffer,"Warning")==0, "incorrect string was returned(%s)\n",buffer); /* string not touched */ 1825 ok(len == 6, "Invalid length (exp. 6, got %d)\n", len); /* unlike success, the length includes the NULL-terminator */ 1826 1827 /* a call with NULL will fail but will return the length */ 1828 index = 0; 1829 len = sizeof(buffer); 1830 SetLastError(0xdeadbeef); 1831 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_RAW_HEADERS_CRLF|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1832 NULL,&len,&index) == FALSE,"Query worked\n"); 1833 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "Unexpected last error: %d\n", GetLastError()); 1834 ok(len > 40, "Invalid length (exp. more than 40, got %d)\n", len); 1835 ok(index == 0, "Index was incremented\n"); 1836 1837 /* even for a len that is too small */ 1838 index = 0; 1839 len = 15; 1840 SetLastError(0xdeadbeef); 1841 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_RAW_HEADERS_CRLF|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1842 NULL,&len,&index) == FALSE,"Query worked\n"); 1843 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "Unexpected last error: %d\n", GetLastError()); 1844 ok(len > 40, "Invalid length (exp. more than 40, got %d)\n", len); 1845 ok(index == 0, "Index was incremented\n"); 1846 1847 index = 0; 1848 len = 0; 1849 SetLastError(0xdeadbeef); 1850 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_RAW_HEADERS_CRLF|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1851 NULL,&len,&index) == FALSE,"Query worked\n"); 1852 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "Unexpected last error: %d\n", GetLastError()); 1853 ok(len > 40, "Invalid length (exp. more than 40, got %d)\n", len); 1854 ok(index == 0, "Index was incremented\n"); 1855 oldlen = len; /* bytes; at least long enough to hold buffer & nul */ 1856 1857 1858 /* a working query */ 1859 index = 0; 1860 len = sizeof(buffer); 1861 memset(buffer, 'x', sizeof(buffer)); 1862 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_RAW_HEADERS_CRLF|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1863 buffer,&len,&index),"Unable to query header\n"); 1864 ok(len + sizeof(CHAR) <= oldlen, "Result longer than advertised\n"); 1865 ok((len < sizeof(buffer)-sizeof(CHAR)) && (buffer[len/sizeof(CHAR)] == 0),"No NUL at end\n"); 1866 ok(len == strlen(buffer) * sizeof(CHAR), "Length wrong\n"); 1867 /* what's in the middle differs between Wine and Windows so currently we check only the beginning and the end */ 1868 ok(strncmp(buffer, "POST /tests/post.php HTTP/1", 25)==0, "Invalid beginning of headers string\n"); 1869 ok(strcmp(buffer + strlen(buffer) - 4, "\r\n\r\n")==0, "Invalid end of headers string\n"); 1870 ok(index == 0, "Index was incremented\n"); 1871 1872 /* Like above two tests, but for W version */ 1873 1874 index = 0; 1875 len = 0; 1876 SetLastError(0xdeadbeef); 1877 ok(HttpQueryInfoW(hRequest,HTTP_QUERY_RAW_HEADERS_CRLF|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1878 NULL,&len,&index) == FALSE,"Query worked\n"); 1879 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "Unexpected last error: %d\n", GetLastError()); 1880 ok(len > 80, "Invalid length (exp. more than 80, got %d)\n", len); 1881 ok(index == 0, "Index was incremented\n"); 1882 oldlen = len; /* bytes; at least long enough to hold buffer & nul */ 1883 1884 /* a working query */ 1885 index = 0; 1886 len = sizeof(wbuffer); 1887 memset(wbuffer, 'x', sizeof(wbuffer)); 1888 ok(HttpQueryInfoW(hRequest,HTTP_QUERY_RAW_HEADERS_CRLF|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1889 wbuffer,&len,&index),"Unable to query header\n"); 1890 ok(len + sizeof(WCHAR) <= oldlen, "Result longer than advertised\n"); 1891 ok(len == lstrlenW(wbuffer) * sizeof(WCHAR), "Length wrong\n"); 1892 ok((len < sizeof(wbuffer)-sizeof(WCHAR)) && (wbuffer[len/sizeof(WCHAR)] == 0),"No NUL at end\n"); 1893 ok(index == 0, "Index was incremented\n"); 1894 1895 /* end of W version tests */ 1896 1897 /* Without HTTP_QUERY_FLAG_REQUEST_HEADERS */ 1898 index = 0; 1899 len = sizeof(buffer); 1900 memset(buffer, 'x', sizeof(buffer)); 1901 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_RAW_HEADERS_CRLF, 1902 buffer,&len,&index) == TRUE,"Query failed\n"); 1903 ok(len == 2 || len == 4 /* win10 */, "Expected 2 or 4, got %d\n", len); 1904 ok(memcmp(buffer, "\r\n\r\n", len) == 0, "Expected CRLF, got '%s'\n", buffer); 1905 ok(index == 0, "Index was incremented\n"); 1906 1907 ok(HttpAddRequestHeadersA(hRequest,"Warning:test2",-1,HTTP_ADDREQ_FLAG_ADD), 1908 "Failed to add duplicate header using HTTP_ADDREQ_FLAG_ADD\n"); 1909 1910 index = 0; 1911 len = sizeof(buffer); 1912 strcpy(buffer,"Warning"); 1913 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1914 buffer,&len,&index),"Unable to query header\n"); 1915 ok(index == 1, "Index was not incremented\n"); 1916 ok(strcmp(buffer,"test1")==0, "incorrect string was returned(%s)\n",buffer); 1917 len = sizeof(buffer); 1918 strcpy(buffer,"Warning"); 1919 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1920 buffer,&len,&index),"Failed to get second header\n"); 1921 ok(index == 2, "Index was not incremented\n"); 1922 ok(strcmp(buffer,"test2")==0, "incorrect string was returned(%s)\n",buffer); 1923 len = sizeof(buffer); 1924 strcpy(buffer,"Warning"); 1925 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1926 buffer,&len,&index)==0,"Third Header Should Not Exist\n"); 1927 1928 ok(HttpAddRequestHeadersA(hRequest,"Warning:test3",-1,HTTP_ADDREQ_FLAG_REPLACE), "Failed to replace header using HTTP_ADDREQ_FLAG_REPLACE\n"); 1929 1930 index = 0; 1931 len = sizeof(buffer); 1932 strcpy(buffer,"Warning"); 1933 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1934 buffer,&len,&index),"Unable to query header\n"); 1935 ok(index == 1, "Index was not incremented\n"); 1936 ok(strcmp(buffer,"test2")==0, "incorrect string was returned(%s)\n",buffer); 1937 len = sizeof(buffer); 1938 strcpy(buffer,"Warning"); 1939 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1940 buffer,&len,&index),"Failed to get second header\n"); 1941 ok(index == 2, "Index was not incremented\n"); 1942 ok(strcmp(buffer,"test3")==0, "incorrect string was returned(%s)\n",buffer); 1943 len = sizeof(buffer); 1944 strcpy(buffer,"Warning"); 1945 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1946 buffer,&len,&index)==0,"Third Header Should Not Exist\n"); 1947 1948 ok(HttpAddRequestHeadersA(hRequest,"Warning:test4",-1,HTTP_ADDREQ_FLAG_ADD_IF_NEW)==0, "HTTP_ADDREQ_FLAG_ADD_IF_NEW replaced existing header\n"); 1949 1950 index = 0; 1951 len = sizeof(buffer); 1952 strcpy(buffer,"Warning"); 1953 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1954 buffer,&len,&index),"Unable to query header\n"); 1955 ok(index == 1, "Index was not incremented\n"); 1956 ok(strcmp(buffer,"test2")==0, "incorrect string was returned(%s)\n",buffer); 1957 len = sizeof(buffer); 1958 strcpy(buffer,"Warning"); 1959 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1960 buffer,&len,&index),"Failed to get second header\n"); 1961 ok(index == 2, "Index was not incremented\n"); 1962 ok(strcmp(buffer,"test3")==0, "incorrect string was returned(%s)\n",buffer); 1963 len = sizeof(buffer); 1964 strcpy(buffer,"Warning"); 1965 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1966 buffer,&len,&index)==0,"Third Header Should Not Exist\n"); 1967 1968 ok(HttpAddRequestHeadersA(hRequest,"Warning:test4",-1, HTTP_ADDREQ_FLAG_COALESCE), "HTTP_ADDREQ_FLAG_COALESCE Did not work\n"); 1969 1970 index = 0; 1971 len = sizeof(buffer); 1972 strcpy(buffer,"Warning"); 1973 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, 1974 buffer,&len,&index),"Unable to query header\n"); 1975 ok(index == 1, "Index was not incremented\n"); 1976 ok(strcmp(buffer,"test2, test4")==0, "incorrect string was returned(%s)\n", buffer); 1977 len = sizeof(buffer); 1978 strcpy(buffer,"Warning"); 1979 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Failed to get second header\n"); 1980 ok(index == 2, "Index was not incremented\n"); 1981 ok(strcmp(buffer,"test3")==0, "incorrect string was returned(%s)\n",buffer); 1982 len = sizeof(buffer); 1983 strcpy(buffer,"Warning"); 1984 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index)==0,"Third Header Should Not Exist\n"); 1985 1986 ok(HttpAddRequestHeadersA(hRequest,"Warning:test5",-1, HTTP_ADDREQ_FLAG_COALESCE_WITH_COMMA), "HTTP_ADDREQ_FLAG_COALESCE Did not work\n"); 1987 1988 index = 0; 1989 len = sizeof(buffer); 1990 strcpy(buffer,"Warning"); 1991 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Unable to query header\n"); 1992 ok(index == 1, "Index was not incremented\n"); 1993 ok(strcmp(buffer,"test2, test4, test5")==0, "incorrect string was returned(%s)\n",buffer); 1994 len = sizeof(buffer); 1995 strcpy(buffer,"Warning"); 1996 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Failed to get second header\n"); 1997 ok(index == 2, "Index was not incremented\n"); 1998 ok(strcmp(buffer,"test3")==0, "incorrect string was returned(%s)\n",buffer); 1999 len = sizeof(buffer); 2000 strcpy(buffer,"Warning"); 2001 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index)==0,"Third Header Should Not Exist\n"); 2002 2003 ok(HttpAddRequestHeadersA(hRequest,"Warning:test6",-1, HTTP_ADDREQ_FLAG_COALESCE_WITH_SEMICOLON), "HTTP_ADDREQ_FLAG_COALESCE Did not work\n"); 2004 2005 index = 0; 2006 len = sizeof(buffer); 2007 strcpy(buffer,"Warning"); 2008 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Unable to query header\n"); 2009 ok(index == 1, "Index was not incremented\n"); 2010 ok(strcmp(buffer,"test2, test4, test5; test6")==0, "incorrect string was returned(%s)\n",buffer); 2011 len = sizeof(buffer); 2012 strcpy(buffer,"Warning"); 2013 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Failed to get second header\n"); 2014 ok(index == 2, "Index was not incremented\n"); 2015 ok(strcmp(buffer,"test3")==0, "incorrect string was returned(%s)\n",buffer); 2016 len = sizeof(buffer); 2017 strcpy(buffer,"Warning"); 2018 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index)==0,"Third Header Should Not Exist\n"); 2019 2020 ok(HttpAddRequestHeadersA(hRequest,"Warning:test7",-1, HTTP_ADDREQ_FLAG_ADD|HTTP_ADDREQ_FLAG_REPLACE), "HTTP_ADDREQ_FLAG_ADD with HTTP_ADDREQ_FLAG_REPALCE Did not work\n"); 2021 2022 index = 0; 2023 len = sizeof(buffer); 2024 strcpy(buffer,"Warning"); 2025 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Unable to query header\n"); 2026 ok(index == 1, "Index was not incremented\n"); 2027 ok(strcmp(buffer,"test3")==0, "incorrect string was returned(%s)\n",buffer); 2028 len = sizeof(buffer); 2029 strcpy(buffer,"Warning"); 2030 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Failed to get second header\n"); 2031 ok(index == 2, "Index was not incremented\n"); 2032 ok(strcmp(buffer,"test7")==0, "incorrect string was returned(%s)\n",buffer); 2033 len = sizeof(buffer); 2034 strcpy(buffer,"Warning"); 2035 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index)==0,"Third Header Should Not Exist\n"); 2036 2037 /* Ensure that blank headers are ignored and don't cause a failure */ 2038 ok(HttpAddRequestHeadersA(hRequest,"\r\nBlankTest:value\r\n\r\n",-1, HTTP_ADDREQ_FLAG_ADD_IF_NEW), "Failed to add header with blank entries in list\n"); 2039 2040 index = 0; 2041 len = sizeof(buffer); 2042 strcpy(buffer,"BlankTest"); 2043 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Unable to query header\n"); 2044 ok(index == 1, "Index was not incremented\n"); 2045 ok(strcmp(buffer,"value")==0, "incorrect string was returned(%s)\n",buffer); 2046 2047 /* Ensure that malformed header separators are ignored and don't cause a failure */ 2048 ok(HttpAddRequestHeadersA(hRequest,"\r\rMalformedTest:value\n\nMalformedTestTwo: value2\rMalformedTestThree: value3\n\n\r\r\n",-1, HTTP_ADDREQ_FLAG_ADD|HTTP_ADDREQ_FLAG_REPLACE), 2049 "Failed to add header with malformed entries in list\n"); 2050 2051 index = 0; 2052 len = sizeof(buffer); 2053 strcpy(buffer,"MalformedTest"); 2054 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Unable to query header\n"); 2055 ok(index == 1, "Index was not incremented\n"); 2056 ok(strcmp(buffer,"value")==0, "incorrect string was returned(%s)\n",buffer); 2057 index = 0; 2058 len = sizeof(buffer); 2059 strcpy(buffer,"MalformedTestTwo"); 2060 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Unable to query header\n"); 2061 ok(index == 1, "Index was not incremented\n"); 2062 ok(strcmp(buffer,"value2")==0, "incorrect string was returned(%s)\n",buffer); 2063 index = 0; 2064 len = sizeof(buffer); 2065 strcpy(buffer,"MalformedTestThree"); 2066 ok(HttpQueryInfoA(hRequest,HTTP_QUERY_CUSTOM|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer,&len,&index),"Unable to query header\n"); 2067 ok(index == 1, "Index was not incremented\n"); 2068 ok(strcmp(buffer,"value3")==0, "incorrect string was returned(%s)\n",buffer); 2069 2070 ret = HttpAddRequestHeadersA(hRequest, "Authorization: Basic\r\n", -1, HTTP_ADDREQ_FLAG_ADD); 2071 ok(ret, "unable to add header %u\n", GetLastError()); 2072 2073 index = 0; 2074 buffer[0] = 0; 2075 len = sizeof(buffer); 2076 ret = HttpQueryInfoA(hRequest, HTTP_QUERY_AUTHORIZATION|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &len, &index); 2077 ok(ret, "unable to query header %u\n", GetLastError()); 2078 ok(index == 1, "index was not incremented\n"); 2079 ok(!strcmp(buffer, "Basic"), "incorrect string was returned (%s)\n", buffer); 2080 2081 ret = HttpAddRequestHeadersA(hRequest, "Authorization:\r\n", -1, HTTP_ADDREQ_FLAG_REPLACE); 2082 ok(ret, "unable to remove header %u\n", GetLastError()); 2083 2084 index = 0; 2085 len = sizeof(buffer); 2086 SetLastError(0xdeadbeef); 2087 ok(!HttpQueryInfoA(hRequest, HTTP_QUERY_AUTHORIZATION|HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &len, &index), 2088 "header still present\n"); 2089 ok(GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, "got %u\n", GetLastError()); 2090 2091 ok(InternetCloseHandle(hRequest), "Close request handle failed\n"); 2092 done: 2093 ok(InternetCloseHandle(hConnect), "Close connect handle failed\n"); 2094 ok(InternetCloseHandle(hSession), "Close session handle failed\n"); 2095 } 2096 2097 static const char garbagemsg[] = 2098 "Garbage: Header\r\n"; 2099 2100 static const char contmsg[] = 2101 "HTTP/1.1 100 Continue\r\n"; 2102 2103 static const char expandcontmsg[] = 2104 "HTTP/1.1 100 Continue\r\n" 2105 "Server: winecontinue\r\n" 2106 "Tag: something witty\r\n"; 2107 2108 static const char okmsg[] = 2109 "HTTP/1.1 200 OK\r\n" 2110 "Server: winetest\r\n" 2111 "\r\n"; 2112 2113 static const char okmsg201[] = 2114 "HTTP/1.1 201 OK\r\n" 2115 "Server: winetest\r\n" 2116 "\r\n"; 2117 2118 static const char okmsg2[] = 2119 "HTTP/1.1 200 OK\r\n" 2120 "Date: Mon, 01 Dec 2008 13:44:34 GMT\r\n" 2121 "Server: winetest\r\n" 2122 "Content-Length: 0\r\n" 2123 "Set-Cookie: one\r\n" 2124 "Set-Cookie: two\r\n" 2125 "\r\n"; 2126 2127 static DWORD64 content_length; 2128 static const char largemsg[] = 2129 "HTTP/1.1 200 OK\r\n" 2130 "Content-Length: %I64u\r\n" 2131 "\r\n"; 2132 2133 static const char okmsg_cookie_path[] = 2134 "HTTP/1.1 200 OK\r\n" 2135 "Date: Mon, 01 Dec 2008 13:44:34 GMT\r\n" 2136 "Server: winetest\r\n" 2137 "Content-Length: 0\r\n" 2138 "Set-Cookie: subcookie2=data; path=/test_cookie_set_path\r\n" 2139 "\r\n"; 2140 2141 static const char okmsg_cookie[] = 2142 "HTTP/1.1 200 OK\r\n" 2143 "Date: Mon, 01 Dec 2008 13:44:34 GMT\r\n" 2144 "Server: winetest\r\n" 2145 "Content-Length: 0\r\n" 2146 "Set-Cookie: testcookie=testvalue\r\n" 2147 "\r\n"; 2148 2149 static const char notokmsg[] = 2150 "HTTP/1.1 400 Bad Request\r\n" 2151 "Server: winetest\r\n" 2152 "\r\n"; 2153 2154 static const char noauthmsg[] = 2155 "HTTP/1.1 401 Unauthorized\r\n" 2156 "Server: winetest\r\n" 2157 "Connection: close\r\n" 2158 "WWW-Authenticate: Basic realm=\"placebo\"\r\n" 2159 "\r\n"; 2160 2161 static const char noauthmsg2[] = 2162 "HTTP/1.0 401 Anonymous requests or requests on unsecure channel are not allowed\r\n" 2163 "HTTP/1.0 401 Anonymous requests or requests on unsecure channel are not allowed" 2164 "\0d`0|6\n" 2165 "Server: winetest\r\n"; 2166 2167 static const char proxymsg[] = 2168 "HTTP/1.1 407 Proxy Authentication Required\r\n" 2169 "Server: winetest\r\n" 2170 "Proxy-Connection: close\r\n" 2171 "Proxy-Authenticate: Basic realm=\"placebo\"\r\n" 2172 "\r\n"; 2173 2174 static const char page1[] = 2175 "<HTML>\r\n" 2176 "<HEAD><TITLE>wininet test page</TITLE></HEAD>\r\n" 2177 "<BODY>The quick brown fox jumped over the lazy dog<P></BODY>\r\n" 2178 "</HTML>\r\n\r\n"; 2179 2180 static const char ok_with_length[] = 2181 "HTTP/1.1 200 OK\r\n" 2182 "Connection: Keep-Alive\r\n" 2183 "Content-Length: 18\r\n\r\n" 2184 "HTTP/1.1 211 OK\r\n\r\n"; 2185 2186 static const char ok_with_length2[] = 2187 "HTTP/1.1 210 OK\r\n" 2188 "Connection: Keep-Alive\r\n" 2189 "Content-Length: 19\r\n\r\n" 2190 "HTTP/1.1 211 OK\r\n\r\n"; 2191 2192 struct server_info { 2193 HANDLE hEvent; 2194 int port; 2195 }; 2196 2197 static int test_cache_gzip; 2198 static const char *send_buffer; 2199 static int server_socket; 2200 2201 static DWORD CALLBACK server_thread(LPVOID param) 2202 { 2203 struct server_info *si = param; 2204 int r, c = -1, i, on, count = 0; 2205 SOCKET s; 2206 struct sockaddr_in sa; 2207 char *buffer; 2208 size_t buffer_size; 2209 WSADATA wsaData; 2210 int last_request = 0; 2211 char host_header[22]; 2212 char host_header_override[30]; 2213 static int test_no_cache = 0; 2214 2215 WSAStartup(MAKEWORD(1,1), &wsaData); 2216 2217 s = socket(AF_INET, SOCK_STREAM, 0); 2218 if (s == INVALID_SOCKET) 2219 return 1; 2220 2221 on = 1; 2222 setsockopt(s, SOL_SOCKET, SO_REUSEADDR, (char*)&on, sizeof on); 2223 2224 memset(&sa, 0, sizeof sa); 2225 sa.sin_family = AF_INET; 2226 sa.sin_port = htons(si->port); 2227 sa.sin_addr.S_un.S_addr = inet_addr("127.0.0.1"); 2228 2229 r = bind(s, (struct sockaddr*) &sa, sizeof sa); 2230 if (r<0) 2231 return 1; 2232 2233 listen(s, 0); 2234 2235 SetEvent(si->hEvent); 2236 2237 sprintf(host_header, "Host: localhost:%d", si->port); 2238 sprintf(host_header_override, "Host: test.local:%d\r\n", si->port); 2239 buffer = HeapAlloc(GetProcessHeap(), 0, buffer_size = 1000); 2240 2241 do 2242 { 2243 if(c == -1) 2244 c = accept(s, NULL, NULL); 2245 2246 memset(buffer, 0, buffer_size); 2247 for(i=0;; i++) 2248 { 2249 if(i == buffer_size) 2250 buffer = HeapReAlloc(GetProcessHeap(), 0, buffer, buffer_size *= 2); 2251 2252 r = recv(c, buffer+i, 1, 0); 2253 if (r != 1) 2254 break; 2255 if (i<4) continue; 2256 if (buffer[i-2] == '\n' && buffer[i] == '\n' && 2257 buffer[i-3] == '\r' && buffer[i-1] == '\r') 2258 break; 2259 } 2260 if (strstr(buffer, "GET /test1")) 2261 { 2262 if (!strstr(buffer, "Content-Length: 0")) 2263 { 2264 send(c, okmsg, sizeof okmsg-1, 0); 2265 send(c, page1, sizeof page1-1, 0); 2266 } 2267 else 2268 send(c, notokmsg, sizeof notokmsg-1, 0); 2269 } 2270 if (strstr(buffer, "CONNECT ")) 2271 { 2272 if (!strstr(buffer, "Content-Length: 0")) 2273 send(c, notokmsg, sizeof notokmsg-1, 0); 2274 else 2275 send(c, proxymsg, sizeof proxymsg-1, 0); 2276 } 2277 if (strstr(buffer, "/test2")) 2278 { 2279 if (strstr(buffer, "Proxy-Authorization: Basic bWlrZToxMTAx")) 2280 { 2281 send(c, okmsg, sizeof okmsg-1, 0); 2282 send(c, page1, sizeof page1-1, 0); 2283 } 2284 else 2285 send(c, proxymsg, sizeof proxymsg-1, 0); 2286 } 2287 if (strstr(buffer, "/test3")) 2288 { 2289 if (strstr(buffer, "Authorization: Basic dXNlcjpwd2Q=")) 2290 send(c, okmsg, sizeof okmsg-1, 0); 2291 else 2292 send(c, noauthmsg, sizeof noauthmsg-1, 0); 2293 } 2294 if (strstr(buffer, "/test4")) 2295 { 2296 if (strstr(buffer, "Connection: Close")) 2297 send(c, okmsg, sizeof okmsg-1, 0); 2298 else 2299 send(c, notokmsg, sizeof notokmsg-1, 0); 2300 } 2301 if (strstr(buffer, "POST /test5") || 2302 strstr(buffer, "RPC_IN_DATA /test5") || 2303 strstr(buffer, "RPC_OUT_DATA /test5")) 2304 { 2305 if (strstr(buffer, "Content-Length: 0")) 2306 { 2307 send(c, okmsg, sizeof okmsg-1, 0); 2308 send(c, page1, sizeof page1-1, 0); 2309 } 2310 else 2311 send(c, notokmsg, sizeof notokmsg-1, 0); 2312 } 2313 if (strstr(buffer, "GET /test6")) 2314 { 2315 send(c, contmsg, sizeof contmsg-1, 0); 2316 send(c, contmsg, sizeof contmsg-1, 0); 2317 send(c, okmsg, sizeof okmsg-1, 0); 2318 send(c, page1, sizeof page1-1, 0); 2319 } 2320 if (strstr(buffer, "POST /test7")) 2321 { 2322 if (strstr(buffer, "Content-Length: 100")) 2323 { 2324 if (strstr(buffer, "POST /test7b")) 2325 recvfrom(c, buffer, buffer_size, 0, NULL, NULL); 2326 send(c, okmsg, sizeof okmsg-1, 0); 2327 send(c, page1, sizeof page1-1, 0); 2328 } 2329 else 2330 send(c, notokmsg, sizeof notokmsg-1, 0); 2331 } 2332 if (strstr(buffer, "/test8")) 2333 { 2334 if (!strstr(buffer, "Connection: Close") && 2335 strstr(buffer, "Connection: Keep-Alive") && 2336 !strstr(buffer, "Cache-Control: no-cache") && 2337 !strstr(buffer, "Pragma: no-cache") && 2338 strstr(buffer, host_header)) 2339 send(c, okmsg, sizeof okmsg-1, 0); 2340 else 2341 send(c, notokmsg, sizeof notokmsg-1, 0); 2342 } 2343 if (strstr(buffer, "/test9")) 2344 { 2345 if (!strstr(buffer, "Connection: Close") && 2346 !strstr(buffer, "Connection: Keep-Alive") && 2347 !strstr(buffer, "Cache-Control: no-cache") && 2348 !strstr(buffer, "Pragma: no-cache") && 2349 strstr(buffer, host_header)) 2350 send(c, okmsg, sizeof okmsg-1, 0); 2351 else 2352 send(c, notokmsg, sizeof notokmsg-1, 0); 2353 } 2354 if (strstr(buffer, "/testA")) 2355 { 2356 if (!strstr(buffer, "Connection: Close") && 2357 !strstr(buffer, "Connection: Keep-Alive") && 2358 (strstr(buffer, "Cache-Control: no-cache") || 2359 strstr(buffer, "Pragma: no-cache")) && 2360 strstr(buffer, host_header)) 2361 send(c, okmsg, sizeof okmsg-1, 0); 2362 else 2363 send(c, notokmsg, sizeof notokmsg-1, 0); 2364 } 2365 if (strstr(buffer, "/testC")) 2366 { 2367 if (strstr(buffer, "cookie=biscuit")) 2368 send(c, okmsg, sizeof okmsg-1, 0); 2369 else 2370 send(c, notokmsg, sizeof notokmsg-1, 0); 2371 } 2372 if (strstr(buffer, "/testD")) 2373 { 2374 send(c, okmsg2, sizeof okmsg2-1, 0); 2375 } 2376 if (strstr(buffer, "/testE")) 2377 { 2378 send(c, noauthmsg2, sizeof noauthmsg2-1, 0); 2379 } 2380 if (strstr(buffer, "GET /quit")) 2381 { 2382 send(c, okmsg, sizeof okmsg-1, 0); 2383 send(c, page1, sizeof page1-1, 0); 2384 last_request = 1; 2385 } 2386 if (strstr(buffer, "GET /testF")) 2387 { 2388 send(c, expandcontmsg, sizeof expandcontmsg-1, 0); 2389 send(c, garbagemsg, sizeof garbagemsg-1, 0); 2390 send(c, contmsg, sizeof contmsg-1, 0); 2391 send(c, garbagemsg, sizeof garbagemsg-1, 0); 2392 send(c, okmsg, sizeof okmsg-1, 0); 2393 send(c, page1, sizeof page1-1, 0); 2394 } 2395 if (strstr(buffer, "GET /testG")) 2396 { 2397 send(c, page1, sizeof page1-1, 0); 2398 } 2399 2400 if (strstr(buffer, "GET /testJ")) 2401 { 2402 if (count == 0) 2403 { 2404 count++; 2405 send(c, ok_with_length, sizeof(ok_with_length)-1, 0); 2406 } 2407 else 2408 { 2409 send(c, ok_with_length2, sizeof(ok_with_length2)-1, 0); 2410 count = 0; 2411 } 2412 } 2413 if (strstr(buffer, "GET /testH")) 2414 { 2415 send(c, ok_with_length2, sizeof(ok_with_length2)-1, 0); 2416 recvfrom(c, buffer, buffer_size, 0, NULL, NULL); 2417 send(c, ok_with_length, sizeof(ok_with_length)-1, 0); 2418 } 2419 2420 if (strstr(buffer, "GET /test_no_content")) 2421 { 2422 static const char nocontentmsg[] = "HTTP/1.1 204 No Content\r\nConnection: close\r\n\r\n"; 2423 send(c, nocontentmsg, sizeof(nocontentmsg)-1, 0); 2424 } 2425 if (strstr(buffer, "GET /test_conn_close")) 2426 { 2427 static const char conn_close_response[] = "HTTP/1.1 200 OK\r\nConnection: close\r\n\r\nsome content"; 2428 send(c, conn_close_response, sizeof(conn_close_response)-1, 0); 2429 WaitForSingleObject(conn_close_event, INFINITE); 2430 trace("closing connection\n"); 2431 } 2432 if (strstr(buffer, "GET /test_cache_control_no_cache")) 2433 { 2434 static const char no_cache_response[] = "HTTP/1.1 200 OK\r\nCache-Control: no-cache\r\n\r\nsome content"; 2435 if(!test_no_cache++) 2436 send(c, no_cache_response, sizeof(no_cache_response)-1, 0); 2437 else 2438 send(c, okmsg, sizeof(okmsg)-1, 0); 2439 } 2440 if (strstr(buffer, "GET /test_cache_control_no_store")) 2441 { 2442 static const char no_cache_response[] = "HTTP/1.1 200 OK\r\nCache-Control: junk, \t No-StOrE\r\n\r\nsome content"; 2443 send(c, no_cache_response, sizeof(no_cache_response)-1, 0); 2444 } 2445 if (strstr(buffer, "GET /test_cache_gzip")) 2446 { 2447 static const char gzip_response[] = "HTTP/1.1 200 OK\r\nContent-Encoding: gzip\r\nContent-Type: text/html\r\n\r\n" 2448 "\x1f\x8b\x08\x00\x00\x00\x00\x00\x00\x03\x4b\xaf\xca\x2c\x50\x28" 2449 "\x49\x2d\x2e\xe1\x02\x00\x62\x92\xc7\x6c\x0a\x00\x00\x00"; 2450 if(!test_cache_gzip++) 2451 send(c, gzip_response, sizeof(gzip_response), 0); 2452 else 2453 send(c, notokmsg, sizeof(notokmsg)-1, 0); 2454 } 2455 if (strstr(buffer, "HEAD /test_head")) { 2456 static const char head_response[] = 2457 "HTTP/1.1 200 OK\r\n" 2458 "Connection: Keep-Alive\r\n" 2459 "Content-Length: 100\r\n" 2460 "\r\n"; 2461 2462 send(c, head_response, sizeof(head_response), 0); 2463 continue; 2464 } 2465 if (strstr(buffer, "GET /send_from_buffer")) 2466 send(c, send_buffer, strlen(send_buffer), 0); 2467 if (strstr(buffer, "/test_cache_control_verb")) 2468 { 2469 if (!memcmp(buffer, "GET ", sizeof("GET ")-1) && 2470 !strstr(buffer, "Cache-Control: no-cache\r\n")) send(c, okmsg, sizeof(okmsg)-1, 0); 2471 else if (strstr(buffer, "Cache-Control: no-cache\r\n")) send(c, okmsg, sizeof(okmsg)-1, 0); 2472 else send(c, notokmsg, sizeof(notokmsg)-1, 0); 2473 } 2474 if (strstr(buffer, "/test_request_content_length")) 2475 { 2476 static char msg[] = "HTTP/1.1 200 OK\r\nConnection: Keep-Alive\r\n\r\n"; 2477 static int seen_content_length; 2478 2479 if (!seen_content_length) 2480 { 2481 if (strstr(buffer, "Content-Length: 0")) 2482 { 2483 seen_content_length = 1; 2484 send(c, msg, sizeof msg-1, 0); 2485 } 2486 else send(c, notokmsg, sizeof notokmsg-1, 0); 2487 WaitForSingleObject(complete_event, 5000); 2488 } 2489 else 2490 { 2491 if (strstr(buffer, "Content-Length: 0")) send(c, msg, sizeof msg-1, 0); 2492 else send(c, notokmsg, sizeof notokmsg-1, 0); 2493 WaitForSingleObject(complete_event, 5000); 2494 } 2495 } 2496 if (strstr(buffer, "GET /test_premature_disconnect")) 2497 trace("closing connection\n"); 2498 if (strstr(buffer, "HEAD /upload.txt")) 2499 { 2500 if (strstr(buffer, "Authorization: Basic dXNlcjpwd2Q=")) 2501 send(c, okmsg, sizeof okmsg-1, 0); 2502 else 2503 send(c, noauthmsg, sizeof noauthmsg-1, 0); 2504 } 2505 if (strstr(buffer, "PUT /upload2.txt")) 2506 { 2507 if (strstr(buffer, "Authorization: Basic dXNlcjpwd2Q=")) 2508 send(c, okmsg, sizeof okmsg-1, 0); 2509 else 2510 send(c, notokmsg, sizeof notokmsg-1, 0); 2511 } 2512 if (strstr(buffer, "HEAD /upload3.txt")) 2513 { 2514 if (strstr(buffer, "Authorization: Basic dXNlcjE6cHdkMQ==")) 2515 send(c, okmsg, sizeof okmsg-1, 0); 2516 else 2517 send(c, noauthmsg, sizeof noauthmsg-1, 0); 2518 } 2519 if (strstr(buffer, "HEAD /upload4.txt")) 2520 { 2521 if (strstr(buffer, "Authorization: Bearer dXNlcjE6cHdkMQ==")) 2522 send(c, okmsg, sizeof okmsg-1, 0); 2523 else if (strstr(buffer, "Authorization: Basic dXNlcjpwd2Q=")) 2524 send(c, okmsg201, sizeof okmsg-1, 0); 2525 else 2526 send(c, noauthmsg, sizeof noauthmsg-1, 0); 2527 } 2528 if (strstr(buffer, "/test_cookie_path1")) 2529 { 2530 if (strstr(buffer, "subcookie=data")) 2531 send(c, okmsg, sizeof okmsg-1, 0); 2532 else 2533 send(c, notokmsg, sizeof notokmsg-1, 0); 2534 } 2535 if (strstr(buffer, "/test_cookie_path2")) 2536 { 2537 if (strstr(buffer, "subcookie2=data")) 2538 send(c, okmsg, sizeof okmsg-1, 0); 2539 else 2540 send(c, notokmsg, sizeof notokmsg-1, 0); 2541 } 2542 if (strstr(buffer, "/test_cookie_set_path")) 2543 { 2544 send(c, okmsg_cookie_path, sizeof okmsg_cookie_path-1, 0); 2545 } 2546 if (strstr(buffer, "/test_cookie_merge")) 2547 { 2548 if (strstr(buffer, "subcookie=data") && 2549 !strstr(buffer, "manual_cookie=test")) 2550 send(c, okmsg, sizeof okmsg-1, 0); 2551 else 2552 send(c, notokmsg, sizeof notokmsg-1, 0); 2553 } 2554 if (strstr(buffer, "/test_cookie_set_host_override")) 2555 { 2556 send(c, okmsg_cookie, sizeof okmsg_cookie-1, 0); 2557 } 2558 if (strstr(buffer, "/test_cookie_check_host_override")) 2559 { 2560 if (strstr(buffer, "Cookie:") && strstr(buffer, "testcookie=testvalue")) 2561 send(c, okmsg, sizeof okmsg-1, 0); 2562 else 2563 send(c, notokmsg, sizeof notokmsg-1, 0); 2564 } 2565 if (strstr(buffer, "/test_cookie_check_different_host")) 2566 { 2567 if (!strstr(buffer, "foo") && 2568 strstr(buffer, "cookie=biscuit")) 2569 send(c, okmsg, sizeof okmsg-1, 0); 2570 else 2571 send(c, notokmsg, sizeof notokmsg-1, 0); 2572 } 2573 if (strstr(buffer, "/test_host_override")) 2574 { 2575 if (strstr(buffer, host_header_override)) 2576 send(c, okmsg, sizeof okmsg-1, 0); 2577 else 2578 send(c, notokmsg, sizeof notokmsg-1, 0); 2579 } 2580 if (strstr(buffer, "/async_read")) 2581 { 2582 const char *page1_mid = page1 + (sizeof page1 - 1)/2; 2583 const char *page1_end = page1 + sizeof page1 - 1; 2584 send(c, okmsg, sizeof okmsg-1, 0); 2585 send(c, page1, page1_mid - page1, 0); 2586 WaitForSingleObject(conn_wait_event, INFINITE); 2587 send(c, page1_mid, page1_end - page1_mid, 0); 2588 } 2589 if (strstr(buffer, "/socket")) 2590 { 2591 server_socket = c; 2592 SetEvent(server_req_rec_event); 2593 WaitForSingleObject(conn_wait_event, INFINITE); 2594 } 2595 if (strstr(buffer, "/echo_request")) 2596 { 2597 send(c, okmsg, sizeof(okmsg)-1, 0); 2598 send(c, buffer, strlen(buffer), 0); 2599 } 2600 if (strstr(buffer, "GET /test_remove_dot_segments")) 2601 { 2602 send(c, okmsg, sizeof(okmsg)-1, 0); 2603 } 2604 2605 if (strstr(buffer, "HEAD /test_large_content")) 2606 { 2607 char msg[sizeof(largemsg) + 16]; 2608 sprintf(msg, largemsg, content_length); 2609 send(c, msg, strlen(msg), 0); 2610 } 2611 if (strstr(buffer, "HEAD /test_auth_host1")) 2612 { 2613 if (strstr(buffer, "Authorization: Basic dGVzdDE6cGFzcw==")) 2614 send(c, okmsg, sizeof okmsg-1, 0); 2615 else 2616 send(c, noauthmsg, sizeof noauthmsg-1, 0); 2617 } 2618 if (strstr(buffer, "HEAD /test_auth_host2")) 2619 { 2620 if (strstr(buffer, "Authorization: Basic dGVzdDE6cGFzczI=")) 2621 send(c, okmsg, sizeof okmsg-1, 0); 2622 else 2623 send(c, noauthmsg, sizeof noauthmsg-1, 0); 2624 } 2625 shutdown(c, 2); 2626 closesocket(c); 2627 c = -1; 2628 } while (!last_request); 2629 2630 closesocket(s); 2631 HeapFree(GetProcessHeap(), 0, buffer); 2632 2633 return 0; 2634 } 2635 2636 static void test_basic_request(int port, const char *verb, const char *url) 2637 { 2638 test_request_t req; 2639 DWORD r, count, error; 2640 char buffer[0x100]; 2641 2642 trace("basic request %s %s\n", verb, url); 2643 2644 open_simple_request(&req, "localhost", port, verb, url); 2645 2646 SetLastError(0xdeadbeef); 2647 r = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 2648 error = GetLastError(); 2649 ok(error == ERROR_SUCCESS || broken(error != ERROR_SUCCESS), "expected ERROR_SUCCESS, got %u\n", error); 2650 ok(r, "HttpSendRequest failed: %u\n", GetLastError()); 2651 2652 count = 0; 2653 memset(buffer, 0, sizeof buffer); 2654 SetLastError(0xdeadbeef); 2655 r = InternetReadFile(req.request, buffer, sizeof buffer, &count); 2656 ok(r, "InternetReadFile failed %u\n", GetLastError()); 2657 ok(count == sizeof page1 - 1, "count was wrong\n"); 2658 ok(!memcmp(buffer, page1, sizeof page1), "http data wrong, got: %s\n", buffer); 2659 2660 close_request(&req); 2661 } 2662 2663 static void test_proxy_indirect(int port) 2664 { 2665 test_request_t req; 2666 DWORD r, sz; 2667 char buffer[0x40]; 2668 2669 open_simple_request(&req, "localhost", port, NULL, "/test2"); 2670 2671 r = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 2672 ok(r, "HttpSendRequest failed %u\n", GetLastError()); 2673 2674 sz = sizeof buffer; 2675 r = HttpQueryInfoA(req.request, HTTP_QUERY_PROXY_AUTHENTICATE, buffer, &sz, NULL); 2676 ok(r || GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, "HttpQueryInfo failed: %d\n", GetLastError()); 2677 if (!r) 2678 { 2679 skip("missing proxy header, not testing remaining proxy headers\n"); 2680 goto out; 2681 } 2682 ok(!strcmp(buffer, "Basic realm=\"placebo\""), "proxy auth info wrong\n"); 2683 2684 test_status_code(req.request, 407); 2685 test_request_flags(req.request, 0); 2686 2687 sz = sizeof buffer; 2688 r = HttpQueryInfoA(req.request, HTTP_QUERY_STATUS_TEXT, buffer, &sz, NULL); 2689 ok(r, "HttpQueryInfo failed\n"); 2690 ok(!strcmp(buffer, "Proxy Authentication Required"), "proxy text wrong\n"); 2691 2692 sz = sizeof buffer; 2693 r = HttpQueryInfoA(req.request, HTTP_QUERY_VERSION, buffer, &sz, NULL); 2694 ok(r, "HttpQueryInfo failed\n"); 2695 ok(!strcmp(buffer, "HTTP/1.1"), "http version wrong\n"); 2696 2697 sz = sizeof buffer; 2698 r = HttpQueryInfoA(req.request, HTTP_QUERY_SERVER, buffer, &sz, NULL); 2699 ok(r, "HttpQueryInfo failed\n"); 2700 ok(!strcmp(buffer, "winetest"), "http server wrong\n"); 2701 2702 sz = sizeof buffer; 2703 r = HttpQueryInfoA(req.request, HTTP_QUERY_CONTENT_ENCODING, buffer, &sz, NULL); 2704 ok(GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, "HttpQueryInfo should fail\n"); 2705 ok(r == FALSE, "HttpQueryInfo failed\n"); 2706 2707 out: 2708 close_request(&req); 2709 } 2710 2711 static void test_proxy_direct(int port) 2712 { 2713 HINTERNET hi, hc, hr; 2714 DWORD r, sz, error; 2715 char buffer[0x40], *url; 2716 WCHAR bufferW[0x40]; 2717 static const char url_fmt[] = "http://test.winehq.org:%u/test2"; 2718 static CHAR username[] = "mike", 2719 password[] = "1101", 2720 useragent[] = "winetest"; 2721 static const WCHAR usernameW[] = {'m','i','k','e',0}, 2722 passwordW[] = {'1','1','0','1',0}, 2723 useragentW[] = {'w','i','n','e','t','e','s','t',0}; 2724 2725 /* specify proxy type without the proxy and bypass */ 2726 SetLastError(0xdeadbeef); 2727 hi = InternetOpenW(NULL, INTERNET_OPEN_TYPE_PROXY, NULL, NULL, 0); 2728 error = GetLastError(); 2729 ok(error == ERROR_INVALID_PARAMETER || 2730 broken(error == ERROR_SUCCESS) /* WinXPProSP2 */, "got %u\n", error); 2731 ok(hi == NULL || broken(!!hi) /* WinXPProSP2 */, "open should have failed\n"); 2732 2733 sprintf(buffer, "localhost:%d\n", port); 2734 hi = InternetOpenA(NULL, INTERNET_OPEN_TYPE_PROXY, buffer, NULL, 0); 2735 ok(hi != NULL, "open failed\n"); 2736 2737 /* try connect without authorization */ 2738 hc = InternetConnectA(hi, "test.winehq.org", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 2739 ok(hc != NULL, "connect failed\n"); 2740 2741 hr = HttpOpenRequestA(hc, NULL, "/test2", NULL, NULL, NULL, 0, 0); 2742 ok(hr != NULL, "HttpOpenRequest failed\n"); 2743 2744 sz = 0; 2745 SetLastError(0xdeadbeef); 2746 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_PASSWORD, NULL, &sz); 2747 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2748 ok(!r, "unexpected success\n"); 2749 ok(sz == 1, "got %u\n", sz); 2750 2751 sz = 0; 2752 SetLastError(0xdeadbeef); 2753 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_USERNAME, NULL, &sz); 2754 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2755 ok(!r, "unexpected success\n"); 2756 ok(sz == 1, "got %u\n", sz); 2757 2758 sz = sizeof(buffer); 2759 SetLastError(0xdeadbeef); 2760 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_PASSWORD, buffer, &sz); 2761 ok(r, "unexpected failure %u\n", GetLastError()); 2762 ok(!sz, "got %u\n", sz); 2763 2764 sz = sizeof(buffer); 2765 SetLastError(0xdeadbeef); 2766 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_USERNAME, buffer, &sz); 2767 ok(r, "unexpected failure %u\n", GetLastError()); 2768 ok(!sz, "got %u\n", sz); 2769 2770 sz = 0; 2771 SetLastError(0xdeadbeef); 2772 r = InternetQueryOptionA(hr, INTERNET_OPTION_PASSWORD, NULL, &sz); 2773 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2774 ok(!r, "unexpected success\n"); 2775 ok(sz == 1, "got %u\n", sz); 2776 2777 sz = 0; 2778 SetLastError(0xdeadbeef); 2779 r = InternetQueryOptionA(hr, INTERNET_OPTION_USERNAME, NULL, &sz); 2780 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2781 ok(!r, "unexpected success\n"); 2782 ok(sz == 1, "got %u\n", sz); 2783 2784 sz = sizeof(buffer); 2785 SetLastError(0xdeadbeef); 2786 r = InternetQueryOptionA(hr, INTERNET_OPTION_PASSWORD, buffer, &sz); 2787 ok(r, "unexpected failure %u\n", GetLastError()); 2788 ok(!sz, "got %u\n", sz); 2789 2790 sz = sizeof(buffer); 2791 SetLastError(0xdeadbeef); 2792 r = InternetQueryOptionA(hr, INTERNET_OPTION_USERNAME, buffer, &sz); 2793 ok(r, "unexpected failure %u\n", GetLastError()); 2794 ok(!sz, "got %u\n", sz); 2795 2796 sz = 0; 2797 SetLastError(0xdeadbeef); 2798 r = InternetQueryOptionA(hr, INTERNET_OPTION_URL, NULL, &sz); 2799 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2800 ok(!r, "unexpected success\n"); 2801 ok(sz == 34, "got %u\n", sz); 2802 2803 sz = sizeof(buffer); 2804 SetLastError(0xdeadbeef); 2805 r = InternetQueryOptionA(hr, INTERNET_OPTION_URL, buffer, &sz); 2806 ok(r, "unexpected failure %u\n", GetLastError()); 2807 ok(sz == 33, "got %u\n", sz); 2808 2809 r = HttpSendRequestW(hr, NULL, 0, NULL, 0); 2810 ok(r || broken(!r), "HttpSendRequest failed %u\n", GetLastError()); 2811 if (!r) 2812 { 2813 win_skip("skipping proxy tests on broken wininet\n"); 2814 goto done; 2815 } 2816 2817 test_status_code(hr, 407); 2818 2819 /* set the user + password then try again */ 2820 r = InternetSetOptionA(hi, INTERNET_OPTION_PROXY_USERNAME, username, 4); 2821 ok(!r, "unexpected success\n"); 2822 2823 r = InternetSetOptionA(hc, INTERNET_OPTION_PROXY_USERNAME, username, 4); 2824 ok(r, "failed to set user\n"); 2825 2826 r = InternetSetOptionA(hr, INTERNET_OPTION_PROXY_USERNAME, username, 4); 2827 ok(r, "failed to set user\n"); 2828 2829 buffer[0] = 0; 2830 sz = 3; 2831 SetLastError(0xdeadbeef); 2832 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_USERNAME, buffer, &sz); 2833 ok(!r, "unexpected failure %u\n", GetLastError()); 2834 ok(!buffer[0], "got %s\n", buffer); 2835 ok(sz == strlen(username) + 1, "got %u\n", sz); 2836 2837 buffer[0] = 0; 2838 sz = 0; 2839 SetLastError(0xdeadbeef); 2840 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_USERNAME, buffer, &sz); 2841 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2842 ok(!r, "unexpected success\n"); 2843 ok(sz == strlen(username) + 1, "got %u\n", sz); 2844 2845 bufferW[0] = 0; 2846 sz = 0; 2847 SetLastError(0xdeadbeef); 2848 r = InternetQueryOptionW(hr, INTERNET_OPTION_PROXY_USERNAME, bufferW, &sz); 2849 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2850 ok(!r, "unexpected success\n"); 2851 ok(sz == (lstrlenW(usernameW) + 1) * sizeof(WCHAR), "got %u\n", sz); 2852 2853 buffer[0] = 0; 2854 sz = sizeof(buffer); 2855 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_USERNAME, buffer, &sz); 2856 ok(r, "failed to get username\n"); 2857 ok(!strcmp(buffer, username), "got %s\n", buffer); 2858 ok(sz == strlen(username), "got %u\n", sz); 2859 2860 buffer[0] = 0; 2861 sz = sizeof(bufferW); 2862 r = InternetQueryOptionW(hr, INTERNET_OPTION_PROXY_USERNAME, bufferW, &sz); 2863 ok(r, "failed to get username\n"); 2864 ok(!lstrcmpW(bufferW, usernameW), "wrong username\n"); 2865 ok(sz == lstrlenW(usernameW), "got %u\n", sz); 2866 2867 r = InternetSetOptionA(hr, INTERNET_OPTION_PROXY_USERNAME, username, 1); 2868 ok(r, "failed to set user\n"); 2869 2870 buffer[0] = 0; 2871 sz = sizeof(buffer); 2872 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_USERNAME, buffer, &sz); 2873 ok(r, "failed to get username\n"); 2874 ok(!strcmp(buffer, username), "got %s\n", buffer); 2875 ok(sz == strlen(username), "got %u\n", sz); 2876 2877 r = InternetSetOptionA(hi, INTERNET_OPTION_USER_AGENT, useragent, 1); 2878 ok(r, "failed to set useragent\n"); 2879 2880 buffer[0] = 0; 2881 sz = 0; 2882 SetLastError(0xdeadbeef); 2883 r = InternetQueryOptionA(hi, INTERNET_OPTION_USER_AGENT, buffer, &sz); 2884 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2885 ok(!r, "unexpected success\n"); 2886 ok(sz == strlen(useragent) + 1, "got %u\n", sz); 2887 2888 buffer[0] = 0; 2889 sz = sizeof(buffer); 2890 r = InternetQueryOptionA(hi, INTERNET_OPTION_USER_AGENT, buffer, &sz); 2891 ok(r, "failed to get user agent\n"); 2892 ok(!strcmp(buffer, useragent), "got %s\n", buffer); 2893 ok(sz == strlen(useragent), "got %u\n", sz); 2894 2895 bufferW[0] = 0; 2896 sz = 0; 2897 SetLastError(0xdeadbeef); 2898 r = InternetQueryOptionW(hi, INTERNET_OPTION_USER_AGENT, bufferW, &sz); 2899 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2900 ok(!r, "unexpected success\n"); 2901 ok(sz == (lstrlenW(useragentW) + 1) * sizeof(WCHAR), "got %u\n", sz); 2902 2903 bufferW[0] = 0; 2904 sz = sizeof(bufferW); 2905 r = InternetQueryOptionW(hi, INTERNET_OPTION_USER_AGENT, bufferW, &sz); 2906 ok(r, "failed to get user agent\n"); 2907 ok(!lstrcmpW(bufferW, useragentW), "wrong user agent\n"); 2908 ok(sz == lstrlenW(useragentW), "got %u\n", sz); 2909 2910 r = InternetSetOptionA(hr, INTERNET_OPTION_USERNAME, username, 1); 2911 ok(r, "failed to set user\n"); 2912 2913 buffer[0] = 0; 2914 sz = 0; 2915 SetLastError(0xdeadbeef); 2916 r = InternetQueryOptionA(hr, INTERNET_OPTION_USERNAME, buffer, &sz); 2917 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2918 ok(!r, "unexpected success\n"); 2919 ok(sz == strlen(username) + 1, "got %u\n", sz); 2920 2921 buffer[0] = 0; 2922 sz = sizeof(buffer); 2923 r = InternetQueryOptionA(hr, INTERNET_OPTION_USERNAME, buffer, &sz); 2924 ok(r, "failed to get user\n"); 2925 ok(!strcmp(buffer, username), "got %s\n", buffer); 2926 ok(sz == strlen(username), "got %u\n", sz); 2927 2928 bufferW[0] = 0; 2929 sz = 0; 2930 SetLastError(0xdeadbeef); 2931 r = InternetQueryOptionW(hr, INTERNET_OPTION_USERNAME, bufferW, &sz); 2932 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2933 ok(!r, "unexpected success\n"); 2934 ok(sz == (lstrlenW(usernameW) + 1) * sizeof(WCHAR), "got %u\n", sz); 2935 2936 bufferW[0] = 0; 2937 sz = sizeof(bufferW); 2938 r = InternetQueryOptionW(hr, INTERNET_OPTION_USERNAME, bufferW, &sz); 2939 ok(r, "failed to get user\n"); 2940 ok(!lstrcmpW(bufferW, usernameW), "wrong user\n"); 2941 ok(sz == lstrlenW(usernameW), "got %u\n", sz); 2942 2943 r = InternetSetOptionA(hr, INTERNET_OPTION_PASSWORD, password, 1); 2944 ok(r, "failed to set password\n"); 2945 2946 buffer[0] = 0; 2947 sz = 0; 2948 SetLastError(0xdeadbeef); 2949 r = InternetQueryOptionA(hr, INTERNET_OPTION_PASSWORD, buffer, &sz); 2950 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2951 ok(!r, "unexpected success\n"); 2952 ok(sz == strlen(password) + 1, "got %u\n", sz); 2953 2954 buffer[0] = 0; 2955 sz = sizeof(buffer); 2956 r = InternetQueryOptionA(hr, INTERNET_OPTION_PASSWORD, buffer, &sz); 2957 ok(r, "failed to get password\n"); 2958 ok(!strcmp(buffer, password), "got %s\n", buffer); 2959 ok(sz == strlen(password), "got %u\n", sz); 2960 2961 bufferW[0] = 0; 2962 sz = 0; 2963 SetLastError(0xdeadbeef); 2964 r = InternetQueryOptionW(hr, INTERNET_OPTION_PASSWORD, bufferW, &sz); 2965 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2966 ok(!r, "unexpected success\n"); 2967 ok(sz == (lstrlenW(passwordW) + 1) * sizeof(WCHAR), "got %u\n", sz); 2968 2969 bufferW[0] = 0; 2970 sz = sizeof(bufferW); 2971 r = InternetQueryOptionW(hr, INTERNET_OPTION_PASSWORD, bufferW, &sz); 2972 ok(r, "failed to get password\n"); 2973 ok(!lstrcmpW(bufferW, passwordW), "wrong password\n"); 2974 ok(sz == lstrlenW(passwordW), "got %u\n", sz); 2975 2976 url = HeapAlloc(GetProcessHeap(), 0, strlen(url_fmt) + 11); 2977 sprintf(url, url_fmt, port); 2978 buffer[0] = 0; 2979 sz = 0; 2980 SetLastError(0xdeadbeef); 2981 r = InternetQueryOptionA(hr, INTERNET_OPTION_URL, buffer, &sz); 2982 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2983 ok(!r, "unexpected success\n"); 2984 ok(sz == strlen(url) + 1, "got %u\n", sz); 2985 2986 buffer[0] = 0; 2987 sz = sizeof(buffer); 2988 r = InternetQueryOptionA(hr, INTERNET_OPTION_URL, buffer, &sz); 2989 ok(r, "failed to get url\n"); 2990 ok(!strcmp(buffer, url), "got %s\n", buffer); 2991 ok(sz == strlen(url), "got %u\n", sz); 2992 2993 bufferW[0] = 0; 2994 sz = 0; 2995 SetLastError(0xdeadbeef); 2996 r = InternetQueryOptionW(hr, INTERNET_OPTION_URL, bufferW, &sz); 2997 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 2998 ok(!r, "unexpected success\n"); 2999 ok(sz == (strlen(url) + 1) * sizeof(WCHAR), "got %u\n", sz); 3000 3001 bufferW[0] = 0; 3002 sz = sizeof(bufferW); 3003 r = InternetQueryOptionW(hr, INTERNET_OPTION_URL, bufferW, &sz); 3004 ok(r, "failed to get url\n"); 3005 ok(!strcmp_wa(bufferW, url), "wrong url\n"); 3006 ok(sz == strlen(url), "got %u\n", sz); 3007 HeapFree(GetProcessHeap(), 0, url); 3008 3009 r = InternetSetOptionA(hr, INTERNET_OPTION_PROXY_PASSWORD, password, 4); 3010 ok(r, "failed to set password\n"); 3011 3012 buffer[0] = 0; 3013 sz = 0; 3014 SetLastError(0xdeadbeef); 3015 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_PASSWORD, buffer, &sz); 3016 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 3017 ok(!r, "unexpected success\n"); 3018 ok(sz == strlen(password) + 1, "got %u\n", sz); 3019 3020 buffer[0] = 0; 3021 sz = sizeof(buffer); 3022 r = InternetQueryOptionA(hr, INTERNET_OPTION_PROXY_PASSWORD, buffer, &sz); 3023 ok(r, "failed to get password\n"); 3024 ok(!strcmp(buffer, password), "got %s\n", buffer); 3025 ok(sz == strlen(password), "got %u\n", sz); 3026 3027 bufferW[0] = 0; 3028 sz = 0; 3029 SetLastError(0xdeadbeef); 3030 r = InternetQueryOptionW(hr, INTERNET_OPTION_PROXY_PASSWORD, bufferW, &sz); 3031 ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %u\n", GetLastError()); 3032 ok(!r, "unexpected success\n"); 3033 ok(sz == (lstrlenW(passwordW) + 1) * sizeof(WCHAR), "got %u\n", sz); 3034 3035 bufferW[0] = 0; 3036 sz = sizeof(bufferW); 3037 r = InternetQueryOptionW(hr, INTERNET_OPTION_PROXY_PASSWORD, bufferW, &sz); 3038 ok(r, "failed to get password\n"); 3039 ok(!lstrcmpW(bufferW, passwordW), "wrong password\n"); 3040 ok(sz == lstrlenW(passwordW), "got %u\n", sz); 3041 3042 r = HttpSendRequestW(hr, NULL, 0, NULL, 0); 3043 if (!r) 3044 { 3045 win_skip("skipping proxy tests on broken wininet\n"); 3046 goto done; 3047 } 3048 ok(r, "HttpSendRequest failed %u\n", GetLastError()); 3049 sz = sizeof buffer; 3050 r = HttpQueryInfoA(hr, HTTP_QUERY_STATUS_CODE, buffer, &sz, NULL); 3051 ok(r, "HttpQueryInfo failed\n"); 3052 ok(!strcmp(buffer, "200"), "proxy code wrong\n"); 3053 3054 InternetCloseHandle(hr); 3055 InternetCloseHandle(hc); 3056 InternetCloseHandle(hi); 3057 3058 sprintf(buffer, "localhost:%d\n", port); 3059 hi = InternetOpenA("winetest", INTERNET_OPEN_TYPE_PROXY, buffer, NULL, 0); 3060 ok(hi != NULL, "InternetOpen failed\n"); 3061 3062 hc = InternetConnectA(hi, "test.winehq.org", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3063 ok(hc != NULL, "InternetConnect failed\n"); 3064 3065 hr = HttpOpenRequestA(hc, "POST", "/test2", NULL, NULL, NULL, INTERNET_FLAG_SECURE, 0); 3066 ok(hr != NULL, "HttpOpenRequest failed\n"); 3067 3068 r = HttpSendRequestA(hr, NULL, 0, (char *)"data", sizeof("data")); 3069 ok(r, "HttpSendRequest failed %u\n", GetLastError()); 3070 3071 test_status_code(hr, 407); 3072 3073 done: 3074 InternetCloseHandle(hr); 3075 InternetCloseHandle(hc); 3076 InternetCloseHandle(hi); 3077 } 3078 3079 static void test_header_handling_order(int port) 3080 { 3081 static const char authorization[] = "Authorization: Basic dXNlcjpwd2Q="; 3082 static const char connection[] = "Connection: Close"; 3083 static const char *types[2] = { "*", NULL }; 3084 char data[32]; 3085 HINTERNET session, connect, request; 3086 DWORD size, status, data_len; 3087 BOOL ret; 3088 3089 session = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3090 ok(session != NULL, "InternetOpen failed\n"); 3091 3092 connect = InternetConnectA(session, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3093 ok(connect != NULL, "InternetConnect failed\n"); 3094 3095 request = HttpOpenRequestA(connect, NULL, "/test3", NULL, NULL, types, INTERNET_FLAG_KEEP_CONNECTION, 0); 3096 ok(request != NULL, "HttpOpenRequest failed\n"); 3097 3098 ret = HttpAddRequestHeadersA(request, authorization, ~0u, HTTP_ADDREQ_FLAG_ADD); 3099 ok(ret, "HttpAddRequestHeaders failed\n"); 3100 3101 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 3102 ok(ret, "HttpSendRequest failed\n"); 3103 3104 test_status_code(request, 200); 3105 test_request_flags(request, 0); 3106 3107 InternetCloseHandle(request); 3108 3109 request = HttpOpenRequestA(connect, NULL, "/test4", NULL, NULL, types, INTERNET_FLAG_KEEP_CONNECTION, 0); 3110 ok(request != NULL, "HttpOpenRequest failed\n"); 3111 3112 ret = HttpSendRequestA(request, connection, ~0u, NULL, 0); 3113 ok(ret, "HttpSendRequest failed\n"); 3114 3115 status = 0; 3116 size = sizeof(status); 3117 ret = HttpQueryInfoA( request, HTTP_QUERY_STATUS_CODE | HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 3118 ok(ret, "HttpQueryInfo failed\n"); 3119 ok(status == 200 || status == 400 /* IE6 */, "got status %u, expected 200 or 400\n", status); 3120 3121 InternetCloseHandle(request); 3122 InternetCloseHandle(connect); 3123 3124 connect = InternetConnectA(session, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3125 ok(connect != NULL, "InternetConnect failed\n"); 3126 3127 request = HttpOpenRequestA(connect, "POST", "/test7", NULL, NULL, types, INTERNET_FLAG_KEEP_CONNECTION, 0); 3128 ok(request != NULL, "HttpOpenRequest failed\n"); 3129 3130 ret = HttpAddRequestHeadersA(request, "Content-Length: 100\r\n", ~0u, HTTP_ADDREQ_FLAG_ADD_IF_NEW); 3131 ok(ret, "HttpAddRequestHeaders failed\n"); 3132 3133 ret = HttpSendRequestA(request, connection, ~0u, NULL, 0); 3134 ok(ret, "HttpSendRequest failed\n"); 3135 3136 status = 0; 3137 size = sizeof(status); 3138 ret = HttpQueryInfoA( request, HTTP_QUERY_STATUS_CODE | HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 3139 ok(ret, "HttpQueryInfo failed\n"); 3140 ok(status == 200, "got status %u, expected 200\n", status); 3141 3142 InternetCloseHandle(request); 3143 InternetCloseHandle(connect); 3144 3145 connect = InternetConnectA(session, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3146 ok(connect != NULL, "InternetConnect failed\n"); 3147 3148 request = HttpOpenRequestA(connect, "POST", "/test7b", NULL, NULL, types, INTERNET_FLAG_KEEP_CONNECTION, 0); 3149 ok(request != NULL, "HttpOpenRequest failed\n"); 3150 3151 ret = HttpAddRequestHeadersA(request, "Content-Length: 100\r\n", ~0u, HTTP_ADDREQ_FLAG_ADD_IF_NEW); 3152 ok(ret, "HttpAddRequestHeaders failed\n"); 3153 3154 data_len = sizeof(data); 3155 memset(data, 'a', sizeof(data)); 3156 ret = HttpSendRequestA(request, NULL, 0, data, data_len); 3157 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 3158 3159 status = 0; 3160 size = sizeof(status); 3161 ret = HttpQueryInfoA( request, HTTP_QUERY_STATUS_CODE | HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 3162 ok(ret, "HttpQueryInfo failed\n"); 3163 ok(status == 200, "got status %u, expected 200\n", status); 3164 3165 InternetCloseHandle(request); 3166 InternetCloseHandle(connect); 3167 InternetCloseHandle(session); 3168 } 3169 3170 static void test_connection_header(int port) 3171 { 3172 HINTERNET ses, con, req; 3173 BOOL ret; 3174 3175 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3176 ok(ses != NULL, "InternetOpen failed\n"); 3177 3178 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3179 ok(con != NULL, "InternetConnect failed\n"); 3180 3181 req = HttpOpenRequestA(con, NULL, "/test8", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3182 ok(req != NULL, "HttpOpenRequest failed\n"); 3183 3184 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3185 ok(ret, "HttpSendRequest failed\n"); 3186 3187 test_status_code(req, 200); 3188 3189 InternetCloseHandle(req); 3190 3191 req = HttpOpenRequestA(con, NULL, "/test9", NULL, NULL, NULL, 0, 0); 3192 ok(req != NULL, "HttpOpenRequest failed\n"); 3193 3194 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3195 ok(ret, "HttpSendRequest failed\n"); 3196 3197 test_status_code(req, 200); 3198 3199 InternetCloseHandle(req); 3200 3201 req = HttpOpenRequestA(con, NULL, "/test9", NULL, NULL, NULL, INTERNET_FLAG_NO_CACHE_WRITE, 0); 3202 ok(req != NULL, "HttpOpenRequest failed\n"); 3203 3204 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3205 ok(ret, "HttpSendRequest failed\n"); 3206 3207 test_status_code(req, 200); 3208 3209 InternetCloseHandle(req); 3210 3211 req = HttpOpenRequestA(con, "POST", "/testA", NULL, NULL, NULL, INTERNET_FLAG_NO_CACHE_WRITE, 0); 3212 ok(req != NULL, "HttpOpenRequest failed\n"); 3213 3214 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3215 ok(ret, "HttpSendRequest failed\n"); 3216 3217 test_status_code(req, 200); 3218 3219 InternetCloseHandle(req); 3220 InternetCloseHandle(con); 3221 InternetCloseHandle(ses); 3222 } 3223 3224 static void test_header_override(int port) 3225 { 3226 char buffer[128], host_header_override[30], full_url[128]; 3227 HINTERNET ses, con, req; 3228 DWORD size, count, err; 3229 BOOL ret; 3230 3231 sprintf(host_header_override, "Host: test.local:%d\r\n", port); 3232 sprintf(full_url, "http://localhost:%d/test_host_override", port); 3233 3234 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3235 ok(ses != NULL, "InternetOpen failed\n"); 3236 3237 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3238 ok(con != NULL, "InternetConnect failed\n"); 3239 3240 req = HttpOpenRequestA(con, NULL, "/test_host_override", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3241 ok(req != NULL, "HttpOpenRequest failed\n"); 3242 3243 size = sizeof(buffer) - 1; 3244 count = 0; 3245 memset(buffer, 0, sizeof(buffer)); 3246 ret = HttpQueryInfoA(req, HTTP_QUERY_HOST | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, &count); 3247 err = GetLastError(); 3248 ok(!ret, "HttpQueryInfo succeeded\n"); 3249 ok(err == ERROR_HTTP_HEADER_NOT_FOUND, "Expected error ERROR_HTTP_HEADER_NOT_FOUND, got %d\n", err); 3250 3251 test_request_url(req, full_url); 3252 3253 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_COALESCE); 3254 ok(ret, "HttpAddRequestHeaders failed\n"); 3255 3256 size = sizeof(buffer) - 1; 3257 count = 0; 3258 memset(buffer, 0, sizeof(buffer)); 3259 ret = HttpQueryInfoA(req, HTTP_QUERY_HOST | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, &count); 3260 ok(ret, "HttpQueryInfo failed\n"); 3261 3262 test_request_url(req, full_url); 3263 3264 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3265 ok(ret, "HttpSendRequest failed\n"); 3266 3267 test_status_code(req, 200); 3268 3269 InternetCloseHandle(req); 3270 req = HttpOpenRequestA(con, NULL, "/test_host_override", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3271 ok(req != NULL, "HttpOpenRequest failed\n"); 3272 3273 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_COALESCE); 3274 ok(ret, "HttpAddRequestHeaders failed\n"); 3275 3276 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_COALESCE); 3277 ok(ret, "HttpAddRequestHeaders failed\n"); 3278 3279 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3280 ok(ret, "HttpSendRequest failed\n"); 3281 3282 test_status_code(req, 400); 3283 3284 InternetCloseHandle(req); 3285 req = HttpOpenRequestA(con, NULL, "/test_host_override", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3286 ok(req != NULL, "HttpOpenRequest failed\n"); 3287 3288 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_ADD); 3289 ok(ret, "HttpAddRequestHeaders failed\n"); 3290 3291 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3292 ok(ret, "HttpSendRequest failed\n"); 3293 3294 test_status_code(req, 200); 3295 3296 InternetCloseHandle(req); 3297 req = HttpOpenRequestA(con, NULL, "/test_host_override", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3298 ok(req != NULL, "HttpOpenRequest failed\n"); 3299 3300 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_REPLACE); 3301 if(ret) { /* win10 returns success */ 3302 trace("replacing host header is supported.\n"); 3303 3304 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3305 ok(ret, "HttpSendRequest failed\n"); 3306 3307 test_status_code(req, 200); 3308 }else { 3309 trace("replacing host header is not supported.\n"); 3310 3311 err = GetLastError(); 3312 ok(err == ERROR_HTTP_HEADER_NOT_FOUND, "Expected error ERROR_HTTP_HEADER_NOT_FOUND, got %d\n", err); 3313 3314 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3315 ok(ret, "HttpSendRequest failed\n"); 3316 3317 test_status_code(req, 400); 3318 } 3319 3320 InternetCloseHandle(req); 3321 InternetSetCookieA("http://localhost", "cookie", "biscuit"); 3322 req = HttpOpenRequestA(con, NULL, "/testC", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3323 ok(req != NULL, "HttpOpenRequest failed\n"); 3324 3325 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_ADD); 3326 ok(ret, "HttpAddRequestHeaders failed\n"); 3327 3328 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3329 ok(ret, "HttpSendRequest failed\n"); 3330 3331 test_status_code(req, 200); 3332 3333 InternetCloseHandle(req); 3334 req = HttpOpenRequestA(con, NULL, "/test_cookie_set_host_override", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3335 ok(req != NULL, "HttpOpenRequest failed\n"); 3336 3337 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_ADD); 3338 ok(ret, "HttpAddRequestHeaders failed\n"); 3339 3340 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3341 ok(ret, "HttpSendRequest failed\n"); 3342 3343 test_status_code(req, 200); 3344 3345 InternetCloseHandle(req); 3346 req = HttpOpenRequestA(con, NULL, "/test_cookie_check_host_override", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3347 ok(req != NULL, "HttpOpenRequest failed\n"); 3348 3349 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_ADD); 3350 ok(ret, "HttpAddRequestHeaders failed\n"); 3351 3352 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3353 ok(ret, "HttpSendRequest failed\n"); 3354 3355 test_status_code(req, 200); 3356 3357 InternetCloseHandle(req); 3358 req = HttpOpenRequestA(con, NULL, "/test_cookie_check_host_override", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3359 ok(req != NULL, "HttpOpenRequest failed\n"); 3360 3361 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3362 ok(ret, "HttpSendRequest failed\n"); 3363 3364 test_status_code(req, 200); 3365 3366 InternetCloseHandle(req); 3367 InternetSetCookieA("http://test.local", "foo", "bar"); 3368 req = HttpOpenRequestA(con, NULL, "/test_cookie_check_different_host", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3369 ok(req != NULL, "HttpOpenRequest failed\n"); 3370 3371 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3372 ok(ret, "HttpSendRequest failed\n"); 3373 3374 test_status_code(req, 200); 3375 3376 InternetCloseHandle(req); 3377 req = HttpOpenRequestA(con, NULL, "/test_cookie_check_different_host", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 3378 ok(req != NULL, "HttpOpenRequest failed\n"); 3379 3380 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_ADD); 3381 ok(ret, "HttpAddRequestHeaders failed\n"); 3382 3383 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3384 ok(ret, "HttpSendRequest failed\n"); 3385 3386 test_status_code(req, 200); 3387 3388 InternetCloseHandle(req); 3389 InternetCloseHandle(con); 3390 InternetCloseHandle(ses); 3391 3392 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3393 ok(ses != NULL, "InternetOpenA failed\n"); 3394 3395 con = InternetConnectA(ses, "localhost", port, "test1", "pass", INTERNET_SERVICE_HTTP, 0, 0); 3396 ok(con != NULL, "InternetConnectA failed %u\n", GetLastError()); 3397 3398 req = HttpOpenRequestA( con, "HEAD", "/test_auth_host1", NULL, NULL, NULL, 0, 0); 3399 ok(req != NULL, "HttpOpenRequestA failed %u\n", GetLastError()); 3400 3401 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3402 ok(ret, "HttpSendRequestA failed %u\n", GetLastError()); 3403 3404 test_status_code(req, 200); 3405 3406 InternetCloseHandle(req); 3407 InternetCloseHandle(con); 3408 InternetCloseHandle(ses); 3409 3410 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3411 ok(ses != NULL, "InternetOpenA failed\n"); 3412 3413 con = InternetConnectA( ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3414 ok(con != NULL, "InternetConnectA failed %u\n", GetLastError()); 3415 3416 req = HttpOpenRequestA(con, "HEAD", "/test_auth_host1", NULL, NULL, NULL, 0, 0); 3417 ok(req != NULL, "HttpOpenRequestA failed %u\n", GetLastError()); 3418 3419 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_ADD); 3420 ok(ret, "HttpAddRequestHeaders failed\n"); 3421 3422 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 3423 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 3424 3425 test_status_code(req, 200); 3426 3427 InternetCloseHandle(req); 3428 InternetCloseHandle(con); 3429 InternetCloseHandle(ses); 3430 3431 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3432 ok(ses != NULL, "InternetOpenA failed\n"); 3433 3434 con = InternetConnectA(ses, "localhost", port, "test1", "pass2", INTERNET_SERVICE_HTTP, 0, 0); 3435 ok(con != NULL, "InternetConnectA failed %u\n", GetLastError()); 3436 3437 req = HttpOpenRequestA(con, "HEAD", "/test_auth_host2", NULL, NULL, NULL, 0, 0); 3438 ok(req != NULL, "HttpOpenRequestA failed %u\n", GetLastError()); 3439 3440 ret = HttpAddRequestHeadersA(req, host_header_override, ~0u, HTTP_ADDREQ_FLAG_ADD); 3441 ok(ret, "HttpAddRequestHeaders failed\n"); 3442 3443 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3444 ok(ret, "HttpSendRequestA failed %u\n", GetLastError()); 3445 3446 test_status_code(req, 200); 3447 3448 InternetCloseHandle(req); 3449 InternetCloseHandle(con); 3450 InternetCloseHandle(ses); 3451 3452 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3453 ok(ses != NULL, "InternetOpenA failed\n"); 3454 3455 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3456 ok(con != NULL, "InternetConnectA failed %u\n", GetLastError()); 3457 3458 req = HttpOpenRequestA(con, "HEAD", "/test_auth_host2", NULL, NULL, NULL, 0, 0); 3459 ok(req != NULL, "HttpOpenRequestA failed %u\n", GetLastError()); 3460 3461 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3462 ok(ret, "HttpSendRequestA failed %u\n", GetLastError()); 3463 3464 test_status_code(req, 200); 3465 3466 InternetCloseHandle(req); 3467 InternetCloseHandle(con); 3468 InternetCloseHandle(ses); 3469 } 3470 3471 static void test_connection_closing(int port) 3472 { 3473 HINTERNET session, connection, req; 3474 DWORD res; 3475 3476 reset_events(); 3477 3478 session = InternetOpenA("", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, INTERNET_FLAG_ASYNC); 3479 ok(session != NULL,"InternetOpen failed with error %u\n", GetLastError()); 3480 3481 pInternetSetStatusCallbackA(session, callback); 3482 3483 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 3484 connection = InternetConnectA(session, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 3485 ok(connection != NULL,"InternetConnect failed with error %u\n", GetLastError()); 3486 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 3487 3488 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 3489 req = HttpOpenRequestA(connection, "GET", "/testJ", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0xdeadbeaf); 3490 ok(req != NULL, "HttpOpenRequest failed: %u\n", GetLastError()); 3491 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 3492 3493 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 3494 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 3495 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 3496 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 3497 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 3498 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 3499 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 3500 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 3501 SET_OPTIONAL(INTERNET_STATUS_CLOSING_CONNECTION); 3502 SET_OPTIONAL(INTERNET_STATUS_CONNECTION_CLOSED); 3503 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 3504 3505 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 3506 ok(!res && (GetLastError() == ERROR_IO_PENDING), 3507 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 3508 WaitForSingleObject(complete_event, INFINITE); 3509 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 3510 3511 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 3512 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 3513 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 3514 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 3515 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 3516 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 3517 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 3518 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 3519 CLEAR_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 3520 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 3521 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 3522 3523 test_status_code(req, 200); 3524 3525 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 3526 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 3527 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 3528 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 3529 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 3530 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 3531 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 3532 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 3533 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 3534 3535 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 3536 ok(!res && (GetLastError() == ERROR_IO_PENDING), 3537 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 3538 WaitForSingleObject(complete_event, INFINITE); 3539 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 3540 3541 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 3542 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 3543 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 3544 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 3545 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 3546 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 3547 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 3548 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 3549 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 3550 3551 test_status_code(req, 210); 3552 3553 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 3554 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 3555 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 3556 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 3557 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 3558 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 3559 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 3560 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 3561 SET_OPTIONAL(INTERNET_STATUS_CLOSING_CONNECTION); 3562 SET_OPTIONAL(INTERNET_STATUS_CONNECTION_CLOSED); 3563 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 3564 3565 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 3566 ok(!res && (GetLastError() == ERROR_IO_PENDING), 3567 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 3568 WaitForSingleObject(complete_event, INFINITE); 3569 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 3570 3571 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 3572 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 3573 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 3574 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 3575 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 3576 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 3577 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 3578 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 3579 CLEAR_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 3580 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 3581 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 3582 3583 test_status_code(req, 200); 3584 3585 SET_WINE_ALLOW(INTERNET_STATUS_CLOSING_CONNECTION); 3586 SET_WINE_ALLOW(INTERNET_STATUS_CONNECTION_CLOSED); 3587 3588 close_async_handle(session, 2); 3589 } 3590 3591 static void test_successive_HttpSendRequest(int port) 3592 { 3593 HINTERNET session, connection, req; 3594 DWORD res; 3595 3596 reset_events(); 3597 3598 session = InternetOpenA("", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, INTERNET_FLAG_ASYNC); 3599 ok(session != NULL,"InternetOpen failed with error %u\n", GetLastError()); 3600 3601 pInternetSetStatusCallbackA(session, callback); 3602 3603 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 3604 connection = InternetConnectA(session, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 3605 ok(connection != NULL,"InternetConnect failed with error %u\n", GetLastError()); 3606 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 3607 3608 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 3609 req = HttpOpenRequestA(connection, "GET", "/testH", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0xdeadbeaf); 3610 ok(req != NULL, "HttpOpenRequest failed: %u\n", GetLastError()); 3611 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 3612 3613 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 3614 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 3615 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 3616 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 3617 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 3618 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 3619 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 3620 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 3621 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 3622 3623 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 3624 ok(!res && (GetLastError() == ERROR_IO_PENDING), 3625 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 3626 WaitForSingleObject(complete_event, INFINITE); 3627 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 3628 3629 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 3630 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 3631 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 3632 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 3633 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 3634 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 3635 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 3636 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 3637 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 3638 3639 test_status_code(req, 210); 3640 3641 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 3642 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 3643 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 3644 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 3645 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 3646 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 3647 SET_OPTIONAL(INTERNET_STATUS_CLOSING_CONNECTION); 3648 SET_OPTIONAL(INTERNET_STATUS_CONNECTION_CLOSED); 3649 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 3650 3651 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 3652 ok(!res && (GetLastError() == ERROR_IO_PENDING), 3653 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 3654 WaitForSingleObject(complete_event, INFINITE); 3655 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 3656 3657 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 3658 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 3659 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 3660 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 3661 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 3662 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 3663 CLEAR_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 3664 CLEAR_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 3665 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 3666 3667 test_status_code(req, 200); 3668 3669 SET_WINE_ALLOW(INTERNET_STATUS_CLOSING_CONNECTION); 3670 SET_WINE_ALLOW(INTERNET_STATUS_CONNECTION_CLOSED); 3671 3672 close_async_handle(session, 2); 3673 } 3674 3675 static void test_no_content(int port) 3676 { 3677 HINTERNET session, connection, req; 3678 DWORD res; 3679 3680 trace("Testing 204 no content response...\n"); 3681 3682 reset_events(); 3683 3684 session = InternetOpenA("", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, INTERNET_FLAG_ASYNC); 3685 ok(session != NULL,"InternetOpen failed with error %u\n", GetLastError()); 3686 3687 pInternetSetStatusCallbackA(session, callback); 3688 3689 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 3690 connection = InternetConnectA(session, "localhost", port, 3691 NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 3692 ok(connection != NULL,"InternetConnect failed with error %u\n", GetLastError()); 3693 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 3694 3695 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 3696 req = HttpOpenRequestA(connection, "GET", "/test_no_content", NULL, NULL, NULL, 3697 INTERNET_FLAG_KEEP_CONNECTION | INTERNET_FLAG_RESYNCHRONIZE, 0xdeadbead); 3698 ok(req != NULL, "HttpOpenRequest failed: %u\n", GetLastError()); 3699 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 3700 3701 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 3702 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 3703 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 3704 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 3705 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 3706 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 3707 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 3708 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 3709 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 3710 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 3711 3712 res = HttpSendRequestA(req, NULL, -1, NULL, 0); 3713 ok(!res && (GetLastError() == ERROR_IO_PENDING), 3714 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 3715 WaitForSingleObject(complete_event, INFINITE); 3716 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 3717 3718 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 3719 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 3720 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 3721 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 3722 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 3723 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 3724 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 3725 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 3726 3727 close_async_handle(session, 2); 3728 3729 /* 3730 * The connection should be closed before closing handle. This is true for most 3731 * wininet versions (including Wine), but some old win2k versions fail to do that. 3732 */ 3733 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 3734 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 3735 } 3736 3737 static void test_conn_close(int port) 3738 { 3739 HINTERNET session, connection, req; 3740 DWORD res, avail, size; 3741 BYTE buf[1024]; 3742 3743 trace("Testing connection close connection...\n"); 3744 3745 reset_events(); 3746 3747 session = InternetOpenA("", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, INTERNET_FLAG_ASYNC); 3748 ok(session != NULL,"InternetOpen failed with error %u\n", GetLastError()); 3749 3750 pInternetSetStatusCallbackA(session, callback); 3751 3752 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 3753 connection = InternetConnectA(session, "localhost", port, 3754 NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 3755 ok(connection != NULL,"InternetConnect failed with error %u\n", GetLastError()); 3756 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 3757 3758 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 3759 req = HttpOpenRequestA(connection, "GET", "/test_conn_close", NULL, NULL, NULL, 3760 INTERNET_FLAG_KEEP_CONNECTION | INTERNET_FLAG_RESYNCHRONIZE, 0xdeadbead); 3761 ok(req != NULL, "HttpOpenRequest failed: %u\n", GetLastError()); 3762 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 3763 3764 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 3765 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 3766 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 3767 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 3768 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 3769 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 3770 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 3771 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 3772 3773 res = HttpSendRequestA(req, NULL, -1, NULL, 0); 3774 ok(!res && (GetLastError() == ERROR_IO_PENDING), 3775 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 3776 WaitForSingleObject(complete_event, INFINITE); 3777 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 3778 3779 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 3780 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 3781 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 3782 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 3783 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 3784 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 3785 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 3786 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 3787 3788 avail = 0; 3789 res = InternetQueryDataAvailable(req, &avail, 0, 0); 3790 ok(res, "InternetQueryDataAvailable failed: %u\n", GetLastError()); 3791 ok(avail != 0, "avail = 0\n"); 3792 3793 size = 0; 3794 res = InternetReadFile(req, buf, avail, &size); 3795 ok(res, "InternetReadFile failed: %u\n", GetLastError()); 3796 3797 /* IE11 calls those in InternetQueryDataAvailable call. */ 3798 SET_OPTIONAL(INTERNET_STATUS_RECEIVING_RESPONSE); 3799 SET_OPTIONAL(INTERNET_STATUS_RESPONSE_RECEIVED); 3800 3801 res = InternetQueryDataAvailable(req, &avail, 0, 0); 3802 ok(!res && (GetLastError() == ERROR_IO_PENDING), 3803 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 3804 ok(!avail, "avail = %u, expected 0\n", avail); 3805 3806 CLEAR_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 3807 3808 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 3809 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 3810 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 3811 SetEvent(conn_close_event); 3812 WaitForSingleObject(complete_event, INFINITE); 3813 ok(req_error == ERROR_SUCCESS, "req_error = %u\n", req_error); 3814 CLEAR_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 3815 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 3816 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 3817 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 3818 3819 close_async_handle(session, 2); 3820 } 3821 3822 static void test_no_cache(int port) 3823 { 3824 static const char cache_control_no_cache[] = "/test_cache_control_no_cache"; 3825 static const char cache_control_no_store[] = "/test_cache_control_no_store"; 3826 static const char cache_url_fmt[] = "http://localhost:%d%s"; 3827 3828 char cache_url[256], buf[256]; 3829 HINTERNET ses, con, req; 3830 DWORD read, size; 3831 BOOL ret; 3832 3833 trace("Testing no-cache header\n"); 3834 3835 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3836 ok(ses != NULL,"InternetOpen failed with error %u\n", GetLastError()); 3837 3838 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3839 ok(con != NULL, "InternetConnect failed with error %u\n", GetLastError()); 3840 3841 req = HttpOpenRequestA(con, NULL, cache_control_no_cache, NULL, NULL, NULL, 0, 0); 3842 ok(req != NULL, "HttpOpenRequest failed\n"); 3843 3844 sprintf(cache_url, cache_url_fmt, port, cache_control_no_cache); 3845 DeleteUrlCacheEntryA(cache_url); 3846 3847 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3848 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 3849 size = 0; 3850 while(InternetReadFile(req, buf, sizeof(buf), &read) && read) 3851 size += read; 3852 ok(size == 12, "read %d bytes of data\n", size); 3853 InternetCloseHandle(req); 3854 3855 req = HttpOpenRequestA(con, NULL, cache_control_no_cache, NULL, NULL, NULL, 0, 0); 3856 ok(req != NULL, "HttpOpenRequest failed\n"); 3857 3858 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3859 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 3860 size = 0; 3861 while(InternetReadFile(req, buf, sizeof(buf), &read) && read) 3862 size += read; 3863 ok(size == 0, "read %d bytes of data\n", size); 3864 InternetCloseHandle(req); 3865 DeleteUrlCacheEntryA(cache_url); 3866 3867 req = HttpOpenRequestA(con, NULL, cache_control_no_store, NULL, NULL, NULL, 0, 0); 3868 ok(req != NULL, "HttpOpenRequest failed\n"); 3869 3870 sprintf(cache_url, cache_url_fmt, port, cache_control_no_store); 3871 DeleteUrlCacheEntryA(cache_url); 3872 3873 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 3874 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 3875 size = 0; 3876 while(InternetReadFile(req, buf, sizeof(buf), &read) && read) 3877 size += read; 3878 ok(size == 12, "read %d bytes of data\n", size); 3879 InternetCloseHandle(req); 3880 3881 ret = DeleteUrlCacheEntryA(cache_url); 3882 ok(!ret && GetLastError()==ERROR_FILE_NOT_FOUND, "cache entry should not exist\n"); 3883 3884 InternetCloseHandle(con); 3885 InternetCloseHandle(ses); 3886 } 3887 3888 static void test_cache_read_gzipped(int port) 3889 { 3890 static const char cache_url_fmt[] = "http://localhost:%d%s"; 3891 static const char get_gzip[] = "/test_cache_gzip"; 3892 static const char content[] = "gzip test\n"; 3893 static const char text_html[] = "text/html"; 3894 static const char raw_header[] = "HTTP/1.1 200 OK\r\nContent-Type: text/html\r\n\r\n"; 3895 3896 HINTERNET ses, con, req; 3897 DWORD read, size; 3898 char cache_url[256], buf[256]; 3899 BOOL ret; 3900 3901 trace("Testing reading compressed content from cache\n"); 3902 3903 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 3904 ok(ses != NULL,"InternetOpen failed with error %u\n", GetLastError()); 3905 3906 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 3907 ok(con != NULL, "InternetConnect failed with error %u\n", GetLastError()); 3908 3909 req = HttpOpenRequestA(con, NULL, get_gzip, NULL, NULL, NULL, 0, 0); 3910 ok(req != NULL, "HttpOpenRequest failed\n"); 3911 3912 ret = TRUE; 3913 ret = InternetSetOptionA(req, INTERNET_OPTION_HTTP_DECODING, &ret, sizeof(ret)); 3914 if(!ret && GetLastError()==ERROR_INTERNET_INVALID_OPTION) { 3915 win_skip("INTERNET_OPTION_HTTP_DECODING not supported\n"); 3916 InternetCloseHandle(req); 3917 InternetCloseHandle(con); 3918 InternetCloseHandle(ses); 3919 return; 3920 } 3921 ok(ret, "InternetSetOption(INTERNET_OPTION_HTTP_DECODING) failed: %d\n", GetLastError()); 3922 3923 ret = HttpSendRequestA(req, "Accept-Encoding: gzip", -1, NULL, 0); 3924 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 3925 size = 0; 3926 while(InternetReadFile(req, buf+size, sizeof(buf)-size, &read) && read) 3927 size += read; 3928 ok(size == 10, "read %d bytes of data\n", size); 3929 buf[size] = 0; 3930 ok(!strncmp(buf, content, size), "incorrect page content: %s\n", buf); 3931 3932 size = sizeof(buf)-1; 3933 ret = HttpQueryInfoA(req, HTTP_QUERY_CONTENT_TYPE, buf, &size, 0); 3934 ok(ret, "HttpQueryInfo(HTTP_QUERY_CONTENT_TYPE) failed: %d\n", GetLastError()); 3935 buf[size] = 0; 3936 ok(!strncmp(text_html, buf, size), "buf = %s\n", buf); 3937 3938 size = sizeof(buf)-1; 3939 ret = HttpQueryInfoA(req, HTTP_QUERY_RAW_HEADERS_CRLF, buf, &size, 0); 3940 ok(ret, "HttpQueryInfo(HTTP_QUERY_CONTENT_TYPE) failed: %d\n", GetLastError()); 3941 buf[size] = 0; 3942 ok(!strncmp(raw_header, buf, size), "buf = %s\n", buf); 3943 InternetCloseHandle(req); 3944 3945 req = HttpOpenRequestA(con, NULL, get_gzip, NULL, NULL, NULL, INTERNET_FLAG_FROM_CACHE, 0); 3946 ok(req != NULL, "HttpOpenRequest failed\n"); 3947 3948 ret = TRUE; 3949 ret = InternetSetOptionA(req, INTERNET_OPTION_HTTP_DECODING, &ret, sizeof(ret)); 3950 ok(ret, "InternetSetOption(INTERNET_OPTION_HTTP_DECODING) failed: %d\n", GetLastError()); 3951 3952 ret = HttpSendRequestA(req, "Accept-Encoding: gzip", -1, NULL, 0); 3953 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 3954 size = 0; 3955 while(InternetReadFile(req, buf+size, sizeof(buf)-1-size, &read) && read) 3956 size += read; 3957 todo_wine ok(size == 10, "read %d bytes of data\n", size); 3958 buf[size] = 0; 3959 ok(!strncmp(buf, content, size), "incorrect page content: %s\n", buf); 3960 3961 size = sizeof(buf); 3962 ret = HttpQueryInfoA(req, HTTP_QUERY_CONTENT_ENCODING, buf, &size, 0); 3963 ok(!ret && GetLastError()==ERROR_HTTP_HEADER_NOT_FOUND, 3964 "HttpQueryInfo(HTTP_QUERY_CONTENT_ENCODING) returned %d, %d\n", 3965 ret, GetLastError()); 3966 3967 size = sizeof(buf)-1; 3968 ret = HttpQueryInfoA(req, HTTP_QUERY_CONTENT_TYPE, buf, &size, 0); 3969 todo_wine ok(ret, "HttpQueryInfo(HTTP_QUERY_CONTENT_TYPE) failed: %d\n", GetLastError()); 3970 buf[size] = 0; 3971 todo_wine ok(!strncmp(text_html, buf, size), "buf = %s\n", buf); 3972 InternetCloseHandle(req); 3973 3974 /* Decompression doesn't work while reading from cache */ 3975 test_cache_gzip = 0; 3976 sprintf(cache_url, cache_url_fmt, port, get_gzip); 3977 DeleteUrlCacheEntryA(cache_url); 3978 3979 req = HttpOpenRequestA(con, NULL, get_gzip, NULL, NULL, NULL, 0, 0); 3980 ok(req != NULL, "HttpOpenRequest failed\n"); 3981 3982 ret = HttpSendRequestA(req, "Accept-Encoding: gzip", -1, NULL, 0); 3983 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 3984 size = 0; 3985 while(InternetReadFile(req, buf+size, sizeof(buf)-1-size, &read) && read) 3986 size += read; 3987 ok(size == 31, "read %d bytes of data\n", size); 3988 InternetCloseHandle(req); 3989 3990 req = HttpOpenRequestA(con, NULL, get_gzip, NULL, NULL, NULL, INTERNET_FLAG_FROM_CACHE, 0); 3991 ok(req != NULL, "HttpOpenRequest failed\n"); 3992 3993 ret = TRUE; 3994 ret = InternetSetOptionA(req, INTERNET_OPTION_HTTP_DECODING, &ret, sizeof(ret)); 3995 ok(ret, "InternetSetOption(INTERNET_OPTION_HTTP_DECODING) failed: %d\n", GetLastError()); 3996 3997 ret = HttpSendRequestA(req, "Accept-Encoding: gzip", -1, NULL, 0); 3998 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 3999 size = 0; 4000 while(InternetReadFile(req, buf+size, sizeof(buf)-1-size, &read) && read) 4001 size += read; 4002 todo_wine ok(size == 31, "read %d bytes of data\n", size); 4003 4004 size = sizeof(buf); 4005 ret = HttpQueryInfoA(req, HTTP_QUERY_CONTENT_ENCODING, buf, &size, 0); 4006 todo_wine ok(ret, "HttpQueryInfo(HTTP_QUERY_CONTENT_ENCODING) failed: %d\n", GetLastError()); 4007 InternetCloseHandle(req); 4008 4009 InternetCloseHandle(con); 4010 InternetCloseHandle(ses); 4011 4012 /* Decompression doesn't work while reading from cache */ 4013 test_cache_gzip = 0; 4014 sprintf(cache_url, cache_url_fmt, port, get_gzip); 4015 DeleteUrlCacheEntryA(cache_url); 4016 4017 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 4018 ok(ses != NULL,"InternetOpen failed with error %u\n", GetLastError()); 4019 4020 ret = TRUE; 4021 ret = InternetSetOptionA(ses, INTERNET_OPTION_HTTP_DECODING, &ret, sizeof(ret)); 4022 ok(ret, "InternetSetOption(INTERNET_OPTION_HTTP_DECODING) failed: %d\n", GetLastError()); 4023 4024 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 4025 ok(con != NULL, "InternetConnect failed with error %u\n", GetLastError()); 4026 4027 req = HttpOpenRequestA(con, NULL, get_gzip, NULL, NULL, NULL, 0, 0); 4028 ok(req != NULL, "HttpOpenRequest failed\n"); 4029 4030 ret = HttpSendRequestA(req, "Accept-Encoding: gzip", -1, NULL, 0); 4031 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 4032 size = 0; 4033 while(InternetReadFile(req, buf+size, sizeof(buf)-1-size, &read) && read) 4034 size += read; 4035 ok(size == 10, "read %d bytes of data\n", size); 4036 buf[size] = 0; 4037 ok(!strncmp(buf, content, size), "incorrect page content: %s\n", buf); 4038 InternetCloseHandle(req); 4039 4040 InternetCloseHandle(con); 4041 InternetCloseHandle(ses); 4042 4043 /* Decompression doesn't work while reading from cache */ 4044 test_cache_gzip = 0; 4045 sprintf(cache_url, cache_url_fmt, port, get_gzip); 4046 DeleteUrlCacheEntryA(cache_url); 4047 4048 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 4049 ok(ses != NULL,"InternetOpen failed with error %u\n", GetLastError()); 4050 4051 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 4052 ok(con != NULL, "InternetConnect failed with error %u\n", GetLastError()); 4053 4054 ret = TRUE; 4055 ret = InternetSetOptionA(con, INTERNET_OPTION_HTTP_DECODING, &ret, sizeof(ret)); 4056 ok(ret, "InternetSetOption(INTERNET_OPTION_HTTP_DECODING) failed: %d\n", GetLastError()); 4057 4058 req = HttpOpenRequestA(con, NULL, get_gzip, NULL, NULL, NULL, 0, 0); 4059 ok(req != NULL, "HttpOpenRequest failed\n"); 4060 4061 ret = HttpSendRequestA(req, "Accept-Encoding: gzip", -1, NULL, 0); 4062 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 4063 size = 0; 4064 while(InternetReadFile(req, buf+size, sizeof(buf)-1-size, &read) && read) 4065 size += read; 4066 ok(size == 10, "read %d bytes of data\n", size); 4067 buf[size] = 0; 4068 ok(!strncmp(buf, content, size), "incorrect page content: %s\n", buf); 4069 InternetCloseHandle(req); 4070 4071 InternetCloseHandle(con); 4072 InternetCloseHandle(ses); 4073 4074 DeleteUrlCacheEntryA(cache_url); 4075 } 4076 4077 static void test_HttpSendRequestW(int port) 4078 { 4079 static const WCHAR header[] = {'U','A','-','C','P','U',':',' ','x','8','6',0}; 4080 HINTERNET ses, con, req; 4081 DWORD error; 4082 BOOL ret; 4083 4084 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, INTERNET_FLAG_ASYNC); 4085 ok(ses != NULL, "InternetOpen failed\n"); 4086 4087 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 4088 ok(con != NULL, "InternetConnect failed\n"); 4089 4090 req = HttpOpenRequestA(con, NULL, "/test1", NULL, NULL, NULL, 0, 0); 4091 ok(req != NULL, "HttpOpenRequest failed\n"); 4092 4093 SetLastError(0xdeadbeef); 4094 ret = HttpSendRequestW(req, header, ~0u, NULL, 0); 4095 error = GetLastError(); 4096 ok(!ret, "HttpSendRequestW succeeded\n"); 4097 ok(error == ERROR_IO_PENDING || 4098 broken(error == ERROR_HTTP_HEADER_NOT_FOUND) || /* IE6 */ 4099 broken(error == ERROR_INVALID_PARAMETER), /* IE5 */ 4100 "got %u expected ERROR_IO_PENDING\n", error); 4101 4102 InternetCloseHandle(req); 4103 InternetCloseHandle(con); 4104 InternetCloseHandle(ses); 4105 } 4106 4107 static void test_cookie_header(int port) 4108 { 4109 HINTERNET ses, con, req; 4110 DWORD size, error; 4111 BOOL ret; 4112 char buffer[256]; 4113 4114 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 4115 ok(ses != NULL, "InternetOpen failed\n"); 4116 4117 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 4118 ok(con != NULL, "InternetConnect failed\n"); 4119 4120 InternetSetCookieA("http://localhost", "cookie", "biscuit"); 4121 4122 req = HttpOpenRequestA(con, NULL, "/testC", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 4123 ok(req != NULL, "HttpOpenRequest failed\n"); 4124 4125 buffer[0] = 0; 4126 size = sizeof(buffer); 4127 SetLastError(0xdeadbeef); 4128 ret = HttpQueryInfoA(req, HTTP_QUERY_COOKIE | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 4129 error = GetLastError(); 4130 ok(!ret, "HttpQueryInfo succeeded\n"); 4131 ok(error == ERROR_HTTP_HEADER_NOT_FOUND, "got %u expected ERROR_HTTP_HEADER_NOT_FOUND\n", error); 4132 4133 ret = HttpAddRequestHeadersA(req, "Cookie: cookie=not biscuit\r\n", ~0u, HTTP_ADDREQ_FLAG_ADD); 4134 ok(ret, "HttpAddRequestHeaders failed: %u\n", GetLastError()); 4135 4136 buffer[0] = 0; 4137 size = sizeof(buffer); 4138 ret = HttpQueryInfoA(req, HTTP_QUERY_COOKIE | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 4139 ok(ret, "HttpQueryInfo failed: %u\n", GetLastError()); 4140 ok(!!strstr(buffer, "cookie=not biscuit"), "got '%s' expected \'cookie=not biscuit\'\n", buffer); 4141 4142 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 4143 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 4144 4145 test_status_code(req, 200); 4146 4147 buffer[0] = 0; 4148 size = sizeof(buffer); 4149 ret = HttpQueryInfoA(req, HTTP_QUERY_COOKIE | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 4150 ok(ret, "HttpQueryInfo failed: %u\n", GetLastError()); 4151 ok(!strstr(buffer, "cookie=not biscuit"), "'%s' should not contain \'cookie=not biscuit\'\n", buffer); 4152 ok(!!strstr(buffer, "cookie=biscuit"), "'%s' should contain \'cookie=biscuit\'\n", buffer); 4153 4154 InternetCloseHandle(req); 4155 4156 InternetSetCookieA("http://localhost/testCCCC", "subcookie", "data"); 4157 4158 req = HttpOpenRequestA(con, NULL, "/test_cookie_path1", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 4159 ok(req != NULL, "HttpOpenRequest failed\n"); 4160 4161 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 4162 ok(ret, "HttpSendRequest failed\n"); 4163 4164 test_status_code(req, 200); 4165 InternetCloseHandle(req); 4166 4167 req = HttpOpenRequestA(con, NULL, "/test_cookie_path1/abc", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 4168 ok(req != NULL, "HttpOpenRequest failed\n"); 4169 4170 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 4171 ok(ret, "HttpSendRequest failed\n"); 4172 4173 test_status_code(req, 200); 4174 InternetCloseHandle(req); 4175 4176 req = HttpOpenRequestA(con, NULL, "/test_cookie_set_path", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 4177 ok(req != NULL, "HttpOpenRequest failed\n"); 4178 4179 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 4180 ok(ret, "HttpSendRequest failed\n"); 4181 4182 test_status_code(req, 200); 4183 InternetCloseHandle(req); 4184 4185 req = HttpOpenRequestA(con, NULL, "/test_cookie_path2", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 4186 ok(req != NULL, "HttpOpenRequest failed\n"); 4187 4188 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 4189 ok(ret, "HttpSendRequest failed\n"); 4190 4191 test_status_code(req, 400); 4192 InternetCloseHandle(req); 4193 4194 req = HttpOpenRequestA(con, NULL, "/test_cookie_merge", NULL, NULL, NULL, INTERNET_FLAG_KEEP_CONNECTION, 0); 4195 ok(req != NULL, "HttpOpenRequest failed\n"); 4196 4197 ret = HttpAddRequestHeadersA(req, "Cookie: manual_cookie=test\r\n", ~0u, HTTP_ADDREQ_FLAG_ADD); 4198 ok(ret, "HttpAddRequestHeaders failed: %u\n", GetLastError()); 4199 4200 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 4201 ok(ret, "HttpSendRequest failed\n"); 4202 4203 test_status_code(req, 200); 4204 InternetCloseHandle(req); 4205 4206 InternetCloseHandle(con); 4207 InternetCloseHandle(ses); 4208 } 4209 4210 static void test_basic_authentication(int port) 4211 { 4212 HINTERNET session, connect, request; 4213 BOOL ret; 4214 4215 session = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 4216 ok(session != NULL, "InternetOpen failed\n"); 4217 4218 connect = InternetConnectA(session, "localhost", port, "user", "pwd", INTERNET_SERVICE_HTTP, 0, 0); 4219 ok(connect != NULL, "InternetConnect failed\n"); 4220 4221 request = HttpOpenRequestA(connect, NULL, "/test3", NULL, NULL, NULL, 0, 0); 4222 ok(request != NULL, "HttpOpenRequest failed\n"); 4223 4224 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 4225 ok(ret, "HttpSendRequest failed %u\n", GetLastError()); 4226 4227 test_status_code(request, 200); 4228 test_request_flags(request, 0); 4229 4230 InternetCloseHandle(request); 4231 InternetCloseHandle(connect); 4232 InternetCloseHandle(session); 4233 } 4234 4235 static void test_premature_disconnect(int port) 4236 { 4237 test_request_t req; 4238 DWORD err; 4239 BOOL ret; 4240 4241 open_simple_request(&req, "localhost", port, NULL, "/premature_disconnect"); 4242 4243 SetLastError(0xdeadbeef); 4244 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 4245 err = GetLastError(); 4246 todo_wine ok(!ret, "HttpSendRequest succeeded\n"); 4247 todo_wine ok(err == ERROR_HTTP_INVALID_SERVER_RESPONSE, "got %u\n", err); 4248 4249 close_request(&req); 4250 } 4251 4252 static void test_invalid_response_headers(int port) 4253 { 4254 test_request_t req; 4255 DWORD size; 4256 BOOL ret; 4257 char buffer[256]; 4258 4259 open_simple_request(&req, "localhost", port, NULL, "/testE"); 4260 4261 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 4262 ok(ret, "HttpSendRequest failed %u\n", GetLastError()); 4263 4264 test_status_code(req.request, 401); 4265 test_request_flags(req.request, 0); 4266 4267 buffer[0] = 0; 4268 size = sizeof(buffer); 4269 ret = HttpQueryInfoA(req.request, HTTP_QUERY_RAW_HEADERS, buffer, &size, NULL); 4270 ok(ret, "HttpQueryInfo failed\n"); 4271 ok(!strcmp(buffer, "HTTP/1.0 401 Anonymous requests or requests on unsecure channel are not allowed"), 4272 "headers wrong \"%s\"\n", buffer); 4273 4274 buffer[0] = 0; 4275 size = sizeof(buffer); 4276 ret = HttpQueryInfoA(req.request, HTTP_QUERY_SERVER, buffer, &size, NULL); 4277 ok(ret, "HttpQueryInfo failed\n"); 4278 ok(!strcmp(buffer, "winetest"), "server wrong \"%s\"\n", buffer); 4279 4280 close_request(&req); 4281 } 4282 4283 static void test_response_without_headers(int port) 4284 { 4285 test_request_t req; 4286 DWORD r, count, size; 4287 char buffer[1024]; 4288 4289 open_simple_request(&req, "localhost", port, NULL, "/testG"); 4290 4291 test_request_flags(req.request, INTERNET_REQFLAG_NO_HEADERS); 4292 4293 r = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 4294 ok(r, "HttpSendRequest failed %u\n", GetLastError()); 4295 4296 test_request_flags_todo(req.request, INTERNET_REQFLAG_NO_HEADERS); 4297 4298 count = 0; 4299 memset(buffer, 0, sizeof buffer); 4300 r = InternetReadFile(req.request, buffer, sizeof buffer, &count); 4301 ok(r, "InternetReadFile failed %u\n", GetLastError()); 4302 todo_wine ok(count == sizeof page1 - 1, "count was wrong\n"); 4303 todo_wine ok(!memcmp(buffer, page1, sizeof page1), "http data wrong\n"); 4304 4305 test_status_code(req.request, 200); 4306 test_request_flags_todo(req.request, INTERNET_REQFLAG_NO_HEADERS); 4307 4308 buffer[0] = 0; 4309 size = sizeof(buffer); 4310 r = HttpQueryInfoA(req.request, HTTP_QUERY_STATUS_TEXT, buffer, &size, NULL ); 4311 ok(r, "HttpQueryInfo failed %u\n", GetLastError()); 4312 ok(!strcmp(buffer, "OK"), "expected OK got: \"%s\"\n", buffer); 4313 4314 buffer[0] = 0; 4315 size = sizeof(buffer); 4316 r = HttpQueryInfoA(req.request, HTTP_QUERY_VERSION, buffer, &size, NULL); 4317 ok(r, "HttpQueryInfo failed %u\n", GetLastError()); 4318 ok(!strcmp(buffer, "HTTP/1.0"), "expected HTTP/1.0 got: \"%s\"\n", buffer); 4319 4320 buffer[0] = 0; 4321 size = sizeof(buffer); 4322 r = HttpQueryInfoA(req.request, HTTP_QUERY_RAW_HEADERS, buffer, &size, NULL); 4323 ok(r, "HttpQueryInfo failed %u\n", GetLastError()); 4324 ok(!strcmp(buffer, "HTTP/1.0 200 OK"), "raw headers wrong: \"%s\"\n", buffer); 4325 4326 close_request(&req); 4327 } 4328 4329 static void test_head_request(int port) 4330 { 4331 DWORD len, content_length; 4332 test_request_t req; 4333 BYTE buf[100]; 4334 BOOL ret; 4335 4336 open_simple_request(&req, "localhost", port, "HEAD", "/test_head"); 4337 4338 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 4339 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 4340 4341 len = sizeof(content_length); 4342 content_length = -1; 4343 ret = HttpQueryInfoA(req.request, HTTP_QUERY_FLAG_NUMBER|HTTP_QUERY_CONTENT_LENGTH, &content_length, &len, 0); 4344 ok(ret, "HttpQueryInfo failed: %u\n", GetLastError()); 4345 ok(len == sizeof(DWORD), "len = %u\n", len); 4346 ok(content_length == 100, "content_length = %u\n", content_length); 4347 4348 len = -1; 4349 ret = InternetReadFile(req.request, buf, sizeof(buf), &len); 4350 ok(ret, "InternetReadFile failed: %u\n", GetLastError()); 4351 4352 len = -1; 4353 ret = InternetReadFile(req.request, buf, sizeof(buf), &len); 4354 ok(ret, "InternetReadFile failed: %u\n", GetLastError()); 4355 4356 close_request(&req); 4357 } 4358 4359 static void test_HttpQueryInfo(int port) 4360 { 4361 test_request_t req; 4362 DWORD size, index, error; 4363 char buffer[1024]; 4364 BOOL ret; 4365 4366 open_simple_request(&req, "localhost", port, NULL, "/testD"); 4367 4368 size = sizeof(buffer); 4369 ret = HttpQueryInfoA(req.request, HTTP_QUERY_STATUS_TEXT, buffer, &size, &index); 4370 error = GetLastError(); 4371 ok(!ret || broken(ret), "HttpQueryInfo succeeded\n"); 4372 if (!ret) ok(error == ERROR_HTTP_HEADER_NOT_FOUND, "got %u expected ERROR_HTTP_HEADER_NOT_FOUND\n", error); 4373 4374 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 4375 ok(ret, "HttpSendRequest failed\n"); 4376 4377 index = 0; 4378 size = sizeof(buffer); 4379 ret = HttpQueryInfoA(req.request, HTTP_QUERY_HOST | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, &index); 4380 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4381 ok(index == 1, "expected 1 got %u\n", index); 4382 4383 index = 0; 4384 size = sizeof(buffer); 4385 ret = HttpQueryInfoA(req.request, HTTP_QUERY_DATE | HTTP_QUERY_FLAG_SYSTEMTIME, buffer, &size, &index); 4386 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4387 ok(index == 1, "expected 1 got %u\n", index); 4388 4389 index = 0; 4390 size = sizeof(buffer); 4391 ret = HttpQueryInfoA(req.request, HTTP_QUERY_RAW_HEADERS, buffer, &size, &index); 4392 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4393 ok(index == 0, "expected 0 got %u\n", index); 4394 4395 size = sizeof(buffer); 4396 ret = HttpQueryInfoA(req.request, HTTP_QUERY_RAW_HEADERS, buffer, &size, &index); 4397 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4398 ok(index == 0, "expected 0 got %u\n", index); 4399 4400 index = 0xdeadbeef; /* invalid start index */ 4401 size = sizeof(buffer); 4402 ret = HttpQueryInfoA(req.request, HTTP_QUERY_RAW_HEADERS, buffer, &size, &index); 4403 todo_wine ok(!ret, "HttpQueryInfo should have failed\n"); 4404 todo_wine ok(GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, 4405 "Expected ERROR_HTTP_HEADER_NOT_FOUND, got %u\n", GetLastError()); 4406 4407 index = 0; 4408 size = sizeof(buffer); 4409 ret = HttpQueryInfoA(req.request, HTTP_QUERY_RAW_HEADERS_CRLF, buffer, &size, &index); 4410 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4411 ok(index == 0, "expected 0 got %u\n", index); 4412 4413 size = sizeof(buffer); 4414 ret = HttpQueryInfoA(req.request, HTTP_QUERY_STATUS_TEXT, buffer, &size, &index); 4415 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4416 ok(index == 0, "expected 0 got %u\n", index); 4417 4418 size = sizeof(buffer); 4419 ret = HttpQueryInfoA(req.request, HTTP_QUERY_VERSION, buffer, &size, &index); 4420 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4421 ok(index == 0, "expected 0 got %u\n", index); 4422 4423 test_status_code(req.request, 200); 4424 4425 index = 0xdeadbeef; 4426 size = sizeof(buffer); 4427 ret = HttpQueryInfoA(req.request, HTTP_QUERY_FORWARDED, buffer, &size, &index); 4428 ok(!ret, "HttpQueryInfo succeeded\n"); 4429 ok(index == 0xdeadbeef, "expected 0xdeadbeef got %u\n", index); 4430 4431 index = 0; 4432 size = sizeof(buffer); 4433 ret = HttpQueryInfoA(req.request, HTTP_QUERY_SERVER, buffer, &size, &index); 4434 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4435 ok(index == 1, "expected 1 got %u\n", index); 4436 4437 index = 0; 4438 size = sizeof(buffer); 4439 strcpy(buffer, "Server"); 4440 ret = HttpQueryInfoA(req.request, HTTP_QUERY_CUSTOM, buffer, &size, &index); 4441 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4442 ok(index == 1, "expected 1 got %u\n", index); 4443 4444 index = 0; 4445 size = sizeof(buffer); 4446 ret = HttpQueryInfoA(req.request, HTTP_QUERY_SET_COOKIE, buffer, &size, &index); 4447 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4448 ok(index == 1, "expected 1 got %u\n", index); 4449 4450 size = sizeof(buffer); 4451 ret = HttpQueryInfoA(req.request, HTTP_QUERY_SET_COOKIE, buffer, &size, &index); 4452 ok(ret, "HttpQueryInfo failed %u\n", GetLastError()); 4453 ok(index == 2, "expected 2 got %u\n", index); 4454 4455 close_request(&req); 4456 } 4457 4458 static void test_options(int port) 4459 { 4460 INTERNET_DIAGNOSTIC_SOCKET_INFO idsi; 4461 HINTERNET ses, con, req; 4462 DWORD size, error; 4463 DWORD_PTR ctx; 4464 BOOL ret; 4465 4466 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 4467 ok(ses != NULL, "InternetOpen failed\n"); 4468 4469 SetLastError(0xdeadbeef); 4470 ret = InternetSetOptionA(ses, INTERNET_OPTION_CONTEXT_VALUE, NULL, 0); 4471 error = GetLastError(); 4472 ok(!ret, "InternetSetOption succeeded\n"); 4473 ok(error == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %u\n", error); 4474 4475 SetLastError(0xdeadbeef); 4476 ret = InternetSetOptionA(ses, INTERNET_OPTION_CONTEXT_VALUE, NULL, sizeof(ctx)); 4477 ok(!ret, "InternetSetOption succeeded\n"); 4478 error = GetLastError(); 4479 ok(error == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %u\n", error); 4480 4481 SetLastError(0xdeadbeef); 4482 ret = InternetSetOptionA(ses, INTERNET_OPTION_CONTEXT_VALUE, &ctx, 0); 4483 ok(!ret, "InternetSetOption succeeded\n"); 4484 error = GetLastError(); 4485 ok(error == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %u\n", error); 4486 4487 ctx = 1; 4488 ret = InternetSetOptionA(ses, INTERNET_OPTION_CONTEXT_VALUE, &ctx, sizeof(ctx)); 4489 ok(ret, "InternetSetOption failed %u\n", GetLastError()); 4490 4491 SetLastError(0xdeadbeef); 4492 ret = InternetQueryOptionA(ses, INTERNET_OPTION_CONTEXT_VALUE, NULL, NULL); 4493 error = GetLastError(); 4494 ok(!ret, "InternetQueryOption succeeded\n"); 4495 ok(error == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %u\n", error); 4496 4497 SetLastError(0xdeadbeef); 4498 ret = InternetQueryOptionA(ses, INTERNET_OPTION_CONTEXT_VALUE, &ctx, NULL); 4499 error = GetLastError(); 4500 ok(!ret, "InternetQueryOption succeeded\n"); 4501 ok(error == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %u\n", error); 4502 4503 size = 0; 4504 SetLastError(0xdeadbeef); 4505 ret = InternetQueryOptionA(ses, INTERNET_OPTION_CONTEXT_VALUE, NULL, &size); 4506 error = GetLastError(); 4507 ok(!ret, "InternetQueryOption succeeded\n"); 4508 ok(error == ERROR_INSUFFICIENT_BUFFER, "expected ERROR_INSUFFICIENT_BUFFER, got %u\n", error); 4509 4510 size = sizeof(ctx); 4511 SetLastError(0xdeadbeef); 4512 ret = InternetQueryOptionA(NULL, INTERNET_OPTION_CONTEXT_VALUE, &ctx, &size); 4513 error = GetLastError(); 4514 ok(!ret, "InternetQueryOption succeeded\n"); 4515 ok(error == ERROR_INTERNET_INCORRECT_HANDLE_TYPE, "expected ERROR_INTERNET_INCORRECT_HANDLE_TYPE, got %u\n", error); 4516 4517 ctx = 0xdeadbeef; 4518 size = sizeof(ctx); 4519 ret = InternetQueryOptionA(ses, INTERNET_OPTION_CONTEXT_VALUE, &ctx, &size); 4520 ok(ret, "InternetQueryOption failed %u\n", GetLastError()); 4521 ok(ctx == 1, "expected 1 got %lu\n", ctx); 4522 4523 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 4524 ok(con != NULL, "InternetConnect failed\n"); 4525 4526 ctx = 0xdeadbeef; 4527 size = sizeof(ctx); 4528 ret = InternetQueryOptionA(con, INTERNET_OPTION_CONTEXT_VALUE, &ctx, &size); 4529 ok(ret, "InternetQueryOption failed %u\n", GetLastError()); 4530 ok(ctx == 0, "expected 0 got %lu\n", ctx); 4531 4532 ctx = 2; 4533 ret = InternetSetOptionA(con, INTERNET_OPTION_CONTEXT_VALUE, &ctx, sizeof(ctx)); 4534 ok(ret, "InternetSetOption failed %u\n", GetLastError()); 4535 4536 ctx = 0xdeadbeef; 4537 size = sizeof(ctx); 4538 ret = InternetQueryOptionA(con, INTERNET_OPTION_CONTEXT_VALUE, &ctx, &size); 4539 ok(ret, "InternetQueryOption failed %u\n", GetLastError()); 4540 ok(ctx == 2, "expected 2 got %lu\n", ctx); 4541 4542 req = HttpOpenRequestA(con, NULL, "/test1", NULL, NULL, NULL, 0, 0); 4543 ok(req != NULL, "HttpOpenRequest failed\n"); 4544 4545 ctx = 0xdeadbeef; 4546 size = sizeof(ctx); 4547 ret = InternetQueryOptionA(req, INTERNET_OPTION_CONTEXT_VALUE, &ctx, &size); 4548 ok(ret, "InternetQueryOption failed %u\n", GetLastError()); 4549 ok(ctx == 0, "expected 0 got %lu\n", ctx); 4550 4551 ctx = 3; 4552 ret = InternetSetOptionA(req, INTERNET_OPTION_CONTEXT_VALUE, &ctx, sizeof(ctx)); 4553 ok(ret, "InternetSetOption failed %u\n", GetLastError()); 4554 4555 ctx = 0xdeadbeef; 4556 size = sizeof(ctx); 4557 ret = InternetQueryOptionA(req, INTERNET_OPTION_CONTEXT_VALUE, &ctx, &size); 4558 ok(ret, "InternetQueryOption failed %u\n", GetLastError()); 4559 ok(ctx == 3, "expected 3 got %lu\n", ctx); 4560 4561 size = sizeof(idsi); 4562 ret = InternetQueryOptionA(req, INTERNET_OPTION_DIAGNOSTIC_SOCKET_INFO, &idsi, &size); 4563 ok(ret, "InternetQueryOption failed %u\n", GetLastError()); 4564 4565 size = 0; 4566 SetLastError(0xdeadbeef); 4567 ret = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, NULL, &size); 4568 error = GetLastError(); 4569 ok(!ret, "InternetQueryOption succeeded\n"); 4570 ok(error == ERROR_INTERNET_INVALID_OPERATION, "expected ERROR_INTERNET_INVALID_OPERATION, got %u\n", error); 4571 4572 /* INTERNET_OPTION_PROXY */ 4573 SetLastError(0xdeadbeef); 4574 ret = InternetQueryOptionA(ses, INTERNET_OPTION_PROXY, NULL, NULL); 4575 error = GetLastError(); 4576 ok(!ret, "InternetQueryOption succeeded\n"); 4577 ok(error == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %u\n", error); 4578 4579 SetLastError(0xdeadbeef); 4580 ret = InternetQueryOptionA(ses, INTERNET_OPTION_PROXY, &ctx, NULL); 4581 error = GetLastError(); 4582 ok(!ret, "InternetQueryOption succeeded\n"); 4583 ok(error == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %u\n", error); 4584 4585 size = 0; 4586 SetLastError(0xdeadbeef); 4587 ret = InternetQueryOptionA(ses, INTERNET_OPTION_PROXY, NULL, &size); 4588 error = GetLastError(); 4589 ok(!ret, "InternetQueryOption succeeded\n"); 4590 ok(error == ERROR_INSUFFICIENT_BUFFER, "expected ERROR_INSUFFICIENT_BUFFER, got %u\n", error); 4591 ok(size >= sizeof(INTERNET_PROXY_INFOA), "expected size to be greater or equal to the struct size\n"); 4592 4593 InternetCloseHandle(req); 4594 InternetCloseHandle(con); 4595 InternetCloseHandle(ses); 4596 } 4597 4598 typedef struct { 4599 const char *response_text; 4600 int status_code; 4601 const char *status_text; 4602 const char *raw_headers; 4603 } http_status_test_t; 4604 4605 static const http_status_test_t http_status_tests[] = { 4606 { 4607 "HTTP/1.1 200 OK\r\n" 4608 "Content-Length: 1\r\n" 4609 "\r\nx", 4610 200, 4611 "OK" 4612 }, 4613 { 4614 "HTTP/1.1 404 Fail\r\n" 4615 "Content-Length: 1\r\n" 4616 "\r\nx", 4617 404, 4618 "Fail" 4619 }, 4620 { 4621 "HTTP/1.1 200\r\n" 4622 "Content-Length: 1\r\n" 4623 "\r\nx", 4624 200, 4625 "" 4626 }, 4627 { 4628 "HTTP/1.1 410 \r\n" 4629 "Content-Length: 1\r\n" 4630 "\r\nx", 4631 410, 4632 "" 4633 } 4634 }; 4635 4636 static void test_http_status(int port) 4637 { 4638 test_request_t req; 4639 char buf[1000]; 4640 DWORD i, size; 4641 BOOL res; 4642 4643 for(i = 0; i < ARRAY_SIZE(http_status_tests); i++) { 4644 send_buffer = http_status_tests[i].response_text; 4645 4646 open_simple_request(&req, "localhost", port, NULL, "/send_from_buffer"); 4647 4648 res = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 4649 ok(res, "HttpSendRequest failed\n"); 4650 4651 test_status_code(req.request, http_status_tests[i].status_code); 4652 4653 size = sizeof(buf); 4654 res = HttpQueryInfoA(req.request, HTTP_QUERY_STATUS_TEXT, buf, &size, NULL); 4655 ok(res, "HttpQueryInfo failed: %u\n", GetLastError()); 4656 ok(!strcmp(buf, http_status_tests[i].status_text), "[%u] Unexpected status text \"%s\", expected \"%s\"\n", 4657 i, buf, http_status_tests[i].status_text); 4658 4659 close_request(&req); 4660 } 4661 } 4662 4663 static void test_cache_control_verb(int port) 4664 { 4665 HINTERNET session, connect, request; 4666 BOOL ret; 4667 4668 session = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 4669 ok(session != NULL, "InternetOpen failed\n"); 4670 4671 connect = InternetConnectA(session, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 4672 ok(connect != NULL, "InternetConnect failed\n"); 4673 4674 request = HttpOpenRequestA(connect, "RPC_OUT_DATA", "/test_cache_control_verb", NULL, NULL, NULL, 4675 INTERNET_FLAG_NO_CACHE_WRITE, 0); 4676 ok(request != NULL, "HttpOpenRequest failed\n"); 4677 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 4678 ok(ret, "HttpSendRequest failed %u\n", GetLastError()); 4679 test_status_code(request, 200); 4680 InternetCloseHandle(request); 4681 4682 request = HttpOpenRequestA(connect, "POST", "/test_cache_control_verb", NULL, NULL, NULL, 4683 INTERNET_FLAG_NO_CACHE_WRITE, 0); 4684 ok(request != NULL, "HttpOpenRequest failed\n"); 4685 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 4686 ok(ret, "HttpSendRequest failed %u\n", GetLastError()); 4687 test_status_code(request, 200); 4688 InternetCloseHandle(request); 4689 4690 request = HttpOpenRequestA(connect, "HEAD", "/test_cache_control_verb", NULL, NULL, NULL, 4691 INTERNET_FLAG_NO_CACHE_WRITE, 0); 4692 ok(request != NULL, "HttpOpenRequest failed\n"); 4693 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 4694 ok(ret, "HttpSendRequest failed %u\n", GetLastError()); 4695 test_status_code(request, 200); 4696 InternetCloseHandle(request); 4697 4698 request = HttpOpenRequestA(connect, "GET", "/test_cache_control_verb", NULL, NULL, NULL, 4699 INTERNET_FLAG_NO_CACHE_WRITE, 0); 4700 ok(request != NULL, "HttpOpenRequest failed\n"); 4701 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 4702 ok(ret, "HttpSendRequest failed %u\n", GetLastError()); 4703 test_status_code(request, 200); 4704 InternetCloseHandle(request); 4705 4706 InternetCloseHandle(connect); 4707 InternetCloseHandle(session); 4708 } 4709 4710 static void test_request_content_length(int port) 4711 { 4712 char data[] = {'t','e','s','t'}; 4713 test_request_t req; 4714 BOOL ret; 4715 4716 reset_events(); 4717 open_simple_request(&req, "localhost", port, "POST", "/test_request_content_length"); 4718 4719 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 4720 ok(ret, "HttpSendRequest failed %u\n", GetLastError()); 4721 test_status_code(req.request, 200); 4722 4723 SetEvent(complete_event); 4724 4725 ret = HttpSendRequestA(req.request, NULL, 0, data, sizeof(data)); 4726 ok(ret, "HttpSendRequest failed %u\n", GetLastError()); 4727 test_status_code(req.request, 200); 4728 4729 SetEvent(complete_event); 4730 close_request(&req); 4731 } 4732 4733 static void test_accept_encoding(int port) 4734 { 4735 HINTERNET ses, con, req; 4736 char buf[1000]; 4737 BOOL ret; 4738 4739 ses = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 4740 ok(ses != NULL, "InternetOpen failed\n"); 4741 4742 con = InternetConnectA(ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 4743 ok(con != NULL, "InternetConnect failed\n"); 4744 4745 req = HttpOpenRequestA(con, "GET", "/echo_request", "HTTP/1.0", NULL, NULL, 0, 0); 4746 ok(req != NULL, "HttpOpenRequest failed\n"); 4747 4748 ret = HttpAddRequestHeadersA(req, "Accept-Encoding: gzip\r\n", ~0u, HTTP_ADDREQ_FLAG_REPLACE | HTTP_ADDREQ_FLAG_ADD); 4749 ok(ret, "HttpAddRequestHeaders failed\n"); 4750 4751 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 4752 ok(ret, "HttpSendRequestA failed\n"); 4753 4754 test_status_code(req, 200); 4755 receive_simple_request(req, buf, sizeof(buf)); 4756 ok(strstr(buf, "Accept-Encoding: gzip") != NULL, "Accept-Encoding header not found in %s\n", buf); 4757 4758 InternetCloseHandle(req); 4759 4760 req = HttpOpenRequestA(con, "GET", "/echo_request", "HTTP/1.0", NULL, NULL, 0, 0); 4761 ok(req != NULL, "HttpOpenRequest failed\n"); 4762 4763 ret = HttpSendRequestA(req, "Accept-Encoding: gzip", ~0u, NULL, 0); 4764 ok(ret, "HttpSendRequestA failed\n"); 4765 4766 test_status_code(req, 200); 4767 receive_simple_request(req, buf, sizeof(buf)); 4768 ok(strstr(buf, "Accept-Encoding: gzip") != NULL, "Accept-Encoding header not found in %s\n", buf); 4769 4770 InternetCloseHandle(req); 4771 InternetCloseHandle(con); 4772 InternetCloseHandle(ses); 4773 } 4774 4775 static void test_basic_auth_credentials_reuse(int port) 4776 { 4777 HINTERNET ses, con, req; 4778 DWORD status, size; 4779 BOOL ret; 4780 char buffer[0x40]; 4781 4782 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 4783 ok( ses != NULL, "InternetOpenA failed\n" ); 4784 4785 con = InternetConnectA( ses, "localhost", port, "user", "pwd", 4786 INTERNET_SERVICE_HTTP, 0, 0 ); 4787 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 4788 4789 req = HttpOpenRequestA( con, "HEAD", "/upload.txt", NULL, NULL, NULL, 0, 0 ); 4790 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 4791 4792 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 4793 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 4794 4795 size = sizeof(buffer); 4796 SetLastError(0xdeadbeef); 4797 ret = InternetQueryOptionA(req, INTERNET_OPTION_USERNAME, buffer, &size); 4798 ok(ret, "unexpected failure %u\n", GetLastError()); 4799 ok(!strcmp(buffer, "user"), "got %s\n", buffer); 4800 ok(size == 4, "got %u\n", size); 4801 4802 size = sizeof(buffer); 4803 SetLastError(0xdeadbeef); 4804 ret = InternetQueryOptionA(req, INTERNET_OPTION_PASSWORD, buffer, &size); 4805 ok(ret, "unexpected failure %u\n", GetLastError()); 4806 ok(!strcmp(buffer, "pwd"), "got %s\n", buffer); 4807 ok(size == 3, "got %u\n", size); 4808 4809 status = 0xdeadbeef; 4810 size = sizeof(status); 4811 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 4812 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 4813 ok( status == 200, "got %u\n", status ); 4814 4815 InternetCloseHandle( req ); 4816 InternetCloseHandle( con ); 4817 InternetCloseHandle( ses ); 4818 4819 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 4820 ok( ses != NULL, "InternetOpenA failed\n" ); 4821 4822 con = InternetConnectA( ses, "localhost", port, NULL, NULL, 4823 INTERNET_SERVICE_HTTP, 0, 0 ); 4824 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 4825 4826 req = HttpOpenRequestA( con, "PUT", "/upload2.txt", NULL, NULL, NULL, 0, 0 ); 4827 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 4828 4829 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 4830 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 4831 4832 size = sizeof(buffer); 4833 SetLastError(0xdeadbeef); 4834 ret = InternetQueryOptionA(req, INTERNET_OPTION_USERNAME, buffer, &size); 4835 ok(ret, "unexpected failure %u\n", GetLastError()); 4836 ok(!strcmp(buffer, "user"), "got %s\n", buffer); 4837 ok(size == 4, "got %u\n", size); 4838 4839 size = sizeof(buffer); 4840 SetLastError(0xdeadbeef); 4841 ret = InternetQueryOptionA(req, INTERNET_OPTION_PASSWORD, buffer, &size); 4842 ok(ret, "unexpected failure %u\n", GetLastError()); 4843 ok(!strcmp(buffer, "pwd"), "got %s\n", buffer); 4844 ok(size == 3, "got %u\n", size); 4845 4846 status = 0xdeadbeef; 4847 size = sizeof(status); 4848 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 4849 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 4850 ok( status == 200, "got %u\n", status ); 4851 4852 InternetCloseHandle( req ); 4853 InternetCloseHandle( con ); 4854 InternetCloseHandle( ses ); 4855 } 4856 4857 static void test_basic_auth_credentials_end_session(int port) 4858 { 4859 HINTERNET ses, con, req; 4860 DWORD status, size; 4861 BOOL ret; 4862 char buffer[0x40]; 4863 4864 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 4865 ok( ses != NULL, "InternetOpenA failed\n" ); 4866 4867 con = InternetConnectA( ses, "localhost", port, "user", "pwd", 4868 INTERNET_SERVICE_HTTP, 0, 0 ); 4869 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 4870 4871 req = HttpOpenRequestA( con, "HEAD", "/upload.txt", NULL, NULL, NULL, 0, 0 ); 4872 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 4873 4874 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 4875 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 4876 4877 size = sizeof(buffer); 4878 SetLastError(0xdeadbeef); 4879 ret = InternetQueryOptionA(req, INTERNET_OPTION_USERNAME, buffer, &size); 4880 ok(ret, "unexpected failure %u\n", GetLastError()); 4881 ok(!strcmp(buffer, "user"), "got %s\n", buffer); 4882 ok(size == 4, "got %u\n", size); 4883 4884 size = sizeof(buffer); 4885 SetLastError(0xdeadbeef); 4886 ret = InternetQueryOptionA(req, INTERNET_OPTION_PASSWORD, buffer, &size); 4887 ok(ret, "unexpected failure %u\n", GetLastError()); 4888 ok(!strcmp(buffer, "pwd"), "got %s\n", buffer); 4889 ok(size == 3, "got %u\n", size); 4890 4891 status = 0xdeadbeef; 4892 size = sizeof(status); 4893 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 4894 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 4895 ok( status == HTTP_STATUS_OK, "got %u\n", status ); 4896 4897 InternetCloseHandle( req ); 4898 InternetCloseHandle( con ); 4899 InternetCloseHandle( ses ); 4900 4901 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 4902 ok( ses != NULL, "InternetOpenA failed\n" ); 4903 4904 /* Clear the cached credentials */ 4905 ret = InternetSetOptionA(ses, INTERNET_OPTION_END_BROWSER_SESSION, NULL, 0); 4906 ok(ret, "unexpected failure %u\n", GetLastError()); 4907 4908 con = InternetConnectA( ses, "localhost", port, NULL, NULL, 4909 INTERNET_SERVICE_HTTP, 0, 0 ); 4910 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 4911 4912 req = HttpOpenRequestA( con, "PUT", "/upload2.txt", NULL, NULL, NULL, 0, 0 ); 4913 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 4914 4915 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 4916 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 4917 4918 size = sizeof(buffer); 4919 SetLastError(0xdeadbeef); 4920 ret = InternetQueryOptionA(req, INTERNET_OPTION_USERNAME, buffer, &size); 4921 ok(ret, "unexpected failure %u\n", GetLastError()); 4922 ok(!strcmp(buffer, ""), "got %s\n", buffer); 4923 ok(size == 0, "got %u\n", size); 4924 4925 size = sizeof(buffer); 4926 SetLastError(0xdeadbeef); 4927 ret = InternetQueryOptionA(req, INTERNET_OPTION_PASSWORD, buffer, &size); 4928 ok(ret, "unexpected failure %u\n", GetLastError()); 4929 ok(!strcmp(buffer, ""), "got %s\n", buffer); 4930 ok(size == 0, "got %u\n", size); 4931 4932 status = 0xdeadbeef; 4933 size = sizeof(status); 4934 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 4935 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 4936 ok( status == HTTP_STATUS_BAD_REQUEST, "got %u\n", status ); 4937 4938 InternetCloseHandle( req ); 4939 InternetCloseHandle( con ); 4940 InternetCloseHandle( ses ); 4941 } 4942 4943 static void test_basic_auth_credentials_different(int port) 4944 { 4945 HINTERNET ses, con, req; 4946 DWORD status, size; 4947 BOOL ret; 4948 char buffer[0x40]; 4949 4950 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 4951 ok( ses != NULL, "InternetOpenA failed\n" ); 4952 4953 con = InternetConnectA( ses, "localhost", port, "user", "pwd", 4954 INTERNET_SERVICE_HTTP, 0, 0 ); 4955 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 4956 4957 req = HttpOpenRequestA( con, "HEAD", "/upload.txt", NULL, NULL, NULL, 0, 0 ); 4958 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 4959 4960 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 4961 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 4962 4963 size = sizeof(buffer); 4964 SetLastError(0xdeadbeef); 4965 ret = InternetQueryOptionA(req, INTERNET_OPTION_USERNAME, buffer, &size); 4966 ok(ret, "unexpected failure %u\n", GetLastError()); 4967 ok(!strcmp(buffer, "user"), "got %s\n", buffer); 4968 ok(size == 4, "got %u\n", size); 4969 4970 size = sizeof(buffer); 4971 SetLastError(0xdeadbeef); 4972 ret = InternetQueryOptionA(req, INTERNET_OPTION_PASSWORD, buffer, &size); 4973 ok(ret, "unexpected failure %u\n", GetLastError()); 4974 ok(!strcmp(buffer, "pwd"), "got %s\n", buffer); 4975 ok(size == 3, "got %u\n", size); 4976 4977 status = 0xdeadbeef; 4978 size = sizeof(status); 4979 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 4980 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 4981 ok( status == 200, "got %u\n", status ); 4982 4983 InternetCloseHandle( req ); 4984 InternetCloseHandle( con ); 4985 InternetCloseHandle( ses ); 4986 4987 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 4988 ok( ses != NULL, "InternetOpenA failed\n" ); 4989 4990 con = InternetConnectA( ses, "localhost", port, "user1", "pwd1", 4991 INTERNET_SERVICE_HTTP, 0, 0 ); 4992 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 4993 4994 req = HttpOpenRequestA( con, "HEAD", "/upload3.txt", NULL, NULL, NULL, 0, 0 ); 4995 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 4996 4997 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 4998 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 4999 5000 size = sizeof(buffer); 5001 SetLastError(0xdeadbeef); 5002 ret = InternetQueryOptionA(req, INTERNET_OPTION_USERNAME, buffer, &size); 5003 ok(ret, "unexpected failure %u\n", GetLastError()); 5004 ok(!strcmp(buffer, "user1"), "got %s\n", buffer); 5005 ok(size == 5, "got %u\n", size); 5006 5007 size = sizeof(buffer); 5008 SetLastError(0xdeadbeef); 5009 ret = InternetQueryOptionA(req, INTERNET_OPTION_PASSWORD, buffer, &size); 5010 ok(ret, "unexpected failure %u\n", GetLastError()); 5011 ok(!strcmp(buffer, "pwd1"), "got %s\n", buffer); 5012 ok(size == 4, "got %u\n", size); 5013 5014 status = 0xdeadbeef; 5015 size = sizeof(status); 5016 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 5017 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 5018 ok( status == 200, "got %u\n", status ); 5019 5020 InternetCloseHandle( req ); 5021 InternetCloseHandle( con ); 5022 InternetCloseHandle( ses ); 5023 } 5024 5025 /* 5026 * Manually set the Authorization for both calls. 5027 */ 5028 static void test_basic_auth_credentials_manual(int port) 5029 { 5030 HINTERNET ses, con, req; 5031 DWORD status, size; 5032 BOOL ret; 5033 5034 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 5035 ok( ses != NULL, "InternetOpenA failed\n" ); 5036 5037 /* Clear the cached credentials */ 5038 ret = InternetSetOptionA(ses, INTERNET_OPTION_END_BROWSER_SESSION, NULL, 0); 5039 ok(ret, "unexpected failure %u\n", GetLastError()); 5040 5041 con = InternetConnectA( ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0 ); 5042 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 5043 5044 req = HttpOpenRequestA( con, "HEAD", "/upload.txt", NULL, NULL, NULL, 0, 0 ); 5045 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 5046 5047 /* Set Authorization Header */ 5048 ret = HttpAddRequestHeadersA(req, "Authorization: Basic dXNlcjpwd2Q=\r\n", ~0u, 5049 HTTP_ADDREQ_FLAG_REPLACE | HTTP_ADDREQ_FLAG_ADD); 5050 ok(ret, "HttpAddRequestHeaders Failed\n"); 5051 5052 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 5053 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 5054 5055 status = 0xdeadbeef; 5056 size = sizeof(status); 5057 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 5058 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 5059 ok( status == 200, "got %u\n", status ); 5060 5061 InternetCloseHandle( req ); 5062 InternetCloseHandle( con ); 5063 InternetCloseHandle( ses ); 5064 5065 /* Show manual headers are cached. */ 5066 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 5067 ok( ses != NULL, "InternetOpenA failed\n" ); 5068 5069 con = InternetConnectA( ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0 ); 5070 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 5071 5072 req = HttpOpenRequestA( con, "HEAD", "/upload.txt", NULL, NULL, NULL, 0, 0 ); 5073 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 5074 5075 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 5076 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 5077 5078 status = 0xdeadbeef; 5079 size = sizeof(status); 5080 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 5081 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 5082 ok( status == 401, "got %u\n", status ); 5083 5084 InternetCloseHandle( req ); 5085 InternetCloseHandle( con ); 5086 InternetCloseHandle( ses ); 5087 5088 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 5089 ok( ses != NULL, "InternetOpenA failed\n" ); 5090 5091 con = InternetConnectA( ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0 ); 5092 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 5093 5094 req = HttpOpenRequestA( con, "HEAD", "/upload4.txt", NULL, NULL, NULL, 0, 0 ); 5095 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 5096 5097 /* Set Authorization Header */ 5098 ret = HttpAddRequestHeadersA(req, "Authorization: Bearer dXNlcjE6cHdkMQ==\r\n", ~0u, 5099 HTTP_ADDREQ_FLAG_REPLACE | HTTP_ADDREQ_FLAG_ADD); 5100 ok(ret, "HttpAddRequestHeaders Failed\n"); 5101 5102 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 5103 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 5104 5105 status = 0xdeadbeef; 5106 size = sizeof(status); 5107 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 5108 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 5109 ok( status == 200, "got %u\n", status ); 5110 5111 InternetCloseHandle( req ); 5112 InternetCloseHandle( con ); 5113 InternetCloseHandle( ses ); 5114 } 5115 5116 /* 5117 * Manually set the Authorization for the bearer call, which shows the cached is used. 5118 */ 5119 static void test_basic_auth_credentials_cached_manual(int port) 5120 { 5121 HINTERNET ses, con, req; 5122 DWORD status, size; 5123 BOOL ret; 5124 5125 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 5126 ok( ses != NULL, "InternetOpenA failed\n" ); 5127 5128 /* Clear the cached credentials */ 5129 ret = InternetSetOptionA(ses, INTERNET_OPTION_END_BROWSER_SESSION, NULL, 0); 5130 ok(ret, "unexpected failure %u\n", GetLastError()); 5131 5132 con = InternetConnectA( ses, "localhost", port, "user", "pwd", 5133 INTERNET_SERVICE_HTTP, 0, 0 ); 5134 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 5135 5136 req = HttpOpenRequestA( con, "HEAD", "/upload.txt", NULL, NULL, NULL, 0, 0 ); 5137 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 5138 5139 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 5140 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 5141 5142 status = 0xdeadbeef; 5143 size = sizeof(status); 5144 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 5145 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 5146 ok( status == 200, "got %u\n", status ); 5147 5148 InternetCloseHandle( req ); 5149 InternetCloseHandle( con ); 5150 InternetCloseHandle( ses ); 5151 5152 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0 ); 5153 ok( ses != NULL, "InternetOpenA failed\n" ); 5154 5155 con = InternetConnectA( ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0 ); 5156 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 5157 5158 req = HttpOpenRequestA( con, "HEAD", "/upload4.txt", NULL, NULL, NULL, 0, 0 ); 5159 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 5160 5161 /* Setting an Authorization Header doesn't override the cached one. */ 5162 ret = HttpAddRequestHeadersA(req, "Authorization: Bearer dXNlcjE6cHdkMQ==\r\n", ~0u, 5163 HTTP_ADDREQ_FLAG_REPLACE | HTTP_ADDREQ_FLAG_ADD); 5164 ok(ret, "HttpAddRequestHeaders Failed\n"); 5165 5166 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 5167 ok( ret, "HttpSendRequestA failed %u\n", GetLastError() ); 5168 5169 status = 0xdeadbeef; 5170 size = sizeof(status); 5171 ret = HttpQueryInfoA( req, HTTP_QUERY_STATUS_CODE|HTTP_QUERY_FLAG_NUMBER, &status, &size, NULL ); 5172 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 5173 ok( status == 201, "got %u\n", status ); 5174 5175 InternetCloseHandle( req ); 5176 InternetCloseHandle( con ); 5177 InternetCloseHandle( ses ); 5178 } 5179 5180 static void test_async_read(int port) 5181 { 5182 HINTERNET ses, con, req; 5183 INTERNET_BUFFERSA ib; 5184 char buffer[0x100]; 5185 DWORD pending_reads; 5186 DWORD res, count, bytes; 5187 BOOL ret; 5188 5189 reset_events(); 5190 5191 /* test asynchronous InternetReadFileEx */ 5192 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, INTERNET_FLAG_ASYNC ); 5193 ok( ses != NULL, "InternetOpenA failed\n" ); 5194 pInternetSetStatusCallbackA( ses, &callback ); 5195 5196 SET_EXPECT( INTERNET_STATUS_HANDLE_CREATED ); 5197 con = InternetConnectA( ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0xdeadbeef ); 5198 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 5199 CHECK_NOTIFIED( INTERNET_STATUS_HANDLE_CREATED ); 5200 5201 SET_EXPECT( INTERNET_STATUS_HANDLE_CREATED ); 5202 req = HttpOpenRequestA( con, "GET", "/async_read", NULL, NULL, NULL, INTERNET_FLAG_RELOAD, 0xdeadbeef ); 5203 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 5204 CHECK_NOTIFIED( INTERNET_STATUS_HANDLE_CREATED ); 5205 5206 SET_OPTIONAL( INTERNET_STATUS_COOKIE_SENT ); 5207 SET_OPTIONAL( INTERNET_STATUS_DETECTING_PROXY ); 5208 SET_EXPECT( INTERNET_STATUS_CONNECTING_TO_SERVER ); 5209 SET_EXPECT( INTERNET_STATUS_CONNECTED_TO_SERVER ); 5210 SET_EXPECT( INTERNET_STATUS_SENDING_REQUEST ); 5211 SET_EXPECT( INTERNET_STATUS_REQUEST_SENT ); 5212 SET_EXPECT( INTERNET_STATUS_RECEIVING_RESPONSE ); 5213 SET_EXPECT( INTERNET_STATUS_RESPONSE_RECEIVED ); 5214 SET_OPTIONAL( INTERNET_STATUS_CLOSING_CONNECTION ); 5215 SET_OPTIONAL( INTERNET_STATUS_CONNECTION_CLOSED ); 5216 SET_EXPECT( INTERNET_STATUS_REQUEST_COMPLETE ); 5217 5218 SetLastError( 0xdeadbeef ); 5219 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 5220 ok( !ret, "HttpSendRequestA unexpectedly succeeded\n" ); 5221 ok( GetLastError() == ERROR_IO_PENDING, "expected ERROR_IO_PENDING, got %u\n", GetLastError() ); 5222 WaitForSingleObject( complete_event, INFINITE ); 5223 ok( req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error ); 5224 5225 CLEAR_NOTIFIED( INTERNET_STATUS_COOKIE_SENT ); 5226 CLEAR_NOTIFIED( INTERNET_STATUS_DETECTING_PROXY ); 5227 CHECK_NOTIFIED( INTERNET_STATUS_CONNECTING_TO_SERVER ); 5228 CHECK_NOTIFIED( INTERNET_STATUS_CONNECTED_TO_SERVER ); 5229 CHECK_NOTIFIED( INTERNET_STATUS_SENDING_REQUEST ); 5230 CHECK_NOTIFIED( INTERNET_STATUS_REQUEST_SENT ); 5231 CHECK_NOTIFIED( INTERNET_STATUS_RECEIVING_RESPONSE ); 5232 CHECK_NOTIFIED( INTERNET_STATUS_RESPONSE_RECEIVED ); 5233 CLEAR_NOTIFIED( INTERNET_STATUS_CLOSING_CONNECTION ); 5234 CLEAR_NOTIFIED( INTERNET_STATUS_CONNECTION_CLOSED ); 5235 CHECK_NOTIFIED( INTERNET_STATUS_REQUEST_COMPLETE ); 5236 5237 pending_reads = 0; 5238 memset( &ib, 0, sizeof(ib) ); 5239 memset( buffer, 0, sizeof(buffer) ); 5240 ib.dwStructSize = sizeof(ib); 5241 for (count = 0; count < sizeof(buffer); count += ib.dwBufferLength) 5242 { 5243 ib.lpvBuffer = buffer + count; 5244 ib.dwBufferLength = min(16, sizeof(buffer) - count); 5245 5246 SET_EXPECT( INTERNET_STATUS_RECEIVING_RESPONSE ); 5247 SET_EXPECT( INTERNET_STATUS_RESPONSE_RECEIVED ); 5248 5249 ret = InternetReadFileExA( req, &ib, 0, 0xdeadbeef ); 5250 if (!count) /* the first part should arrive immediately */ 5251 ok( ret, "InternetReadFileExA failed %u\n", GetLastError() ); 5252 ros_skip_flaky 5253 if (!ret) 5254 { 5255 ok( GetLastError() == ERROR_IO_PENDING, "expected ERROR_IO_PENDING, got %u\n", GetLastError() ); 5256 ros_skip_flaky 5257 CHECK_NOTIFIED( INTERNET_STATUS_RECEIVING_RESPONSE ); 5258 SET_EXPECT( INTERNET_STATUS_REQUEST_COMPLETE ); 5259 if (!pending_reads++) 5260 { 5261 res = WaitForSingleObject( complete_event, 0 ); 5262 ok( res == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %u\n", res ); 5263 SetEvent( conn_wait_event ); 5264 } 5265 res = WaitForSingleObject( complete_event, INFINITE ); 5266 ok( res == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", res ); 5267 ok( req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error ); 5268 todo_wine_if( pending_reads > 1 ) 5269 ok( ib.dwBufferLength != 0, "expected ib.dwBufferLength != 0\n" ); 5270 CHECK_NOTIFIED( INTERNET_STATUS_RESPONSE_RECEIVED ); 5271 CHECK_NOTIFIED( INTERNET_STATUS_REQUEST_COMPLETE ); 5272 } 5273 5274 CLEAR_NOTIFIED( INTERNET_STATUS_RECEIVING_RESPONSE ); 5275 CLEAR_NOTIFIED( INTERNET_STATUS_RESPONSE_RECEIVED ); 5276 if (!ib.dwBufferLength) break; 5277 } 5278 5279 ok( pending_reads == 1, "expected 1 pending read, got %u\n", pending_reads ); 5280 ok( !strcmp(buffer, page1), "unexpected buffer content\n" ); 5281 close_async_handle( ses, 2 ); 5282 ResetEvent( conn_wait_event ); 5283 5284 /* test asynchronous InternetReadFile */ 5285 ses = InternetOpenA( "winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, INTERNET_FLAG_ASYNC ); 5286 ok( ses != NULL, "InternetOpenA failed\n" ); 5287 pInternetSetStatusCallbackA( ses, &callback ); 5288 5289 SET_EXPECT( INTERNET_STATUS_HANDLE_CREATED ); 5290 con = InternetConnectA( ses, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0xdeadbeef ); 5291 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 5292 CHECK_NOTIFIED( INTERNET_STATUS_HANDLE_CREATED ); 5293 5294 SET_EXPECT( INTERNET_STATUS_HANDLE_CREATED ); 5295 req = HttpOpenRequestA( con, "GET", "/async_read", NULL, NULL, NULL, INTERNET_FLAG_RELOAD, 0xdeadbeef ); 5296 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 5297 CHECK_NOTIFIED( INTERNET_STATUS_HANDLE_CREATED ); 5298 5299 SET_OPTIONAL( INTERNET_STATUS_COOKIE_SENT ); 5300 SET_OPTIONAL( INTERNET_STATUS_DETECTING_PROXY ); 5301 SET_EXPECT( INTERNET_STATUS_CONNECTING_TO_SERVER ); 5302 SET_EXPECT( INTERNET_STATUS_CONNECTED_TO_SERVER ); 5303 SET_EXPECT( INTERNET_STATUS_SENDING_REQUEST ); 5304 SET_EXPECT( INTERNET_STATUS_REQUEST_SENT ); 5305 SET_EXPECT( INTERNET_STATUS_RECEIVING_RESPONSE ); 5306 SET_EXPECT( INTERNET_STATUS_RESPONSE_RECEIVED ); 5307 SET_OPTIONAL( INTERNET_STATUS_CLOSING_CONNECTION ); 5308 SET_OPTIONAL( INTERNET_STATUS_CONNECTION_CLOSED ); 5309 SET_EXPECT( INTERNET_STATUS_REQUEST_COMPLETE ); 5310 5311 SetLastError( 0xdeadbeef ); 5312 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 5313 ok( !ret, "HttpSendRequestA unexpectedly succeeded\n" ); 5314 ok( GetLastError() == ERROR_IO_PENDING, "expected ERROR_IO_PENDING, got %u\n", GetLastError() ); 5315 WaitForSingleObject( complete_event, INFINITE ); 5316 ok( req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error ); 5317 5318 CLEAR_NOTIFIED( INTERNET_STATUS_COOKIE_SENT ); 5319 CLEAR_NOTIFIED( INTERNET_STATUS_DETECTING_PROXY ); 5320 CHECK_NOTIFIED( INTERNET_STATUS_CONNECTING_TO_SERVER ); 5321 CHECK_NOTIFIED( INTERNET_STATUS_CONNECTED_TO_SERVER ); 5322 CHECK_NOTIFIED( INTERNET_STATUS_SENDING_REQUEST ); 5323 CHECK_NOTIFIED( INTERNET_STATUS_REQUEST_SENT ); 5324 CHECK_NOTIFIED( INTERNET_STATUS_RECEIVING_RESPONSE ); 5325 CHECK_NOTIFIED( INTERNET_STATUS_RESPONSE_RECEIVED ); 5326 CLEAR_NOTIFIED( INTERNET_STATUS_CLOSING_CONNECTION ); 5327 CLEAR_NOTIFIED( INTERNET_STATUS_CONNECTION_CLOSED ); 5328 CHECK_NOTIFIED( INTERNET_STATUS_REQUEST_COMPLETE ); 5329 5330 pending_reads = 0; 5331 memset( buffer, 0, sizeof(buffer) ); 5332 for (count = 0; count < sizeof(buffer); count += bytes) 5333 { 5334 SET_EXPECT( INTERNET_STATUS_RECEIVING_RESPONSE ); 5335 SET_EXPECT( INTERNET_STATUS_RESPONSE_RECEIVED ); 5336 5337 bytes = 0xdeadbeef; 5338 ret = InternetReadFile( req, buffer + count, min(16, sizeof(buffer) - count), &bytes ); 5339 if (!count) /* the first part should arrive immediately */ 5340 ok( ret, "InternetReadFile failed %u\n", GetLastError() ); 5341 if (!ret) 5342 { 5343 ok( GetLastError() == ERROR_IO_PENDING, "expected ERROR_IO_PENDING, got %u\n", GetLastError() ); 5344 ok( bytes == 0, "expected 0, got %u\n", bytes ); 5345 ros_skip_flaky 5346 CHECK_NOTIFIED( INTERNET_STATUS_RECEIVING_RESPONSE ); 5347 SET_EXPECT( INTERNET_STATUS_REQUEST_COMPLETE ); 5348 if (!pending_reads++) 5349 { 5350 res = WaitForSingleObject( complete_event, 0 ); 5351 ok( res == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %u\n", res ); 5352 SetEvent( conn_wait_event ); 5353 } 5354 res = WaitForSingleObject( complete_event, INFINITE ); 5355 ok( res == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", res ); 5356 ok( req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error ); 5357 ros_skip_flaky { 5358 todo_wine_if( pending_reads > 1 ) 5359 ok( bytes != 0, "expected bytes != 0\n" ); 5360 } 5361 ros_skip_flaky 5362 CHECK_NOTIFIED( INTERNET_STATUS_RESPONSE_RECEIVED ); 5363 ros_skip_flaky 5364 CHECK_NOTIFIED( INTERNET_STATUS_REQUEST_COMPLETE ); 5365 } 5366 5367 CLEAR_NOTIFIED( INTERNET_STATUS_RECEIVING_RESPONSE ); 5368 CLEAR_NOTIFIED( INTERNET_STATUS_RESPONSE_RECEIVED ); 5369 if (!bytes) break; 5370 } 5371 5372 ros_skip_flaky 5373 ok( pending_reads == 1, "expected 1 pending read, got %u\n", pending_reads ); 5374 ok( !strcmp(buffer, page1), "unexpected buffer content\n" ); 5375 close_async_handle( ses, 2 ); 5376 } 5377 5378 static void server_send_string(const char *msg) 5379 { 5380 send(server_socket, msg, strlen(msg), 0); 5381 } 5382 5383 static size_t server_read_data(char *buf, size_t buf_size) 5384 { 5385 return recv(server_socket, buf, buf_size, 0); 5386 } 5387 5388 #define server_read_request(a) _server_read_request(__LINE__,a) 5389 static void _server_read_request(unsigned line, const char *expected_request) 5390 { 5391 char buf[4000], *p; 5392 size_t size; 5393 5394 size = server_read_data(buf, sizeof(buf) - 1); 5395 buf[size] = 0; 5396 p = strstr(buf, "\r\n"); 5397 if(p) *p = 0; 5398 ok_(__FILE__,line)(p && !strcmp(buf, expected_request), "unexpected request %s\n", buf); 5399 } 5400 5401 static BOOL skip_receive_notification_tests; 5402 static DWORD received_response_size; 5403 5404 static void WINAPI readex_callback(HINTERNET handle, DWORD_PTR context, DWORD status, void *info, DWORD info_size) 5405 { 5406 switch(status) { 5407 case INTERNET_STATUS_RECEIVING_RESPONSE: 5408 if(!skip_receive_notification_tests) 5409 callback(handle, context, status, info, info_size); 5410 break; 5411 case INTERNET_STATUS_RESPONSE_RECEIVED: 5412 if(!skip_receive_notification_tests) 5413 callback(handle, context, status, info, info_size); 5414 received_response_size = *(DWORD*)info; 5415 break; 5416 case INTERNET_STATUS_REQUEST_SENT: 5417 callback(handle, context, status, info, info_size); 5418 SetEvent(request_sent_event); 5419 break; 5420 default: 5421 callback(handle, context, status, info, info_size); 5422 } 5423 } 5424 5425 static void send_socket_request(test_request_t *req, BOOL new_connection) 5426 { 5427 BOOL ret; 5428 5429 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 5430 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 5431 if(new_connection) { 5432 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 5433 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 5434 } 5435 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 5436 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 5437 if(!skip_receive_notification_tests) 5438 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 5439 5440 SetLastError(0xdeadbeef); 5441 ret = HttpSendRequestA(req->request, NULL, 0, NULL, 0); 5442 ok(!ret, "HttpSendRequestA unexpectedly succeeded\n"); 5443 ok(GetLastError() == ERROR_IO_PENDING, "expected ERROR_IO_PENDING, got %u\n", GetLastError()); 5444 5445 if(new_connection) 5446 WaitForSingleObject(server_req_rec_event, INFINITE); 5447 WaitForSingleObject(request_sent_event, INFINITE); 5448 5449 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 5450 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 5451 if(new_connection) { 5452 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 5453 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 5454 } 5455 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 5456 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 5457 } 5458 5459 static void open_socket_request(int port, test_request_t *req, const char *verb) 5460 { 5461 /* We're connecting to new socket */ 5462 if(!verb) 5463 reset_events(); 5464 5465 req->session = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, INTERNET_FLAG_ASYNC); 5466 ok(req->session != NULL, "InternetOpenA failed\n"); 5467 pInternetSetStatusCallbackA(req->session, readex_callback); 5468 5469 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 5470 req->connection = InternetConnectA(req->session, "localhost", port, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0xdeadbeef); 5471 ok(req->connection != NULL, "InternetConnectA failed %u\n", GetLastError()); 5472 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED ); 5473 5474 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 5475 req->request = HttpOpenRequestA(req->connection, "GET", verb ? verb : "/socket", 5476 NULL, NULL, NULL, INTERNET_FLAG_RELOAD, 0xdeadbeef); 5477 ok(req->request != NULL, "HttpOpenRequestA failed %u\n", GetLastError()); 5478 CHECK_NOTIFIED( INTERNET_STATUS_HANDLE_CREATED ); 5479 5480 send_socket_request(req, !verb); 5481 } 5482 5483 static void open_read_test_request(int port, test_request_t *req, const char *response) 5484 { 5485 if(!skip_receive_notification_tests) 5486 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 5487 5488 open_socket_request(port, req, NULL); 5489 5490 if(!skip_receive_notification_tests) { 5491 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 5492 received_response_size = 0xdeadbeef; 5493 } 5494 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 5495 5496 server_send_string(response); 5497 WaitForSingleObject(complete_event, INFINITE); 5498 5499 if(!skip_receive_notification_tests) { 5500 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 5501 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 5502 todo_wine 5503 ok(received_response_size == strlen(response), "received_response_size = %u\n", received_response_size); 5504 } 5505 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 5506 ok(req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error); 5507 } 5508 5509 #define readex_expect_sync_data_len(a,b,c,d,e,f,g) _readex_expect_sync_data_len(__LINE__,a,b,c,d,e,f,g) 5510 static void _readex_expect_sync_data_len(unsigned line, HINTERNET req, DWORD flags, INTERNET_BUFFERSW *buf, 5511 DWORD buf_size, const char *exdata, DWORD len, DWORD expect_receive) 5512 { 5513 BOOL ret; 5514 5515 if(!skip_receive_notification_tests && expect_receive) { 5516 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 5517 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 5518 received_response_size = 0xdeadbeef; 5519 } 5520 5521 memset(buf->lpvBuffer, 0xff, buf_size); 5522 buf->dwBufferLength = buf_size; 5523 ret = InternetReadFileExW(req, buf, flags, 0xdeadbeef); 5524 ok_(__FILE__,line)(ret, "InternetReadFileExW failed: %u\n", GetLastError()); 5525 ok_(__FILE__,line)(buf->dwBufferLength == len, "dwBufferLength = %u, expected %u\n", buf->dwBufferLength, len); 5526 if(len && exdata) 5527 ok_(__FILE__,line)(!memcmp(buf->lpvBuffer, exdata, len), "Unexpected data\n"); 5528 5529 if(!skip_receive_notification_tests && expect_receive) { 5530 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 5531 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 5532 ok_(__FILE__,line)(received_response_size == len, "received_response_size = %u\n", received_response_size); 5533 } 5534 } 5535 5536 #define readex_expect_sync_data(a,b,c,d,e,f) _readex_expect_sync_data(__LINE__,a,b,c,d,e,f) 5537 static void _readex_expect_sync_data(unsigned line, HINTERNET req, DWORD flags, INTERNET_BUFFERSW *buf, 5538 DWORD buf_size, const char *exdata, DWORD expect_receive) 5539 { 5540 _readex_expect_sync_data_len(line, req, flags, buf, buf_size, exdata, strlen(exdata), expect_receive); 5541 } 5542 5543 #define read_expect_sync_data_len(a,b,c,d,e) _read_expect_sync_data_len(__LINE__,a,b,c,d,e) 5544 static void _read_expect_sync_data_len(unsigned line, HINTERNET req, void *buf, DWORD buf_size, 5545 const char *exdata, DWORD len) 5546 { 5547 DWORD ret_size = 0xdeadbeef; 5548 BOOL ret; 5549 5550 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 5551 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 5552 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 5553 received_response_size = 0xdeadbeef; 5554 5555 memset(buf, 0xff, buf_size); 5556 ret = InternetReadFile(req, buf, buf_size, &ret_size); 5557 ok_(__FILE__,line)(ret, "InternetReadFileExW failed: %u\n", GetLastError()); 5558 ok_(__FILE__,line)(ret_size == len, "dwBufferLength = %u, expected %u\n", ret_size, len); 5559 if(len && exdata) 5560 ok_(__FILE__,line)(!memcmp(buf, exdata, len), "Unexpected data\n"); 5561 5562 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 5563 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 5564 CLEAR_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 5565 ok_(__FILE__,line)(received_response_size == len, "received_response_size = %u\n", received_response_size); 5566 ok_(__FILE__,line)(!req_error, "req_error = %u\n", req_error); 5567 } 5568 5569 #define read_expect_sync_data(a,b,c,d) _read_expect_sync_data(__LINE__,a,b,c,d) 5570 static void _read_expect_sync_data(unsigned line, HINTERNET req, void *buf, 5571 DWORD buf_size, const char *exdata) 5572 { 5573 _read_expect_sync_data_len(line, req, buf, buf_size, exdata, strlen(exdata)); 5574 } 5575 5576 static void close_connection(void) 5577 { 5578 char c; 5579 SetEvent(conn_wait_event); 5580 recv(server_socket, &c, 1, 0); 5581 } 5582 5583 #define send_response_and_wait(a,b,c,d,e,f,g,h) _send_response_and_wait(__LINE__,a,b,c,d,e,f,g,h) 5584 static void _send_response_and_wait(unsigned line, const char *response, BOOL do_close_connection, 5585 void *buf, DWORD *ret_size, const char *exdata, 5586 DWORD expected_size, DWORD expected_req_error, DWORD expected_receive_size) 5587 { 5588 if(!skip_receive_notification_tests) 5589 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 5590 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 5591 5592 if(response) 5593 server_send_string(response); 5594 5595 if(do_close_connection) 5596 close_connection(); 5597 5598 WaitForSingleObject(complete_event, INFINITE); 5599 5600 if(!skip_receive_notification_tests) 5601 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 5602 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 5603 if(!skip_receive_notification_tests && expected_receive_size != -1) 5604 todo_wine_if(received_response_size != expected_receive_size) /* FIXME! remove when wine is fixed */ 5605 ok_(__FILE__,line)(received_response_size == expected_receive_size, 5606 "received_response_size = %u\n", received_response_size); 5607 ok_(__FILE__,line)(req_error == expected_req_error, "req_error = %u, expected %u\n", req_error, expected_req_error); 5608 5609 /* If IRF_NO_WAIT is used, buffer is not changed. */ 5610 ok_(__FILE__,line)(*ret_size == expected_size, "dwBufferLength = %u\n", *ret_size); 5611 if(exdata) 5612 ok_(__FILE__,line)(!memcmp(buf, exdata, strlen(exdata)), "unexpected buffer data\n"); 5613 else if(buf) 5614 ok_(__FILE__,line)(!*(DWORD*)buf, "buffer data changed\n"); 5615 } 5616 5617 #define send_response_ex_and_wait(a,b,c,d,e,f) _send_response_ex_and_wait(__LINE__,a,b,c,d,e,f) 5618 static void _send_response_ex_and_wait(unsigned line, const char *response, BOOL close_connection, 5619 INTERNET_BUFFERSW *buf, const char *exdata, DWORD expected_req_error, 5620 DWORD expected_receive_size) 5621 { 5622 _send_response_and_wait(line, response, close_connection, buf->lpvBuffer, &buf->dwBufferLength, 5623 exdata, exdata ? strlen(exdata) : buf->dwBufferLength, expected_req_error, 5624 expected_receive_size); 5625 } 5626 5627 static void send_response_len_and_wait(unsigned len, BOOL close_connection, INTERNET_BUFFERSW *buf) 5628 { 5629 char *response; 5630 5631 response = HeapAlloc(GetProcessHeap(), 0, len+1); 5632 memset(response, 'x', len); 5633 response[len] = 0; 5634 send_response_ex_and_wait(response, close_connection, buf, NULL, 0, -1); 5635 HeapFree(GetProcessHeap(), 0, response); 5636 } 5637 5638 #define readex_expect_async(a,b,c,d,e) _readex_expect_async(__LINE__,a,b,c,d,e) 5639 static void _readex_expect_async(unsigned line, HINTERNET req, DWORD flags, INTERNET_BUFFERSW *buf, 5640 DWORD buf_size, const char *exdata) 5641 { 5642 unsigned len = 0; 5643 BOOL ret; 5644 5645 if(!skip_receive_notification_tests) 5646 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 5647 5648 memset(buf->lpvBuffer, 0, max(buf_size, sizeof(DWORD))); 5649 buf->dwBufferLength = buf_size; 5650 ret = InternetReadFileExW(req, buf, flags, 0xdeadbeef); 5651 ok_(__FILE__,line)(!ret && GetLastError() == ERROR_IO_PENDING, "InternetReadFileExW returned %x (%u)\n", ret, GetLastError()); 5652 ok_(__FILE__,line)(buf->dwBufferLength == buf_size, "dwBufferLength = %u, expected %u\n", buf->dwBufferLength, buf_size); 5653 if(exdata) { 5654 len = strlen(exdata); 5655 ok_(__FILE__,line)(!memcmp(buf->lpvBuffer, exdata, len), "unexpected buffer data\n"); 5656 }else { 5657 ok_(__FILE__,line)(!*(DWORD*)buf->lpvBuffer, "buffer data changed\n"); 5658 } 5659 5660 if(!skip_receive_notification_tests) 5661 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 5662 } 5663 5664 static void read_expect_async(HINTERNET req, void *buf, DWORD buf_size, DWORD *ret_size, const char *exdata) 5665 { 5666 unsigned len = 0; 5667 const char *p; 5668 BOOL ret; 5669 5670 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 5671 5672 *ret_size = 0xdeadbeef; 5673 memset(buf, 0, buf_size); 5674 ret = InternetReadFile(req, buf, buf_size, ret_size); 5675 ok(!ret && GetLastError() == ERROR_IO_PENDING, "InternetReadFileExW returned %x (%u)\n", ret, GetLastError()); 5676 ok(*ret_size == 0, "dwBufferLength = %u\n", *ret_size); 5677 if(exdata) { 5678 len = strlen(exdata); 5679 ok(!memcmp(buf, exdata, len), "unexpected buffer data\n"); 5680 } 5681 for(p = (const char*)buf + len; p < (const char*)buf + buf_size; p++) { 5682 if(*p) 5683 ok(0, "buffer data changed\n"); 5684 } 5685 5686 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 5687 } 5688 5689 #define expect_data_available(a,b) _expect_data_available(__LINE__,a,b) 5690 static DWORD _expect_data_available(unsigned line, HINTERNET req, int exsize) 5691 { 5692 DWORD size = 0; 5693 BOOL res; 5694 5695 res = InternetQueryDataAvailable(req, &size, 0, 0); 5696 ok_(__FILE__,line)(res, "InternetQueryDataAvailable failed: %u\n", GetLastError()); 5697 if(exsize != -1) 5698 ok_(__FILE__,line)(size == exsize, "size = %u, expected %u\n", size, exsize); 5699 5700 return size; 5701 } 5702 5703 #define async_query_data_available(a,b) _async_query_data_available(__LINE__,a,b) 5704 static void _async_query_data_available(unsigned line, HINTERNET req, DWORD *size) 5705 { 5706 BOOL res; 5707 5708 if(!skip_receive_notification_tests) 5709 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 5710 5711 *size = 0xdeadbeef; 5712 res = InternetQueryDataAvailable(req, size, 0, 0); 5713 ok_(__FILE__,line)(!res && GetLastError() == ERROR_IO_PENDING, 5714 "InternetQueryDataAvailable returned: %x(%u)\n", res, GetLastError()); 5715 ok_(__FILE__,line)(!*size, "size = %u\n", *size); 5716 5717 if(!skip_receive_notification_tests) 5718 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 5719 } 5720 5721 static void test_http_read(int port) 5722 { 5723 INTERNET_BUFFERSW ib; 5724 test_request_t req; 5725 DWORD read_size; 5726 char buf[24000]; 5727 DWORD avail, i; 5728 5729 if(!is_ie7plus) 5730 return; 5731 5732 memset(&ib, 0, sizeof(ib)); 5733 ib.dwStructSize = sizeof(ib); 5734 ib.lpvBuffer = buf; 5735 5736 trace("Testing InternetReadFileExW with IRF_ASYNC flag...\n"); 5737 5738 open_read_test_request(port, &req, 5739 "HTTP/1.1 200 OK\r\n" 5740 "Server: winetest\r\n" 5741 "\r\n" 5742 "xx"); 5743 5744 readex_expect_async(req.request, IRF_ASYNC, &ib, 4, "xx"); 5745 5746 send_response_ex_and_wait("yy1234567890", FALSE, &ib, "xxyy", 0, 2); 5747 readex_expect_sync_data(req.request, IRF_ASYNC, &ib, 4, "1234", 4); 5748 readex_expect_sync_data(req.request, IRF_ASYNC, &ib, 5, "56789", 5); 5749 5750 readex_expect_async(req.request, IRF_ASYNC, &ib, sizeof(buf), "0"); 5751 send_response_ex_and_wait("123", TRUE, &ib, "0123", 0, 4); 5752 5753 close_async_handle(req.session, 2); 5754 5755 trace("Testing InternetReadFileExW with no flags...\n"); 5756 5757 open_read_test_request(port, &req, 5758 "HTTP/1.1 200 OK\r\n" 5759 "Server: winetest\r\n" 5760 "\r\n" 5761 "xx"); 5762 5763 readex_expect_async(req.request, 0, &ib, 4, "xx"); 5764 5765 send_response_ex_and_wait("yy1234567890", FALSE, &ib, "xxyy", 0, 2); 5766 readex_expect_sync_data(req.request, 0, &ib, 4, "1234", 4); 5767 readex_expect_sync_data(req.request, 0, &ib, 5, "56789", 5); 5768 5769 readex_expect_async(req.request, 0, &ib, sizeof(buf), "0"); 5770 send_response_ex_and_wait("123", TRUE, &ib, "0123", 0, 4); 5771 5772 close_async_handle(req.session, 2); 5773 5774 trace("Testing InternetReadFile...\n"); 5775 5776 open_read_test_request(port, &req, 5777 "HTTP/1.1 200 OK\r\n" 5778 "Server: winetest\r\n" 5779 "\r\n" 5780 "xx"); 5781 5782 read_expect_async(req.request, buf, 4, &read_size, "xx"); 5783 5784 send_response_and_wait("yy1234567890", FALSE, buf, &read_size, "xxyy", 4, 0, 2); 5785 read_expect_sync_data(req.request, buf, 4, "1234"); 5786 read_expect_sync_data(req.request, buf, 5, "56789"); 5787 5788 read_expect_async(req.request, buf, sizeof(buf), &read_size, "0"); 5789 send_response_and_wait("123", TRUE, buf, &read_size, "0123", 4, 0, 4); 5790 5791 close_async_handle(req.session, 2); 5792 5793 trace("Testing InternetReadFileExW with IRF_NO_WAIT flag...\n"); 5794 5795 open_read_test_request(port, &req, 5796 "HTTP/1.1 200 OK\r\n" 5797 "Server: winetest\r\n" 5798 "\r\n" 5799 "xx"); 5800 5801 SET_OPTIONAL(INTERNET_STATUS_RECEIVING_RESPONSE); 5802 5803 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "xx", 0); 5804 5805 if(notified[INTERNET_STATUS_RECEIVING_RESPONSE]) { 5806 win_skip("Skipping receive notification tests on too old Windows.\n"); 5807 skip_receive_notification_tests = TRUE; 5808 } 5809 CLEAR_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 5810 5811 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5812 send_response_ex_and_wait("1234567890", FALSE, &ib, NULL, 0, 10); 5813 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, 5, "12345", 0); 5814 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "67890", 0); 5815 5816 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5817 send_response_ex_and_wait("12345", TRUE, &ib, NULL, 0, 5); 5818 5819 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "12345", 0); 5820 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "", TRUE); 5821 5822 close_async_handle(req.session, 2); 5823 5824 open_read_test_request(port, &req, 5825 "HTTP/1.1 200 OK\r\n" 5826 "Server: winetest\r\n" 5827 "Transfer-Encoding: chunked\r\n" 5828 "\r\n" 5829 "9\r\n123456789"); 5830 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "123456789", 0); 5831 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5832 5833 send_response_ex_and_wait("\r\n1\r\na\r\n1\r\nb\r", FALSE, &ib, NULL, 0, 13); 5834 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "ab", 0); 5835 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5836 5837 send_response_ex_and_wait("\n3\r\nab", FALSE, &ib, NULL, 0, 6); 5838 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "ab", 0); 5839 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5840 5841 send_response_ex_and_wait("c", FALSE, &ib, NULL, 0, 1); 5842 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "c", 0); 5843 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5844 5845 send_response_ex_and_wait("\r\n1\r\nx\r\n0\r\n\r\n", TRUE, &ib, NULL, 0, 13); 5846 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "x", 0); 5847 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "", 0); 5848 5849 close_async_handle(req.session, 2); 5850 5851 open_read_test_request(port, &req, 5852 "HTTP/1.1 200 OK\r\n" 5853 "Server: winetest\r\n" 5854 "Transfer-Encoding: chunked\r\n" 5855 "\r\n" 5856 "3\r\n123\r\n"); 5857 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "123", 0); 5858 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5859 5860 send_response_ex_and_wait("0\r\n\r\n", TRUE, &ib, NULL, 0, 5); 5861 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "", 0); 5862 5863 close_async_handle(req.session, 2); 5864 5865 open_read_test_request(port, &req, 5866 "HTTP/1.1 200 OK\r\n" 5867 "Server: winetest\r\n" 5868 "Connection: close\r\n" 5869 "\r\n"); 5870 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5871 send_response_ex_and_wait("123", TRUE, &ib, NULL, 0, 3); 5872 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "123", 0); 5873 5874 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 5875 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 5876 close_async_handle(req.session, 2); 5877 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 5878 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 5879 5880 trace("Testing InternetQueryDataAvailable...\n"); 5881 5882 open_read_test_request(port, &req, 5883 "HTTP/1.1 200 OK\r\n" 5884 "Server: winetest\r\n" 5885 "\r\n" 5886 "123"); 5887 expect_data_available(req.request, 3); 5888 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "123", 0); 5889 readex_expect_async(req.request, IRF_NO_WAIT, &ib, sizeof(buf), NULL); 5890 5891 send_response_len_and_wait(20000, TRUE, &ib); 5892 avail = expect_data_available(req.request, -1); 5893 ok(avail <= 20000, "avail = %u\n", avail); 5894 5895 SET_WINE_ALLOW(INTERNET_STATUS_CLOSING_CONNECTION); 5896 SET_WINE_ALLOW(INTERNET_STATUS_CONNECTION_CLOSED); 5897 close_async_handle(req.session, 2); 5898 todo_wine CHECK_NOT_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 5899 todo_wine CHECK_NOT_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 5900 5901 open_read_test_request(port, &req, 5902 "HTTP/1.1 200 OK\r\n" 5903 "Server: winetest\r\n" 5904 "Connection: close\r\n" 5905 "\r\n" 5906 "123"); 5907 5908 expect_data_available(req.request, 3); 5909 readex_expect_sync_data(req.request, 0, &ib, 3, "123", 0); 5910 5911 async_query_data_available(req.request, &read_size); 5912 send_response_and_wait("1234567890", FALSE, NULL, &read_size, NULL, 10, 10, 10); 5913 5914 readex_expect_sync_data(req.request, 0, &ib, 9, "123456789", 0); 5915 expect_data_available(req.request, 1); 5916 readex_expect_sync_data(req.request, 0, &ib, 1, "0", 0); 5917 5918 async_query_data_available(req.request, &read_size); 5919 send_response_and_wait("1234567890", FALSE, NULL, &read_size, NULL, 10, 10, 10); 5920 expect_data_available(req.request, 10); 5921 for(i = 0; i < 10; i++) 5922 server_send_string("x"); 5923 expect_data_available(req.request, 10); 5924 5925 readex_expect_async(req.request, IRF_ASYNC, &ib, 21, "1234567890"); 5926 send_response_ex_and_wait("X", FALSE, &ib, "1234567890xxxxxxxxxxX", 0, 11); 5927 async_query_data_available(req.request, &read_size); 5928 5929 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 5930 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 5931 send_response_and_wait(NULL, TRUE, NULL, &read_size, NULL, 0, 0, 0); 5932 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 5933 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 5934 5935 close_async_handle(req.session, 2); 5936 5937 skip_receive_notification_tests = FALSE; 5938 } 5939 5940 static void test_connection_break(int port) 5941 { 5942 INTERNET_BUFFERSW ib; 5943 test_request_t req; 5944 char buf[24000]; 5945 5946 if(!is_ie7plus) 5947 return; 5948 5949 memset(&ib, 0, sizeof(ib)); 5950 ib.dwStructSize = sizeof(ib); 5951 ib.lpvBuffer = buf; 5952 5953 trace("Testing InternetReadFileExW on broken connection...\n"); 5954 5955 open_read_test_request(port, &req, 5956 "HTTP/1.1 200 OK\r\n" 5957 "Server: winetest\r\n" 5958 "Content-Length: 10000\r\n" 5959 "\r\n" 5960 "xx"); 5961 5962 /* close connection and make sure that it's closed on handle release. */ 5963 close_connection(); 5964 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 5965 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 5966 close_async_handle(req.session, 2); 5967 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 5968 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 5969 } 5970 5971 static void test_long_url(int port) 5972 { 5973 char long_path[INTERNET_MAX_PATH_LENGTH*2] = "/echo_request?"; 5974 char buf[sizeof(long_path)*2], url[sizeof(buf)]; 5975 test_request_t req; 5976 DWORD size, len; 5977 BOOL ret; 5978 5979 if(!is_ie7plus) 5980 return; 5981 5982 memset(long_path+strlen(long_path), 'x', sizeof(long_path)-strlen(long_path)); 5983 long_path[sizeof(long_path)-1] = 0; 5984 open_simple_request(&req, "localhost", port, NULL, long_path); 5985 5986 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 5987 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 5988 test_status_code(req.request, 200); 5989 5990 receive_simple_request(req.request, buf, sizeof(buf)); 5991 ok(strstr(buf, long_path) != NULL, "long pathnot found in %s\n", buf); 5992 5993 sprintf(url, "http://localhost:%u%s", port, long_path); 5994 5995 size = sizeof(buf); 5996 ret = InternetQueryOptionA(req.request, INTERNET_OPTION_URL, buf, &size); 5997 ok(ret, "InternetQueryOptionA(INTERNET_OPTION_URL) failed: %u\n", GetLastError()); 5998 len = strlen(url); 5999 ok(size == len, "size = %u, expected %u\n", size, len); 6000 ok(!strcmp(buf, url), "Wrong URL %s, expected %s\n", buf, url); 6001 6002 close_request(&req); 6003 } 6004 6005 static void test_persistent_connection(int port) 6006 { 6007 INTERNET_BUFFERSW ib; 6008 test_request_t req; 6009 char buf[24000]; 6010 6011 if(!is_ie7plus) 6012 return; 6013 6014 memset(&ib, 0, sizeof(ib)); 6015 ib.dwStructSize = sizeof(ib); 6016 ib.lpvBuffer = buf; 6017 6018 skip_receive_notification_tests = TRUE; 6019 6020 trace("Testing persistent connection...\n"); 6021 6022 open_read_test_request(port, &req, 6023 "HTTP/1.1 200 OK\r\n" 6024 "Server: winetest\r\n" 6025 "Content-Length: 2\r\n" 6026 "\r\n" 6027 "xx"); 6028 readex_expect_sync_data(req.request, IRF_ASYNC, &ib, 4, "xx", 0); 6029 close_async_handle(req.session, 2); 6030 6031 open_socket_request(port, &req, "/test_simple_chunked"); 6032 server_read_request("GET /test_simple_chunked HTTP/1.1"); 6033 6034 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6035 server_send_string("HTTP/1.1 200 OK\r\n" 6036 "Server: winetest\r\n" 6037 "Transfer-Encoding: chunked\r\n" 6038 "\r\n" 6039 "2\r\nab\r\n"); 6040 WaitForSingleObject(complete_event, INFINITE); 6041 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6042 ok(req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error); 6043 6044 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "ab", 0); 6045 readex_expect_async(req.request, IRF_ASYNC, &ib, sizeof(buf), NULL); 6046 send_response_ex_and_wait("3\r\nabc\r\n0\r\n\r\n", FALSE, &ib, "abc", 0, 13); 6047 close_async_handle(req.session, 2); 6048 6049 open_socket_request(port, &req, "/chunked"); 6050 server_read_request("GET /chunked HTTP/1.1"); 6051 6052 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6053 server_send_string("HTTP/1.1 200 OK\r\n" 6054 "Server: winetest\r\n" 6055 "Transfer-Encoding: chunked\r\n" 6056 "\r\n" 6057 "2\r\nab\r\n"); 6058 WaitForSingleObject(complete_event, INFINITE); 6059 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6060 ok(req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error); 6061 6062 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, 3, "ab", 0); 6063 readex_expect_async(req.request, IRF_ASYNC, &ib, 3, NULL); 6064 send_response_ex_and_wait("3\r\nabc\r\n", FALSE, &ib, "abc", 0, 13); 6065 6066 /* send another request on the same request handle, it must drain remaining last chunk marker */ 6067 server_send_string("0\r\n\r\n"); 6068 6069 send_socket_request(&req, FALSE); 6070 server_read_request("GET /chunked HTTP/1.1"); 6071 6072 ResetEvent(complete_event); 6073 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6074 server_send_string("HTTP/1.1 201 OK\r\n" 6075 "Server: winetest\r\n" 6076 "Content-Length: 0\r\n" 6077 "Connection: keep-alive\r\n" 6078 "\r\n"); 6079 WaitForSingleObject(complete_event, INFINITE); 6080 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6081 ok(req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error); 6082 6083 test_status_code(req.request, 201); 6084 close_async_handle(req.session, 2); 6085 6086 /* the connection is still valid */ 6087 open_socket_request(port, &req, "/another_chunked"); 6088 server_read_request("GET /another_chunked HTTP/1.1"); 6089 6090 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6091 server_send_string("HTTP/1.1 200 OK\r\n" 6092 "Server: winetest\r\n" 6093 "Transfer-Encoding: chunked\r\n" 6094 "\r\n" 6095 "2\r\nab\r\n"); 6096 WaitForSingleObject(complete_event, INFINITE); 6097 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6098 ok(req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error); 6099 6100 readex_expect_sync_data(req.request, IRF_NO_WAIT, &ib, sizeof(buf), "ab", 0); 6101 readex_expect_async(req.request, IRF_ASYNC, &ib, sizeof(buf), NULL); 6102 6103 /* we're missing trailing '\n'; the connection can't be drained without blocking, 6104 * so it will be closed */ 6105 send_response_ex_and_wait("3\r\nabc\r\n0\r\n\r", FALSE, &ib, "abc", 0, 13); 6106 6107 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 6108 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 6109 close_async_handle(req.session, 2); 6110 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 6111 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 6112 6113 close_connection(); 6114 skip_receive_notification_tests = FALSE; 6115 } 6116 6117 static void test_redirect(int port) 6118 { 6119 char buf[4000], expect_url[INTERNET_MAX_URL_LENGTH]; 6120 INTERNET_BUFFERSW ib; 6121 test_request_t req; 6122 6123 if(!is_ie7plus) 6124 return; 6125 6126 skip_receive_notification_tests = TRUE; 6127 6128 memset(&ib, 0, sizeof(ib)); 6129 ib.dwStructSize = sizeof(ib); 6130 ib.lpvBuffer = buf; 6131 6132 trace("Testing redirection...\n"); 6133 6134 open_socket_request(port, &req, NULL); 6135 6136 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 6137 SET_EXPECT(INTERNET_STATUS_REDIRECT); 6138 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 6139 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 6140 6141 server_send_string("HTTP/1.1 302 Found\r\n" 6142 "Server: winetest\r\n" 6143 "Location: test_redirection\r\n" 6144 "Connection: keep-alive\r\n" 6145 "Content-Length: 0\r\n" 6146 "\r\n"); 6147 6148 server_read_request("GET /test_redirection HTTP/1.1"); 6149 6150 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 6151 6152 sprintf(expect_url, "http://localhost:%u/test_redirection", port); 6153 test_request_url(req.request, expect_url); 6154 6155 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6156 6157 server_send_string("HTTP/1.1 200 OK\r\n" 6158 "Server: winetest\r\n" 6159 "Content-Length: 3\r\n" 6160 "\r\n" 6161 "xxx"); 6162 6163 WaitForSingleObject(complete_event, INFINITE); 6164 6165 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 6166 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 6167 CHECK_NOTIFIED(INTERNET_STATUS_REDIRECT); 6168 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6169 ok(req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error); 6170 6171 test_status_code(req.request, 200); 6172 6173 close_connection(); 6174 close_async_handle(req.session, 2); 6175 6176 trace("Test redirect to non-http URL...\n"); 6177 6178 open_socket_request(port, &req, NULL); 6179 6180 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6181 6182 server_send_string("HTTP/1.1 302 Found\r\n" 6183 "Server: winetest\r\n" 6184 "Location: test:non:http/url\r\n" 6185 "Connection: keep-alive\r\n" 6186 "Content-Length: 0\r\n" 6187 "\r\n"); 6188 6189 WaitForSingleObject(complete_event, INFINITE); 6190 6191 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6192 ok(req_error == ERROR_SUCCESS, "expected ERROR_SUCCESS, got %u\n", req_error); 6193 6194 sprintf(expect_url, "http://localhost:%u/socket", port); 6195 test_request_url(req.request, expect_url); 6196 test_status_code(req.request, 302); 6197 6198 close_connection(); 6199 close_async_handle(req.session, 2); 6200 6201 trace("Test redirect to http URL with no host name...\n"); 6202 6203 open_socket_request(port, &req, NULL); 6204 6205 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6206 6207 server_send_string("HTTP/1.1 302 Found\r\n" 6208 "Server: winetest\r\n" 6209 "Location: http:///nohost\r\n" 6210 "Connection: keep-alive\r\n" 6211 "Content-Length: 0\r\n" 6212 "\r\n"); 6213 6214 WaitForSingleObject(complete_event, INFINITE); 6215 6216 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6217 ok(req_error == ERROR_INTERNET_INVALID_URL, "expected ERROR_INTERNET_INVALID_URL, got %u\n", req_error); 6218 6219 sprintf(expect_url, "http://localhost:%u/socket", port); 6220 test_request_url(req.request, expect_url); 6221 test_status_code(req.request, 302); 6222 6223 close_connection(); 6224 close_async_handle(req.session, 2); 6225 6226 skip_receive_notification_tests = FALSE; 6227 } 6228 6229 static void test_remove_dot_segments(int port) 6230 { 6231 test_request_t req; 6232 BOOL ret; 6233 6234 open_simple_request(&req, "localhost", port, NULL, "/A/../B/./C/../../test_remove_dot_segments"); 6235 6236 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 6237 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 6238 test_status_code(req.request, 200); 6239 6240 close_request(&req); 6241 } 6242 6243 struct large_test 6244 { 6245 DWORD64 content_length; 6246 BOOL ret; 6247 }; 6248 6249 static void test_large_content(int port) 6250 { 6251 struct large_test tests[] = { 6252 { 0, TRUE }, 6253 { UINT_MAX-1, TRUE }, 6254 { UINT_MAX, TRUE }, 6255 { (DWORD64)UINT_MAX+1, FALSE }, 6256 { ~0, FALSE }, 6257 }; 6258 test_request_t req; 6259 DWORD sizelen, len; 6260 DWORD read_size; 6261 DWORD64 len64; 6262 char buf[16]; 6263 BOOL ret; 6264 size_t i; 6265 6266 open_simple_request(&req, "localhost", port, "HEAD", "/test_large_content"); 6267 6268 for (i = 0; i < ARRAY_SIZE(tests); i++) 6269 { 6270 content_length = tests[i].content_length; 6271 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 6272 ok(ret, "HttpSendRequest failed: %u\n", GetLastError()); 6273 6274 len = ~0; 6275 sizelen = sizeof(len); 6276 SetLastError(0xdeadbeef); 6277 ret = HttpQueryInfoA(req.request, HTTP_QUERY_FLAG_NUMBER|HTTP_QUERY_CONTENT_LENGTH, 6278 &len, &sizelen, 0); 6279 if (tests[i].ret) 6280 { 6281 ok(ret, "HttpQueryInfo should have succeeded\n"); 6282 ok(GetLastError() == ERROR_SUCCESS || 6283 broken(GetLastError() == 0xdeadbeef), /* xp, 2k8, vista */ 6284 "expected ERROR_SUCCESS, got %x\n", GetLastError()); 6285 ok(len == (DWORD)tests[i].content_length, "expected %u, got %u\n", 6286 (DWORD)tests[i].content_length, len); 6287 } 6288 else 6289 { 6290 ok(!ret, "HttpQueryInfo should have failed\n"); 6291 ok(GetLastError() == ERROR_HTTP_INVALID_HEADER, 6292 "expected ERROR_HTTP_INVALID_HEADER, got %x\n", GetLastError()); 6293 ok(len == ~0, "expected ~0, got %u\n", len); 6294 } 6295 ok(sizelen == sizeof(DWORD), "sizelen %u\n", sizelen); 6296 } 6297 6298 /* test argument size */ 6299 len64 = ~0; 6300 sizelen = sizeof(len64); 6301 SetLastError(0xdeadbeef); 6302 ret = HttpQueryInfoA(req.request, HTTP_QUERY_FLAG_NUMBER|HTTP_QUERY_CONTENT_LENGTH, 6303 &len64, &len, 0); 6304 ok(!ret, "HttpQueryInfo should have failed\n"); 6305 ok(GetLastError() == ERROR_HTTP_INVALID_HEADER, 6306 "expected ERROR_HTTP_INVALID_HEADER, got %x\n", GetLastError()); 6307 ok(sizelen == sizeof(DWORD64), "sizelen %u\n", sizelen); 6308 ok(len64 == ~0, "len64 %x%08x\n", (DWORD)(len64 >> 32), (DWORD)len64); 6309 6310 close_request(&req); 6311 6312 /* test internal use of HttpQueryInfo on large size */ 6313 open_read_test_request(port, &req, 6314 "HTTP/1.1 200 OK\r\n" 6315 "Server: winetest\r\n" 6316 "Content-Length: 4294967296\r\n" 6317 "\r\n" 6318 "xx"); 6319 read_expect_async(req.request, buf, 4, &read_size, "xx"); 6320 send_response_and_wait("yy1234567890", FALSE, buf, &read_size, "xxyy", 4, 0, 2); 6321 read_expect_sync_data(req.request, buf, 10, "1234567890"); 6322 6323 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 6324 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 6325 close_async_handle(req.session, 2); 6326 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 6327 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 6328 close_connection(); 6329 } 6330 6331 static void test_http_connection(void) 6332 { 6333 struct server_info si; 6334 HANDLE hThread; 6335 DWORD id = 0, r; 6336 6337 si.hEvent = CreateEventW(NULL, 0, 0, NULL); 6338 si.port = 7531; 6339 6340 hThread = CreateThread(NULL, 0, server_thread, &si, 0, &id); 6341 ok( hThread != NULL, "create thread failed\n"); 6342 6343 r = WaitForSingleObject(si.hEvent, 10000); 6344 ok (r == WAIT_OBJECT_0, "failed to start wininet test server\n"); 6345 if (r != WAIT_OBJECT_0) 6346 { 6347 CloseHandle(hThread); 6348 return; 6349 } 6350 6351 test_basic_request(si.port, "GET", "/test1"); 6352 test_proxy_indirect(si.port); 6353 test_proxy_direct(si.port); 6354 test_header_handling_order(si.port); 6355 test_basic_request(si.port, "POST", "/test5"); 6356 test_basic_request(si.port, "RPC_IN_DATA", "/test5"); 6357 test_basic_request(si.port, "RPC_OUT_DATA", "/test5"); 6358 test_basic_request(si.port, "GET", "/test6"); 6359 test_basic_request(si.port, "GET", "/testF"); 6360 test_connection_header(si.port); 6361 test_header_override(si.port); 6362 test_cookie_header(si.port); 6363 test_basic_authentication(si.port); 6364 test_invalid_response_headers(si.port); 6365 test_response_without_headers(si.port); 6366 test_HttpQueryInfo(si.port); 6367 test_HttpSendRequestW(si.port); 6368 test_options(si.port); 6369 test_no_content(si.port); 6370 test_conn_close(si.port); 6371 test_no_cache(si.port); 6372 test_cache_read_gzipped(si.port); 6373 test_http_status(si.port); 6374 test_premature_disconnect(si.port); 6375 test_connection_closing(si.port); 6376 test_cache_control_verb(si.port); 6377 test_successive_HttpSendRequest(si.port); 6378 test_head_request(si.port); 6379 test_request_content_length(si.port); 6380 test_accept_encoding(si.port); 6381 test_basic_auth_credentials_reuse(si.port); 6382 test_basic_auth_credentials_end_session(si.port); 6383 test_basic_auth_credentials_different(si.port); 6384 test_basic_auth_credentials_manual(si.port); 6385 test_basic_auth_credentials_cached_manual(si.port); 6386 test_async_read(si.port); 6387 test_http_read(si.port); 6388 test_connection_break(si.port); 6389 test_long_url(si.port); 6390 #ifdef __REACTOS__ 6391 if (!winetest_interactive) 6392 { 6393 skip("Skipping test_redirect and test_persistent_connection due to hang. See ROSTESTS-294.\n"); 6394 } 6395 else 6396 { 6397 #endif 6398 test_redirect(si.port); 6399 test_persistent_connection(si.port); 6400 #ifdef __REACTOS__ 6401 } 6402 #endif 6403 test_remove_dot_segments(si.port); 6404 test_large_content(si.port); 6405 6406 /* send the basic request again to shutdown the server thread */ 6407 test_basic_request(si.port, "GET", "/quit"); 6408 6409 r = WaitForSingleObject(hThread, 3000); 6410 ok( r == WAIT_OBJECT_0, "thread wait failed\n"); 6411 CloseHandle(hThread); 6412 } 6413 6414 static void release_cert_info(INTERNET_CERTIFICATE_INFOA *info) 6415 { 6416 LocalFree(info->lpszSubjectInfo); 6417 LocalFree(info->lpszIssuerInfo); 6418 LocalFree(info->lpszProtocolName); 6419 LocalFree(info->lpszSignatureAlgName); 6420 LocalFree(info->lpszEncryptionAlgName); 6421 } 6422 6423 typedef struct { 6424 const char *ex_subject; 6425 const char *ex_issuer; 6426 } cert_struct_test_t; 6427 6428 static const cert_struct_test_t test_winehq_org_cert = { 6429 "US\r\n" 6430 "55114\r\n" 6431 "Minnesota\r\n" 6432 "Saint Paul\r\n" 6433 "Ste 120\r\n" 6434 "700 Raymond Ave\r\n" 6435 "CodeWeavers\r\n" 6436 "IT\r\n" 6437 "*.winehq.org", 6438 6439 "US\r\n" 6440 "VA\r\n" 6441 "Herndon\r\n" 6442 "Network Solutions L.L.C.\r\n" 6443 "Network Solutions OV Server CA 2" 6444 }; 6445 6446 static const cert_struct_test_t test_winehq_com_cert = { 6447 "US\r\n" 6448 "Minnesota\r\n" 6449 "Saint Paul\r\n" 6450 "WineHQ\r\n" 6451 "IT\r\n" 6452 "test.winehq.com\r\n" 6453 "webmaster@winehq.org", 6454 6455 "US\r\n" 6456 "Minnesota\r\n" 6457 "Saint Paul\r\n" 6458 "WineHQ\r\n" 6459 "IT\r\n" 6460 "test.winehq.com\r\n" 6461 "webmaster@winehq.org" 6462 }; 6463 6464 static const char *cert_string_fmt = 6465 "Subject:\r\n%s\r\n" 6466 "Issuer:\r\n%s\r\n" 6467 "Effective Date:\t%s %s\r\n" 6468 "Expiration Date:\t%s %s\r\n" 6469 "Security Protocol:\t%s\r\n" 6470 "Signature Type:\t%s\r\n" 6471 "Encryption Type:\t%s\r\n" 6472 "Privacy Strength:\t%s (%u bits)"; 6473 6474 static void test_cert_struct_string(HINTERNET req, const INTERNET_CERTIFICATE_INFOA *info) 6475 { 6476 SYSTEMTIME start, expiry; 6477 char expiry_date[32]; 6478 char expiry_time[32]; 6479 char start_date[32]; 6480 char start_time[32]; 6481 char expect[512]; 6482 char actual[512]; 6483 DWORD size; 6484 BOOL res; 6485 6486 size = sizeof(actual); 6487 SetLastError(0xdeadbeef); 6488 memset(actual, 0x55, sizeof(actual)); 6489 res = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_CERTIFICATE, actual, &size); 6490 ok(res, "InternetQueryOption failed: %u\n", GetLastError()); 6491 6492 FileTimeToSystemTime(&info->ftStart, &start); 6493 FileTimeToSystemTime(&info->ftExpiry, &expiry); 6494 6495 GetDateFormatA(LOCALE_USER_DEFAULT, 0, &start, NULL, start_date, sizeof(start_date)); 6496 GetTimeFormatA(LOCALE_USER_DEFAULT, 0, &start, NULL, start_time, sizeof(start_time)); 6497 GetDateFormatA(LOCALE_USER_DEFAULT, 0, &expiry, NULL, expiry_date, sizeof(expiry_date)); 6498 GetTimeFormatA(LOCALE_USER_DEFAULT, 0, &expiry, NULL, expiry_time, sizeof(expiry_time)); 6499 6500 snprintf(expect, sizeof(expect), cert_string_fmt, info->lpszSubjectInfo, info->lpszIssuerInfo, 6501 start_date, start_time, expiry_date, expiry_time, 6502 info->lpszSignatureAlgName, info->lpszEncryptionAlgName, info->lpszProtocolName, 6503 info->dwKeySize >= 128 ? "High" : "Low", info->dwKeySize); 6504 ok(size == strlen(actual), "size = %u\n", size); 6505 ok(!strcmp(actual, expect), "expected:\n%s\nactual:\n%s\n", expect, actual); 6506 6507 --size; 6508 SetLastError(0xdeadbeef); 6509 memset(actual, 0x55, sizeof(actual)); 6510 res = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_CERTIFICATE, actual, &size); 6511 ok(!res && GetLastError() == ERROR_INSUFFICIENT_BUFFER, "InternetQueryOption failed: %d\n", GetLastError()); 6512 ok(size == 1, "unexpected size: %u\n", size); 6513 ok(actual[0] == 0x55, "unexpected byte: %02x\n", actual[0]); 6514 } 6515 6516 static void test_cert_struct(HINTERNET req, const cert_struct_test_t *test) 6517 { 6518 INTERNET_CERTIFICATE_INFOA info; 6519 DWORD size; 6520 BOOL res; 6521 6522 memset(&info, 0x5, sizeof(info)); 6523 6524 size = sizeof(info); 6525 res = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, &info, &size); 6526 if (!res) 6527 { 6528 win_skip("Querying INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT failed, skipping tests\n"); 6529 return; 6530 } 6531 6532 ok(res, "InternetQueryOption failed: %u\n", GetLastError()); 6533 ok(size == sizeof(info), "size = %u\n", size); 6534 6535 ok(!strcmp(info.lpszSubjectInfo, test->ex_subject), "lpszSubjectInfo = %s\n", info.lpszSubjectInfo); 6536 ok(!strcmp(info.lpszIssuerInfo, test->ex_issuer), "lpszIssuerInfo = %s\n", info.lpszIssuerInfo); 6537 ok(!info.lpszSignatureAlgName, "lpszSignatureAlgName = %s\n", info.lpszSignatureAlgName); 6538 ok(!info.lpszEncryptionAlgName, "lpszEncryptionAlgName = %s\n", info.lpszEncryptionAlgName); 6539 ok(!info.lpszProtocolName, "lpszProtocolName = %s\n", info.lpszProtocolName); 6540 ok(info.dwKeySize >= 128 && info.dwKeySize <= 256, "dwKeySize = %u\n", info.dwKeySize); 6541 6542 if (is_lang_english()) 6543 test_cert_struct_string(req, &info); 6544 else 6545 skip("Skipping tests that are English-only\n"); 6546 release_cert_info(&info); 6547 } 6548 6549 #define test_security_info(a,b,c) _test_security_info(__LINE__,a,b,c) 6550 static void _test_security_info(unsigned line, const char *urlc, DWORD error, DWORD ex_flags) 6551 { 6552 char url[INTERNET_MAX_URL_LENGTH]; 6553 const CERT_CHAIN_CONTEXT *chain; 6554 DWORD flags; 6555 BOOL res; 6556 6557 if(!pInternetGetSecurityInfoByURLA) { 6558 win_skip("pInternetGetSecurityInfoByURLA not available\n"); 6559 return; 6560 } 6561 6562 strcpy(url, urlc); 6563 chain = (void*)0xdeadbeef; 6564 flags = 0xdeadbeef; 6565 res = pInternetGetSecurityInfoByURLA(url, &chain, &flags); 6566 if(error == ERROR_SUCCESS) { 6567 ok_(__FILE__,line)(res, "InternetGetSecurityInfoByURLA failed: %u\n", GetLastError()); 6568 ok_(__FILE__,line)(chain != NULL, "chain = NULL\n"); 6569 ok_(__FILE__,line)(flags == ex_flags, "flags = %x\n", flags); 6570 CertFreeCertificateChain(chain); 6571 6572 SetLastError(0xdeadbeef); 6573 res = pInternetGetSecurityInfoByURLA(url, NULL, NULL); 6574 ok_(__FILE__,line)(!res && GetLastError() == ERROR_INVALID_PARAMETER, 6575 "InternetGetSecurityInfoByURLA returned: %x(%u)\n", res, GetLastError()); 6576 6577 res = pInternetGetSecurityInfoByURLA(url, &chain, NULL); 6578 ok_(__FILE__,line)(res, "InternetGetSecurityInfoByURLA failed: %u\n", GetLastError()); 6579 CertFreeCertificateChain(chain); 6580 6581 res = pInternetGetSecurityInfoByURLA(url, NULL, &flags); 6582 ok_(__FILE__,line)(res, "InternetGetSecurityInfoByURLA failed: %u\n", GetLastError()); 6583 }else { 6584 ok_(__FILE__,line)(!res && GetLastError() == error, 6585 "InternetGetSecurityInfoByURLA returned: %x(%u), expected %u\n", res, GetLastError(), error); 6586 } 6587 } 6588 6589 #define test_secflags_option(a,b,c) _test_secflags_option(__LINE__,a,b,c) 6590 static void _test_secflags_option(unsigned line, HINTERNET req, DWORD ex_flags, DWORD opt_flags) 6591 { 6592 DWORD flags, size; 6593 BOOL res; 6594 6595 flags = 0xdeadbeef; 6596 size = sizeof(flags); 6597 res = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_FLAGS, &flags, &size); 6598 ok_(__FILE__,line)(res, "InternetQueryOptionW(INTERNET_OPTION_SECURITY_FLAGS) failed: %u\n", GetLastError()); 6599 ok_(__FILE__,line)((flags & ~opt_flags) == ex_flags, "INTERNET_OPTION_SECURITY_FLAGS flags = %x, expected %x\n", 6600 flags, ex_flags); 6601 6602 /* Option 98 is undocumented and seems to be the same as INTERNET_OPTION_SECURITY_FLAGS */ 6603 flags = 0xdeadbeef; 6604 size = sizeof(flags); 6605 res = InternetQueryOptionW(req, 98, &flags, &size); 6606 ok_(__FILE__,line)(res, "InternetQueryOptionW(98) failed: %u\n", GetLastError()); 6607 ok_(__FILE__,line)((flags & ~opt_flags) == ex_flags, "INTERNET_OPTION_SECURITY_FLAGS(98) flags = %x, expected %x\n", 6608 flags, ex_flags); 6609 } 6610 6611 #define set_secflags(a,b,c) _set_secflags(__LINE__,a,b,c) 6612 static void _set_secflags(unsigned line, HINTERNET req, BOOL use_undoc, DWORD flags) 6613 { 6614 BOOL res; 6615 6616 res = InternetSetOptionW(req, use_undoc ? 99 : INTERNET_OPTION_SECURITY_FLAGS, &flags, sizeof(flags)); 6617 ok_(__FILE__,line)(res, "InternetSetOption(INTERNET_OPTION_SECURITY_FLAGS) failed: %u\n", GetLastError()); 6618 } 6619 6620 static void test_security_flags(void) 6621 { 6622 INTERNET_CERTIFICATE_INFOA *cert; 6623 HINTERNET ses, conn, req; 6624 DWORD size, flags; 6625 char buf[512]; 6626 BOOL res; 6627 6628 if (!https_support) 6629 { 6630 win_skip("Can't make https connections, skipping security flags test\n"); 6631 return; 6632 } 6633 6634 trace("Testing security flags...\n"); 6635 reset_events(); 6636 6637 ses = InternetOpenA("WineTest", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, INTERNET_FLAG_ASYNC); 6638 ok(ses != NULL, "InternetOpen failed\n"); 6639 6640 pInternetSetStatusCallbackA(ses, &callback); 6641 6642 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 6643 conn = InternetConnectA(ses, "test.winehq.com", INTERNET_DEFAULT_HTTPS_PORT, 6644 NULL, NULL, INTERNET_SERVICE_HTTP, INTERNET_FLAG_SECURE, 0xdeadbeef); 6645 ok(conn != NULL, "InternetConnect failed with error %u\n", GetLastError()); 6646 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 6647 6648 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 6649 req = HttpOpenRequestA(conn, "GET", "/tests/hello.html", NULL, NULL, NULL, 6650 INTERNET_FLAG_SECURE|INTERNET_FLAG_KEEP_CONNECTION|INTERNET_FLAG_RELOAD|INTERNET_FLAG_NO_CACHE_WRITE, 6651 0xdeadbeef); 6652 ok(req != NULL, "HttpOpenRequest failed\n"); 6653 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 6654 6655 flags = 0xdeadbeef; 6656 size = sizeof(flags); 6657 res = InternetQueryOptionW(req, 98, &flags, &size); 6658 if(!res && GetLastError() == ERROR_INVALID_PARAMETER) { 6659 win_skip("Incomplete security flags support, skipping\n"); 6660 6661 close_async_handle(ses, 2); 6662 return; 6663 } 6664 6665 test_secflags_option(req, 0, 0); 6666 test_security_info("https://test.winehq.com/data/some_file.html?q", ERROR_INTERNET_ITEM_NOT_FOUND, 0); 6667 6668 set_secflags(req, TRUE, SECURITY_FLAG_IGNORE_REVOCATION); 6669 test_secflags_option(req, SECURITY_FLAG_IGNORE_REVOCATION, 0); 6670 6671 set_secflags(req, TRUE, SECURITY_FLAG_IGNORE_CERT_CN_INVALID); 6672 test_secflags_option(req, SECURITY_FLAG_IGNORE_REVOCATION|SECURITY_FLAG_IGNORE_CERT_CN_INVALID, 0); 6673 6674 set_secflags(req, FALSE, SECURITY_FLAG_IGNORE_UNKNOWN_CA); 6675 test_secflags_option(req, SECURITY_FLAG_IGNORE_UNKNOWN_CA|SECURITY_FLAG_IGNORE_REVOCATION|SECURITY_FLAG_IGNORE_CERT_CN_INVALID, 0); 6676 6677 flags = SECURITY_FLAG_IGNORE_CERT_CN_INVALID|SECURITY_FLAG_SECURE; 6678 res = InternetSetOptionW(req, 99, &flags, sizeof(flags)); 6679 ok(!res && GetLastError() == ERROR_INTERNET_OPTION_NOT_SETTABLE, "InternetSetOption(99) failed: %u\n", GetLastError()); 6680 6681 SET_EXPECT(INTERNET_STATUS_RESOLVING_NAME); 6682 SET_EXPECT(INTERNET_STATUS_NAME_RESOLVED); 6683 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 6684 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 6685 SET_OPTIONAL(INTERNET_STATUS_CLOSING_CONNECTION); /* IE11 calls it, it probably reconnects. */ 6686 SET_OPTIONAL(INTERNET_STATUS_CONNECTION_CLOSED); /* IE11 */ 6687 SET_OPTIONAL(INTERNET_STATUS_CONNECTING_TO_SERVER); /* IE11 */ 6688 SET_OPTIONAL(INTERNET_STATUS_CONNECTED_TO_SERVER); /* IE11 */ 6689 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 6690 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 6691 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 6692 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 6693 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6694 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 6695 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 6696 6697 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 6698 ok(!res && GetLastError() == ERROR_IO_PENDING, "HttpSendRequest failed: %u\n", GetLastError()); 6699 6700 WaitForSingleObject(complete_event, INFINITE); 6701 ok(req_error == ERROR_SUCCESS, "req_error = %d\n", req_error); 6702 6703 CHECK_NOTIFIED(INTERNET_STATUS_RESOLVING_NAME); 6704 CHECK_NOTIFIED(INTERNET_STATUS_NAME_RESOLVED); 6705 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTING_TO_SERVER, 2); 6706 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTED_TO_SERVER, 2); 6707 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 6708 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 6709 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 6710 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 6711 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 6712 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 6713 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6714 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 6715 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 6716 6717 test_request_flags(req, 0); 6718 test_secflags_option(req, SECURITY_FLAG_SECURE|SECURITY_FLAG_IGNORE_UNKNOWN_CA 6719 |SECURITY_FLAG_IGNORE_REVOCATION|SECURITY_FLAG_IGNORE_CERT_CN_INVALID|SECURITY_FLAG_STRENGTH_STRONG, 0); 6720 6721 res = InternetReadFile(req, buf, sizeof(buf), &size); 6722 ok(res, "InternetReadFile failed: %u\n", GetLastError()); 6723 ok(size, "size = 0\n"); 6724 6725 /* Collect all existing persistent connections */ 6726 res = InternetSetOptionA(NULL, INTERNET_OPTION_SETTINGS_CHANGED, NULL, 0); 6727 ok(res, "InternetSetOption(INTERNET_OPTION_END_BROWSER_SESSION) failed: %u\n", GetLastError()); 6728 6729 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 6730 req = HttpOpenRequestA(conn, "GET", "/tests/hello.html", NULL, NULL, NULL, 6731 INTERNET_FLAG_SECURE|INTERNET_FLAG_KEEP_CONNECTION|INTERNET_FLAG_RELOAD|INTERNET_FLAG_NO_CACHE_WRITE, 6732 0xdeadbeef); 6733 ok(req != NULL, "HttpOpenRequest failed\n"); 6734 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 6735 6736 flags = INTERNET_ERROR_MASK_COMBINED_SEC_CERT|INTERNET_ERROR_MASK_LOGIN_FAILURE_DISPLAY_ENTITY_BODY; 6737 res = InternetSetOptionA(req, INTERNET_OPTION_ERROR_MASK, (void*)&flags, sizeof(flags)); 6738 ok(res, "InternetQueryOption(INTERNET_OPTION_ERROR_MASK failed: %u\n", GetLastError()); 6739 6740 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 6741 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 6742 SET_OPTIONAL(INTERNET_STATUS_CLOSING_CONNECTION); /* IE11 calls it, it probably reconnects. */ 6743 SET_OPTIONAL(INTERNET_STATUS_CONNECTION_CLOSED); /* IE11 */ 6744 SET_OPTIONAL(INTERNET_STATUS_CONNECTING_TO_SERVER); /* IE11 */ 6745 SET_OPTIONAL(INTERNET_STATUS_CONNECTED_TO_SERVER); /* IE11 */ 6746 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 6747 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 6748 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6749 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 6750 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 6751 6752 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 6753 ok(!res && GetLastError() == ERROR_IO_PENDING, "HttpSendRequest failed: %u\n", GetLastError()); 6754 6755 WaitForSingleObject(complete_event, INFINITE); 6756 ok(req_error == ERROR_INTERNET_SEC_CERT_ERRORS, 6757 "req_error = %d\n", req_error); 6758 6759 size = 0; 6760 res = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, NULL, &size); 6761 ok(res || GetLastError() == ERROR_INSUFFICIENT_BUFFER, "InternetQueryOption failed: %d\n", GetLastError()); 6762 ok(size == sizeof(INTERNET_CERTIFICATE_INFOA), "size = %u\n", size); 6763 cert = HeapAlloc(GetProcessHeap(), 0, size); 6764 cert->lpszSubjectInfo = NULL; 6765 cert->lpszIssuerInfo = NULL; 6766 cert->lpszSignatureAlgName = (char *)0xdeadbeef; 6767 cert->lpszEncryptionAlgName = (char *)0xdeadbeef; 6768 cert->lpszProtocolName = (char *)0xdeadbeef; 6769 cert->dwKeySize = 0xdeadbeef; 6770 res = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, cert, &size); 6771 ok(res, "InternetQueryOption failed: %u\n", GetLastError()); 6772 if (res) 6773 { 6774 ok(cert->lpszSubjectInfo && strlen(cert->lpszSubjectInfo) > 1, "expected a non-empty subject name\n"); 6775 ok(cert->lpszIssuerInfo && strlen(cert->lpszIssuerInfo) > 1, "expected a non-empty issuer name\n"); 6776 ok(!cert->lpszSignatureAlgName, "unexpected signature algorithm name\n"); 6777 ok(!cert->lpszEncryptionAlgName, "unexpected encryption algorithm name\n"); 6778 ok(!cert->lpszProtocolName, "unexpected protocol name\n"); 6779 ok(cert->dwKeySize != 0xdeadbeef, "unexpected key size\n"); 6780 6781 LocalFree(cert->lpszSubjectInfo); 6782 LocalFree(cert->lpszIssuerInfo); 6783 } 6784 HeapFree(GetProcessHeap(), 0, cert); 6785 6786 SetLastError(0xdeadbeef); 6787 res = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE, NULL, NULL); 6788 ok(!res && GetLastError() == ERROR_INVALID_PARAMETER, "InternetQueryOption failed: %d\n", GetLastError()); 6789 6790 size = 0; 6791 SetLastError(0xdeadbeef); 6792 res = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE, NULL, &size); 6793 ok(!res && GetLastError() == ERROR_INSUFFICIENT_BUFFER, "InternetQueryOption failed: %d\n", GetLastError()); 6794 ok(size == 1, "unexpected size: %u\n", size); 6795 6796 size = 42; 6797 SetLastError(0xdeadbeef); 6798 memset(buf, 0x55, sizeof(buf)); 6799 res = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE, buf, &size); 6800 ok(!res && GetLastError() == ERROR_INSUFFICIENT_BUFFER, "InternetQueryOption failed: %d\n", GetLastError()); 6801 ok(size == 1, "unexpected size: %u\n", size); 6802 ok(buf[0] == 0x55, "unexpected byte: %02x\n", buf[0]); 6803 6804 size = sizeof(buf); 6805 SetLastError(0xdeadbeef); 6806 res = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE, buf, &size); 6807 ok(res && GetLastError() == ERROR_SUCCESS, "InternetQueryOption failed: %d\n", GetLastError()); 6808 ok(size < sizeof(buf), "unexpected size: %u\n", size); 6809 6810 ros_skip_flaky 6811 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTING_TO_SERVER, 2); 6812 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTED_TO_SERVER, 2); 6813 CHECK_NOTIFIED2(INTERNET_STATUS_CLOSING_CONNECTION, 2); 6814 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTION_CLOSED, 2); 6815 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6816 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 6817 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 6818 6819 if(req_error != ERROR_INTERNET_SEC_CERT_ERRORS) { 6820 win_skip("Unexpected cert errors %u, skipping security flags tests\n", req_error); 6821 6822 close_async_handle(ses, 3); 6823 return; 6824 } 6825 6826 size = sizeof(buf); 6827 res = HttpQueryInfoA(req, HTTP_QUERY_CONTENT_ENCODING, buf, &size, 0); 6828 ok(!res && GetLastError() == ERROR_HTTP_HEADER_NOT_FOUND, "HttpQueryInfoA(HTTP_QUERY_CONTENT_ENCODING) failed: %u\n", GetLastError()); 6829 6830 test_request_flags(req, 8); 6831 /* IE11 finds both rev failure and invalid CA. Previous versions required rev failure 6832 to be ignored before invalid CA was reported. */ 6833 test_secflags_option(req, _SECURITY_FLAG_CERT_INVALID_CA, _SECURITY_FLAG_CERT_REV_FAILED); 6834 6835 set_secflags(req, FALSE, SECURITY_FLAG_IGNORE_REVOCATION); 6836 test_secflags_option(req, _SECURITY_FLAG_CERT_INVALID_CA|SECURITY_FLAG_IGNORE_REVOCATION, _SECURITY_FLAG_CERT_REV_FAILED); 6837 6838 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 6839 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 6840 SET_EXPECT(INTERNET_STATUS_CLOSING_CONNECTION); 6841 SET_EXPECT(INTERNET_STATUS_CONNECTION_CLOSED); 6842 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6843 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 6844 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 6845 6846 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 6847 ok(!res && GetLastError() == ERROR_IO_PENDING, "HttpSendRequest failed: %u\n", GetLastError()); 6848 6849 WaitForSingleObject(complete_event, INFINITE); 6850 ok(req_error == ERROR_INTERNET_INVALID_CA || req_error == ERROR_INTERNET_SEC_CERT_ERRORS, "req_error = %d\n", req_error); 6851 6852 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTING_TO_SERVER); 6853 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTED_TO_SERVER); 6854 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 6855 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 6856 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6857 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 6858 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 6859 6860 test_request_flags(req, INTERNET_REQFLAG_NO_HEADERS); 6861 test_secflags_option(req, SECURITY_FLAG_IGNORE_REVOCATION|_SECURITY_FLAG_CERT_INVALID_CA, 0); 6862 test_security_info("https://test.winehq.com/data/some_file.html?q", ERROR_INTERNET_ITEM_NOT_FOUND, 0); 6863 6864 set_secflags(req, FALSE, SECURITY_FLAG_IGNORE_UNKNOWN_CA); 6865 test_secflags_option(req, _SECURITY_FLAG_CERT_INVALID_CA 6866 |SECURITY_FLAG_IGNORE_REVOCATION|SECURITY_FLAG_IGNORE_UNKNOWN_CA, 0); 6867 test_http_version(req); 6868 6869 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 6870 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 6871 SET_OPTIONAL(INTERNET_STATUS_CLOSING_CONNECTION); /* IE11 calls it, it probably reconnects. */ 6872 SET_OPTIONAL(INTERNET_STATUS_CONNECTION_CLOSED); /* IE11 */ 6873 SET_OPTIONAL(INTERNET_STATUS_CONNECTING_TO_SERVER); /* IE11 */ 6874 SET_OPTIONAL(INTERNET_STATUS_CONNECTED_TO_SERVER); /* IE11 */ 6875 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 6876 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 6877 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 6878 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 6879 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6880 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 6881 SET_OPTIONAL(INTERNET_STATUS_DETECTING_PROXY); 6882 6883 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 6884 ok(!res && GetLastError() == ERROR_IO_PENDING, "HttpSendRequest failed: %u\n", GetLastError()); 6885 6886 WaitForSingleObject(complete_event, INFINITE); 6887 ok(req_error == ERROR_SUCCESS, "req_error = %d\n", req_error); 6888 6889 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTING_TO_SERVER, 2); 6890 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTED_TO_SERVER, 2); 6891 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 6892 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 6893 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 6894 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 6895 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 6896 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 6897 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6898 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 6899 CLEAR_NOTIFIED(INTERNET_STATUS_DETECTING_PROXY); 6900 6901 test_request_flags(req, 0); 6902 test_secflags_option(req, SECURITY_FLAG_SECURE|SECURITY_FLAG_IGNORE_UNKNOWN_CA|SECURITY_FLAG_IGNORE_REVOCATION 6903 |SECURITY_FLAG_STRENGTH_STRONG|_SECURITY_FLAG_CERT_INVALID_CA, 0); 6904 6905 test_cert_struct(req, &test_winehq_com_cert); 6906 test_security_info("https://test.winehq.com/data/some_file.html?q", 0, 6907 _SECURITY_FLAG_CERT_INVALID_CA); 6908 6909 res = InternetReadFile(req, buf, sizeof(buf), &size); 6910 ok(res, "InternetReadFile failed: %u\n", GetLastError()); 6911 ok(size, "size = 0\n"); 6912 6913 close_async_handle(ses, 3); 6914 6915 /* Collect all existing persistent connections */ 6916 res = InternetSetOptionA(NULL, INTERNET_OPTION_SETTINGS_CHANGED, NULL, 0); 6917 ok(res, "InternetSetOption(INTERNET_OPTION_END_BROWSER_SESSION) failed: %u\n", GetLastError()); 6918 6919 /* Make another request, without setting security flags */ 6920 6921 ses = InternetOpenA("WineTest", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, INTERNET_FLAG_ASYNC); 6922 ok(ses != NULL, "InternetOpen failed\n"); 6923 6924 pInternetSetStatusCallbackA(ses, &callback); 6925 6926 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 6927 conn = InternetConnectA(ses, "test.winehq.com", INTERNET_DEFAULT_HTTPS_PORT, 6928 NULL, NULL, INTERNET_SERVICE_HTTP, INTERNET_FLAG_SECURE, 0xdeadbeef); 6929 ok(conn != NULL, "InternetConnect failed with error %u\n", GetLastError()); 6930 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 6931 6932 SET_EXPECT(INTERNET_STATUS_HANDLE_CREATED); 6933 req = HttpOpenRequestA(conn, "GET", "/tests/hello.html", NULL, NULL, NULL, 6934 INTERNET_FLAG_SECURE|INTERNET_FLAG_KEEP_CONNECTION|INTERNET_FLAG_RELOAD|INTERNET_FLAG_NO_CACHE_WRITE, 6935 0xdeadbeef); 6936 ok(req != NULL, "HttpOpenRequest failed\n"); 6937 CHECK_NOTIFIED(INTERNET_STATUS_HANDLE_CREATED); 6938 6939 test_secflags_option(req, SECURITY_FLAG_SECURE|SECURITY_FLAG_IGNORE_UNKNOWN_CA|SECURITY_FLAG_STRENGTH_STRONG 6940 |SECURITY_FLAG_IGNORE_REVOCATION|_SECURITY_FLAG_CERT_INVALID_CA, 0); 6941 test_http_version(req); 6942 6943 SET_EXPECT(INTERNET_STATUS_CONNECTING_TO_SERVER); 6944 SET_EXPECT(INTERNET_STATUS_CONNECTED_TO_SERVER); 6945 SET_OPTIONAL(INTERNET_STATUS_CLOSING_CONNECTION); /* IE11 calls it, it probably reconnects. */ 6946 SET_OPTIONAL(INTERNET_STATUS_CONNECTION_CLOSED); /* IE11 */ 6947 SET_OPTIONAL(INTERNET_STATUS_CONNECTING_TO_SERVER); /* IE11 */ 6948 SET_OPTIONAL(INTERNET_STATUS_CONNECTED_TO_SERVER); /* IE11 */ 6949 SET_EXPECT(INTERNET_STATUS_SENDING_REQUEST); 6950 SET_EXPECT(INTERNET_STATUS_REQUEST_SENT); 6951 SET_EXPECT(INTERNET_STATUS_RECEIVING_RESPONSE); 6952 SET_EXPECT(INTERNET_STATUS_RESPONSE_RECEIVED); 6953 SET_EXPECT(INTERNET_STATUS_REQUEST_COMPLETE); 6954 SET_OPTIONAL(INTERNET_STATUS_COOKIE_SENT); 6955 6956 res = HttpSendRequestA(req, NULL, 0, NULL, 0); 6957 ok(!res && GetLastError() == ERROR_IO_PENDING, "HttpSendRequest failed: %u\n", GetLastError()); 6958 6959 WaitForSingleObject(complete_event, INFINITE); 6960 ok(req_error == ERROR_SUCCESS, "req_error = %d\n", req_error); 6961 6962 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTING_TO_SERVER, 2); 6963 CHECK_NOTIFIED2(INTERNET_STATUS_CONNECTED_TO_SERVER, 2); 6964 CHECK_NOTIFIED(INTERNET_STATUS_CLOSING_CONNECTION); 6965 CHECK_NOTIFIED(INTERNET_STATUS_CONNECTION_CLOSED); 6966 CHECK_NOTIFIED(INTERNET_STATUS_SENDING_REQUEST); 6967 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_SENT); 6968 CHECK_NOTIFIED(INTERNET_STATUS_RECEIVING_RESPONSE); 6969 CHECK_NOTIFIED(INTERNET_STATUS_RESPONSE_RECEIVED); 6970 CHECK_NOTIFIED(INTERNET_STATUS_REQUEST_COMPLETE); 6971 CLEAR_NOTIFIED(INTERNET_STATUS_COOKIE_SENT); 6972 6973 test_request_flags(req, 0); 6974 test_secflags_option(req, SECURITY_FLAG_SECURE|SECURITY_FLAG_IGNORE_UNKNOWN_CA|SECURITY_FLAG_STRENGTH_STRONG 6975 |SECURITY_FLAG_IGNORE_REVOCATION|_SECURITY_FLAG_CERT_INVALID_CA, 0); 6976 6977 res = InternetReadFile(req, buf, sizeof(buf), &size); 6978 ok(res, "InternetReadFile failed: %u\n", GetLastError()); 6979 ok(size, "size = 0\n"); 6980 6981 close_async_handle(ses, 2); 6982 6983 test_security_info("http://test.winehq.com/data/some_file.html?q", ERROR_INTERNET_ITEM_NOT_FOUND, 0); 6984 test_security_info("file:///c:/dir/file.txt", ERROR_INTERNET_ITEM_NOT_FOUND, 0); 6985 test_security_info("xxx:///c:/dir/file.txt", ERROR_INTERNET_ITEM_NOT_FOUND, 0); 6986 } 6987 6988 static void test_secure_connection(void) 6989 { 6990 static const WCHAR gizmo5[] = {'G','i','z','m','o','5',0}; 6991 static const WCHAR testsite[] = {'t','e','s','t','.','w','i','n','e','h','q','.','o','r','g',0}; 6992 static const WCHAR get[] = {'G','E','T',0}; 6993 static const WCHAR testpage[] = {'/','t','e','s','t','s','/','h','e','l','l','o','.','h','t','m','l',0}; 6994 HINTERNET ses, con, req; 6995 DWORD size, size2, flags, err; 6996 INTERNET_CERTIFICATE_INFOA *certificate_structA = NULL; 6997 INTERNET_CERTIFICATE_INFOW *certificate_structW = NULL; 6998 char certstr1[512], certstr2[512]; 6999 BOOL ret; 7000 7001 ses = InternetOpenA("Gizmo5", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0); 7002 ok(ses != NULL, "InternetOpen failed\n"); 7003 7004 con = InternetConnectA(ses, "test.winehq.org", 7005 INTERNET_DEFAULT_HTTPS_PORT, NULL, NULL, 7006 INTERNET_SERVICE_HTTP, 0, 0); 7007 ok(con != NULL, "InternetConnect failed\n"); 7008 7009 req = HttpOpenRequestA(con, "GET", "/tests/hello.html", NULL, NULL, NULL, 7010 INTERNET_FLAG_SECURE, 0); 7011 ok(req != NULL, "HttpOpenRequest failed\n"); 7012 7013 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 7014 err = GetLastError(); 7015 ok(ret || broken(err == ERROR_INTERNET_CANNOT_CONNECT) || 7016 broken(err == ERROR_INTERNET_SECURITY_CHANNEL_ERROR), "HttpSendRequest failed: %u\n", err); 7017 if (!ret) 7018 { 7019 win_skip("Cannot connect to https.\n"); 7020 if (err == ERROR_INTERNET_SECURITY_CHANNEL_ERROR) https_support = FALSE; 7021 goto done; 7022 } 7023 7024 size = sizeof(flags); 7025 ret = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_FLAGS, &flags, &size); 7026 ok(ret, "InternetQueryOption failed: %d\n", GetLastError()); 7027 ok(flags & SECURITY_FLAG_SECURE, "expected secure flag to be set\n"); 7028 7029 test_cert_struct(req, &test_winehq_org_cert); 7030 7031 /* Querying the same option through InternetQueryOptionW still results in 7032 * ASCII strings being returned. 7033 */ 7034 size = 0; 7035 ret = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, 7036 NULL, &size); 7037 ok(ret || GetLastError() == ERROR_INSUFFICIENT_BUFFER, "InternetQueryOption failed: %d\n", GetLastError()); 7038 ok(size == sizeof(INTERNET_CERTIFICATE_INFOW), "size = %d\n", size); 7039 certificate_structW = HeapAlloc(GetProcessHeap(), 0, size); 7040 ret = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, 7041 certificate_structW, &size); 7042 certificate_structA = (INTERNET_CERTIFICATE_INFOA *)certificate_structW; 7043 ok(ret, "InternetQueryOption failed: %d\n", GetLastError()); 7044 if (ret) 7045 { 7046 ok(certificate_structA->lpszSubjectInfo && 7047 strlen(certificate_structA->lpszSubjectInfo) > 1, 7048 "expected a non-empty subject name\n"); 7049 ok(certificate_structA->lpszIssuerInfo && 7050 strlen(certificate_structA->lpszIssuerInfo) > 1, 7051 "expected a non-empty issuer name\n"); 7052 ok(!certificate_structA->lpszSignatureAlgName, 7053 "unexpected signature algorithm name\n"); 7054 ok(!certificate_structA->lpszEncryptionAlgName, 7055 "unexpected encryption algorithm name\n"); 7056 ok(!certificate_structA->lpszProtocolName, 7057 "unexpected protocol name\n"); 7058 ok(certificate_structA->dwKeySize, "expected a non-zero key size\n"); 7059 release_cert_info(certificate_structA); 7060 } 7061 HeapFree(GetProcessHeap(), 0, certificate_structW); 7062 7063 SetLastError(0xdeadbeef); 7064 size = sizeof(certstr1); 7065 ret = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE, certstr1, &size); 7066 ok(ret && GetLastError() == ERROR_SUCCESS, "InternetQueryOption failed: %d\n", GetLastError()); 7067 7068 SetLastError(0xdeadbeef); 7069 size2 = sizeof(certstr2); 7070 ret = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_CERTIFICATE, certstr2, &size2); 7071 ok(ret && GetLastError() == ERROR_SUCCESS, "InternetQueryOption failed: %d\n", GetLastError()); 7072 7073 ok(size == size2, "expected same size\n"); 7074 ok(!strcmp(certstr1, certstr2), "expected same string\n"); 7075 7076 InternetCloseHandle(req); 7077 InternetCloseHandle(con); 7078 InternetCloseHandle(ses); 7079 7080 /* Repeating the tests with the W functions has the same result: */ 7081 ses = InternetOpenW(gizmo5, INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0); 7082 ok(ses != NULL, "InternetOpen failed\n"); 7083 7084 con = InternetConnectW(ses, testsite, 7085 INTERNET_DEFAULT_HTTPS_PORT, NULL, NULL, 7086 INTERNET_SERVICE_HTTP, 0, 0); 7087 ok(con != NULL, "InternetConnect failed\n"); 7088 7089 req = HttpOpenRequestW(con, get, testpage, NULL, NULL, NULL, 7090 INTERNET_FLAG_SECURE|INTERNET_FLAG_RELOAD, 0); 7091 ok(req != NULL, "HttpOpenRequest failed\n"); 7092 7093 ret = HttpSendRequestA(req, NULL, 0, NULL, 0); 7094 ok(ret, "HttpSendRequest failed: %d\n", GetLastError()); 7095 7096 size = sizeof(flags); 7097 ret = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_FLAGS, &flags, &size); 7098 ok(ret, "InternetQueryOption failed: %d\n", GetLastError()); 7099 ok(flags & SECURITY_FLAG_SECURE, "expected secure flag to be set, got %x\n", flags); 7100 7101 ret = InternetQueryOptionA(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, 7102 NULL, &size); 7103 ok(ret || GetLastError() == ERROR_INSUFFICIENT_BUFFER, "InternetQueryOption failed: %d\n", GetLastError()); 7104 ok(size == sizeof(INTERNET_CERTIFICATE_INFOA), "size = %d\n", size); 7105 certificate_structA = HeapAlloc(GetProcessHeap(), 0, size); 7106 ret = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, 7107 certificate_structA, &size); 7108 ok(ret, "InternetQueryOption failed: %d\n", GetLastError()); 7109 if (ret) 7110 { 7111 ok(certificate_structA->lpszSubjectInfo && 7112 strlen(certificate_structA->lpszSubjectInfo) > 1, 7113 "expected a non-empty subject name\n"); 7114 ok(certificate_structA->lpszIssuerInfo && 7115 strlen(certificate_structA->lpszIssuerInfo) > 1, 7116 "expected a non-empty issuer name\n"); 7117 ok(!certificate_structA->lpszSignatureAlgName, 7118 "unexpected signature algorithm name\n"); 7119 ok(!certificate_structA->lpszEncryptionAlgName, 7120 "unexpected encryption algorithm name\n"); 7121 ok(!certificate_structA->lpszProtocolName, 7122 "unexpected protocol name\n"); 7123 ok(certificate_structA->dwKeySize, "expected a non-zero key size\n"); 7124 release_cert_info(certificate_structA); 7125 } 7126 HeapFree(GetProcessHeap(), 0, certificate_structA); 7127 7128 /* Again, querying the same option through InternetQueryOptionW still 7129 * results in ASCII strings being returned. 7130 */ 7131 size = 0; 7132 ret = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, 7133 NULL, &size); 7134 ok(ret || GetLastError() == ERROR_INSUFFICIENT_BUFFER, "InternetQueryOption failed: %d\n", GetLastError()); 7135 ok(size == sizeof(INTERNET_CERTIFICATE_INFOW), "size = %d\n", size); 7136 certificate_structW = HeapAlloc(GetProcessHeap(), 0, size); 7137 ret = InternetQueryOptionW(req, INTERNET_OPTION_SECURITY_CERTIFICATE_STRUCT, 7138 certificate_structW, &size); 7139 certificate_structA = (INTERNET_CERTIFICATE_INFOA *)certificate_structW; 7140 ok(ret, "InternetQueryOption failed: %d\n", GetLastError()); 7141 if (ret) 7142 { 7143 ok(certificate_structA->lpszSubjectInfo && 7144 strlen(certificate_structA->lpszSubjectInfo) > 1, 7145 "expected a non-empty subject name\n"); 7146 ok(certificate_structA->lpszIssuerInfo && 7147 strlen(certificate_structA->lpszIssuerInfo) > 1, 7148 "expected a non-empty issuer name\n"); 7149 ok(!certificate_structA->lpszSignatureAlgName, 7150 "unexpected signature algorithm name\n"); 7151 ok(!certificate_structA->lpszEncryptionAlgName, 7152 "unexpected encryption algorithm name\n"); 7153 ok(!certificate_structA->lpszProtocolName, 7154 "unexpected protocol name\n"); 7155 ok(certificate_structA->dwKeySize, "expected a non-zero key size\n"); 7156 release_cert_info(certificate_structA); 7157 } 7158 HeapFree(GetProcessHeap(), 0, certificate_structW); 7159 7160 done: 7161 InternetCloseHandle(req); 7162 InternetCloseHandle(con); 7163 InternetCloseHandle(ses); 7164 } 7165 7166 static void test_user_agent_header(void) 7167 { 7168 HINTERNET ses, con, req; 7169 DWORD size, err; 7170 char buffer[64]; 7171 BOOL ret; 7172 7173 ses = InternetOpenA("Gizmo5", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0); 7174 ok(ses != NULL, "InternetOpen failed\n"); 7175 7176 con = InternetConnectA(ses, "test.winehq.org", 80, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 7177 ok(con != NULL, "InternetConnect failed\n"); 7178 7179 req = HttpOpenRequestA(con, "GET", "/tests/hello.html", "HTTP/1.0", NULL, NULL, 0, 0); 7180 ok(req != NULL, "HttpOpenRequest failed\n"); 7181 7182 size = sizeof(buffer); 7183 ret = HttpQueryInfoA(req, HTTP_QUERY_USER_AGENT | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 7184 err = GetLastError(); 7185 ok(!ret, "HttpQueryInfo succeeded\n"); 7186 ok(err == ERROR_HTTP_HEADER_NOT_FOUND, "expected ERROR_HTTP_HEADER_NOT_FOUND, got %u\n", err); 7187 7188 ret = HttpAddRequestHeadersA(req, "User-Agent: Gizmo Project\r\n", ~0u, HTTP_ADDREQ_FLAG_ADD_IF_NEW); 7189 ok(ret, "HttpAddRequestHeaders succeeded\n"); 7190 7191 size = sizeof(buffer); 7192 ret = HttpQueryInfoA(req, HTTP_QUERY_USER_AGENT | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 7193 err = GetLastError(); 7194 ok(ret, "HttpQueryInfo failed\n"); 7195 7196 InternetCloseHandle(req); 7197 7198 req = HttpOpenRequestA(con, "GET", "/", "HTTP/1.0", NULL, NULL, 0, 0); 7199 ok(req != NULL, "HttpOpenRequest failed\n"); 7200 7201 size = sizeof(buffer); 7202 ret = HttpQueryInfoA(req, HTTP_QUERY_ACCEPT | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 7203 err = GetLastError(); 7204 ok(!ret, "HttpQueryInfo succeeded\n"); 7205 ok(err == ERROR_HTTP_HEADER_NOT_FOUND, "expected ERROR_HTTP_HEADER_NOT_FOUND, got %u\n", err); 7206 7207 ret = HttpAddRequestHeadersA(req, "Accept: audio/*, image/*, text/*\r\nUser-Agent: Gizmo Project\r\n", ~0u, HTTP_ADDREQ_FLAG_ADD_IF_NEW); 7208 ok(ret, "HttpAddRequestHeaders failed\n"); 7209 7210 buffer[0] = 0; 7211 size = sizeof(buffer); 7212 ret = HttpQueryInfoA(req, HTTP_QUERY_ACCEPT | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 7213 ok(ret, "HttpQueryInfo failed: %u\n", GetLastError()); 7214 ok(!strcmp(buffer, "audio/*, image/*, text/*"), "got '%s' expected 'audio/*, image/*, text/*'\n", buffer); 7215 7216 InternetCloseHandle(req); 7217 InternetCloseHandle(con); 7218 InternetCloseHandle(ses); 7219 } 7220 7221 static void test_bogus_accept_types_array(void) 7222 { 7223 HINTERNET ses, con, req; 7224 static const char *types[] = { (const char *)6240, "*/*", "%p", "", (const char *)0xffffffff, "*/*", NULL }; 7225 DWORD size, error; 7226 char buffer[32]; 7227 BOOL ret; 7228 7229 ses = InternetOpenA("MERONG(0.9/;p)", INTERNET_OPEN_TYPE_DIRECT, "", "", 0); 7230 con = InternetConnectA(ses, "www.winehq.org", 80, NULL, NULL, INTERNET_SERVICE_HTTP, 0, 0); 7231 req = HttpOpenRequestA(con, "POST", "/post/post_action.php", "HTTP/1.0", "", types, INTERNET_FLAG_FORMS_SUBMIT, 0); 7232 7233 ok(req != NULL, "HttpOpenRequest failed: %u\n", GetLastError()); 7234 7235 buffer[0] = 0; 7236 size = sizeof(buffer); 7237 SetLastError(0xdeadbeef); 7238 ret = HttpQueryInfoA(req, HTTP_QUERY_ACCEPT | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 7239 error = GetLastError(); 7240 ok(!ret || broken(ret), "HttpQueryInfo succeeded\n"); 7241 if (!ret) ok(error == ERROR_HTTP_HEADER_NOT_FOUND, "expected ERROR_HTTP_HEADER_NOT_FOUND, got %u\n", error); 7242 ok(broken(!strcmp(buffer, ", */*, %p, , , */*")) /* IE6 */ || 7243 broken(!strcmp(buffer, "*/*, %p, */*")) /* IE7/8 */ || 7244 !strcmp(buffer, ""), "got '%s' expected ''\n", buffer); 7245 7246 InternetCloseHandle(req); 7247 InternetCloseHandle(con); 7248 InternetCloseHandle(ses); 7249 } 7250 7251 struct context 7252 { 7253 HANDLE event; 7254 HINTERNET req; 7255 }; 7256 7257 static void WINAPI cb(HINTERNET handle, DWORD_PTR context, DWORD status, LPVOID info, DWORD size) 7258 { 7259 INTERNET_ASYNC_RESULT *result = info; 7260 struct context *ctx = (struct context *)context; 7261 7262 if(winetest_debug > 1) 7263 trace("%p 0x%08lx %u %p 0x%08x\n", handle, context, status, info, size); 7264 7265 switch(status) { 7266 case INTERNET_STATUS_REQUEST_COMPLETE: 7267 trace("request handle: 0x%08lx\n", result->dwResult); 7268 ctx->req = (HINTERNET)result->dwResult; 7269 SetEvent(ctx->event); 7270 break; 7271 case INTERNET_STATUS_HANDLE_CLOSING: { 7272 DWORD type = INTERNET_HANDLE_TYPE_CONNECT_HTTP, size = sizeof(type); 7273 7274 if (InternetQueryOptionA(handle, INTERNET_OPTION_HANDLE_TYPE, &type, &size)) 7275 ok(type != INTERNET_HANDLE_TYPE_CONNECT_HTTP, "unexpected callback\n"); 7276 SetEvent(ctx->event); 7277 break; 7278 } 7279 case INTERNET_STATUS_NAME_RESOLVED: 7280 case INTERNET_STATUS_CONNECTING_TO_SERVER: 7281 case INTERNET_STATUS_CONNECTED_TO_SERVER: { 7282 char *str = info; 7283 ok(str[0] && str[1], "Got string: %s\n", str); 7284 ok(size == strlen(str)+1, "unexpected size %u\n", size); 7285 } 7286 } 7287 } 7288 7289 static void test_open_url_async(void) 7290 { 7291 BOOL ret; 7292 HINTERNET ses, req; 7293 DWORD size, error; 7294 struct context ctx; 7295 ULONG type; 7296 7297 /* Collect all existing persistent connections */ 7298 ret = InternetSetOptionA(NULL, INTERNET_OPTION_SETTINGS_CHANGED, NULL, 0); 7299 ok(ret, "InternetSetOption(INTERNET_OPTION_END_BROWSER_SESSION) failed: %u\n", GetLastError()); 7300 7301 /* 7302 * Some versions of IE6 fail those tests. They pass some notification data as UNICODE string, while 7303 * other versions never do. They also hang of following tests. We disable it for everything older 7304 * than IE7. 7305 */ 7306 if(!is_ie7plus) 7307 return; 7308 7309 ctx.req = NULL; 7310 ctx.event = CreateEventA(NULL, TRUE, FALSE, "Z:_home_hans_jaman-installer.exe_ev1"); 7311 7312 ses = InternetOpenA("AdvancedInstaller", 0, NULL, NULL, INTERNET_FLAG_ASYNC); 7313 ok(ses != NULL, "InternetOpen failed\n"); 7314 7315 SetLastError(0xdeadbeef); 7316 ret = InternetSetOptionA(NULL, INTERNET_OPTION_CALLBACK, &cb, sizeof(DWORD_PTR)); 7317 error = GetLastError(); 7318 ok(!ret, "InternetSetOptionA succeeded\n"); 7319 ok(error == ERROR_INTERNET_INCORRECT_HANDLE_TYPE, "got %u expected ERROR_INTERNET_INCORRECT_HANDLE_TYPE\n", error); 7320 7321 ret = InternetSetOptionA(ses, INTERNET_OPTION_CALLBACK, &cb, sizeof(DWORD_PTR)); 7322 error = GetLastError(); 7323 ok(!ret, "InternetSetOptionA failed\n"); 7324 ok(error == ERROR_INTERNET_OPTION_NOT_SETTABLE, "got %u expected ERROR_INTERNET_OPTION_NOT_SETTABLE\n", error); 7325 7326 pInternetSetStatusCallbackW(ses, cb); 7327 ResetEvent(ctx.event); 7328 7329 req = InternetOpenUrlA(ses, "http://test.winehq.org", NULL, 0, 0, (DWORD_PTR)&ctx); 7330 ok(!req && GetLastError() == ERROR_IO_PENDING, "InternetOpenUrl failed\n"); 7331 7332 WaitForSingleObject(ctx.event, INFINITE); 7333 7334 type = 0; 7335 size = sizeof(type); 7336 ret = InternetQueryOptionA(ctx.req, INTERNET_OPTION_HANDLE_TYPE, &type, &size); 7337 ok(ret, "InternetQueryOption failed: %u\n", GetLastError()); 7338 ok(type == INTERNET_HANDLE_TYPE_HTTP_REQUEST, 7339 "expected INTERNET_HANDLE_TYPE_HTTP_REQUEST, got %u\n", type); 7340 7341 size = 0; 7342 ret = HttpQueryInfoA(ctx.req, HTTP_QUERY_RAW_HEADERS_CRLF, NULL, &size, NULL); 7343 ok(!ret && GetLastError() == ERROR_INSUFFICIENT_BUFFER, "HttpQueryInfo failed\n"); 7344 ok(size > 0, "expected size > 0\n"); 7345 7346 ResetEvent(ctx.event); 7347 InternetCloseHandle(ctx.req); 7348 WaitForSingleObject(ctx.event, INFINITE); 7349 7350 InternetCloseHandle(ses); 7351 CloseHandle(ctx.event); 7352 } 7353 7354 enum api 7355 { 7356 internet_connect = 1, 7357 http_open_request, 7358 http_send_request_ex, 7359 internet_writefile, 7360 http_end_request, 7361 internet_close_handle 7362 }; 7363 7364 struct notification 7365 { 7366 enum api function; /* api responsible for notification */ 7367 unsigned int status; /* status received */ 7368 BOOL async; /* delivered from another thread? */ 7369 BOOL todo; 7370 BOOL optional; 7371 }; 7372 7373 struct info 7374 { 7375 enum api function; 7376 const struct notification *test; 7377 unsigned int count; 7378 unsigned int index; 7379 HANDLE wait; 7380 DWORD thread; 7381 unsigned int line; 7382 DWORD expect_result; 7383 BOOL is_aborted; 7384 }; 7385 7386 static CRITICAL_SECTION notification_cs; 7387 7388 static void CALLBACK check_notification( HINTERNET handle, DWORD_PTR context, DWORD status, LPVOID buffer, DWORD buflen ) 7389 { 7390 BOOL status_ok, function_ok; 7391 struct info *info = (struct info *)context; 7392 unsigned int i; 7393 7394 EnterCriticalSection( ¬ification_cs ); 7395 7396 if(info->is_aborted) { 7397 LeaveCriticalSection(¬ification_cs); 7398 return; 7399 } 7400 7401 if (status == INTERNET_STATUS_HANDLE_CREATED) 7402 { 7403 DWORD size = sizeof(struct info *); 7404 HttpQueryInfoA( handle, INTERNET_OPTION_CONTEXT_VALUE, &info, &size, 0 ); 7405 }else if(status == INTERNET_STATUS_REQUEST_COMPLETE) { 7406 INTERNET_ASYNC_RESULT *ar = (INTERNET_ASYNC_RESULT*)buffer; 7407 7408 ok(buflen == sizeof(*ar), "unexpected buflen = %d\n", buflen); 7409 if(info->expect_result == ERROR_SUCCESS) { 7410 ok(ar->dwResult == 1, "ar->dwResult = %ld, expected 1\n", ar->dwResult); 7411 }else { 7412 ok(!ar->dwResult, "ar->dwResult = %ld, expected 1\n", ar->dwResult); 7413 ok(ar->dwError == info->expect_result, "ar->dwError = %d, expected %d\n", ar->dwError, info->expect_result); 7414 } 7415 } 7416 7417 i = info->index; 7418 if (i >= info->count) 7419 { 7420 LeaveCriticalSection( ¬ification_cs ); 7421 return; 7422 } 7423 7424 while (info->test[i].status != status && 7425 (info->test[i].optional || info->test[i].todo) && 7426 i < info->count - 1 && 7427 info->test[i].function == info->test[i + 1].function) 7428 { 7429 i++; 7430 } 7431 7432 status_ok = (info->test[i].status == status); 7433 function_ok = (info->test[i].function == info->function); 7434 7435 if (!info->test[i].todo) 7436 { 7437 ok( status_ok, "%u: expected status %u got %u\n", info->line, info->test[i].status, status ); 7438 ok( function_ok, "%u: expected function %u got %u\n", info->line, info->test[i].function, info->function ); 7439 7440 if (info->test[i].async) 7441 ok(info->thread != GetCurrentThreadId(), "%u: expected thread %u got %u\n", 7442 info->line, info->thread, GetCurrentThreadId()); 7443 } 7444 else 7445 { 7446 todo_wine ok( status_ok, "%u: expected status %u got %u\n", info->line, info->test[i].status, status ); 7447 if (status_ok) 7448 todo_wine ok( function_ok, "%u: expected function %u got %u\n", info->line, info->test[i].function, info->function ); 7449 } 7450 if (i == info->count - 1 || info->test[i].function != info->test[i + 1].function) SetEvent( info->wait ); 7451 info->index = i+1; 7452 7453 LeaveCriticalSection( ¬ification_cs ); 7454 } 7455 7456 static void setup_test( struct info *info, enum api function, unsigned int line, DWORD expect_result ) 7457 { 7458 info->function = function; 7459 info->line = line; 7460 info->expect_result = expect_result; 7461 } 7462 7463 struct notification_data 7464 { 7465 const struct notification *test; 7466 const unsigned int count; 7467 const char *method; 7468 const char *host; 7469 const char *path; 7470 const char *data; 7471 BOOL expect_conn_failure; 7472 }; 7473 7474 static const struct notification async_send_request_ex_test[] = 7475 { 7476 { internet_connect, INTERNET_STATUS_HANDLE_CREATED, FALSE }, 7477 { http_open_request, INTERNET_STATUS_HANDLE_CREATED, FALSE }, 7478 { http_send_request_ex, INTERNET_STATUS_DETECTING_PROXY, TRUE, FALSE, TRUE }, 7479 { http_send_request_ex, INTERNET_STATUS_COOKIE_SENT, TRUE, FALSE, TRUE }, 7480 { http_send_request_ex, INTERNET_STATUS_RESOLVING_NAME, TRUE, FALSE, TRUE }, 7481 { http_send_request_ex, INTERNET_STATUS_NAME_RESOLVED, TRUE, FALSE, TRUE }, 7482 { http_send_request_ex, INTERNET_STATUS_CONNECTING_TO_SERVER, TRUE }, 7483 { http_send_request_ex, INTERNET_STATUS_CONNECTED_TO_SERVER, TRUE }, 7484 { http_send_request_ex, INTERNET_STATUS_SENDING_REQUEST, TRUE }, 7485 { http_send_request_ex, INTERNET_STATUS_REQUEST_SENT, TRUE }, 7486 { http_send_request_ex, INTERNET_STATUS_REQUEST_COMPLETE, TRUE }, 7487 { internet_writefile, INTERNET_STATUS_SENDING_REQUEST, FALSE }, 7488 { internet_writefile, INTERNET_STATUS_REQUEST_SENT, FALSE }, 7489 { http_end_request, INTERNET_STATUS_RECEIVING_RESPONSE, TRUE }, 7490 { http_end_request, INTERNET_STATUS_RESPONSE_RECEIVED, TRUE }, 7491 { http_end_request, INTERNET_STATUS_REQUEST_COMPLETE, TRUE }, 7492 { internet_close_handle, INTERNET_STATUS_CLOSING_CONNECTION, FALSE, FALSE, TRUE }, 7493 { internet_close_handle, INTERNET_STATUS_CONNECTION_CLOSED, FALSE, FALSE, TRUE }, 7494 { internet_close_handle, INTERNET_STATUS_HANDLE_CLOSING, FALSE, }, 7495 { internet_close_handle, INTERNET_STATUS_HANDLE_CLOSING, FALSE, } 7496 }; 7497 7498 static const struct notification async_send_request_ex_test2[] = 7499 { 7500 { internet_connect, INTERNET_STATUS_HANDLE_CREATED, FALSE }, 7501 { http_open_request, INTERNET_STATUS_HANDLE_CREATED, FALSE }, 7502 { http_send_request_ex, INTERNET_STATUS_DETECTING_PROXY, TRUE, FALSE, TRUE }, 7503 { http_send_request_ex, INTERNET_STATUS_COOKIE_SENT, TRUE, FALSE, TRUE }, 7504 { http_send_request_ex, INTERNET_STATUS_RESOLVING_NAME, TRUE, FALSE, TRUE }, 7505 { http_send_request_ex, INTERNET_STATUS_NAME_RESOLVED, TRUE, FALSE, TRUE }, 7506 { http_send_request_ex, INTERNET_STATUS_CONNECTING_TO_SERVER, TRUE, TRUE }, 7507 { http_send_request_ex, INTERNET_STATUS_CONNECTED_TO_SERVER, TRUE, TRUE }, 7508 { http_send_request_ex, INTERNET_STATUS_SENDING_REQUEST, TRUE }, 7509 { http_send_request_ex, INTERNET_STATUS_REQUEST_SENT, TRUE }, 7510 { http_send_request_ex, INTERNET_STATUS_REQUEST_COMPLETE, TRUE }, 7511 { http_end_request, INTERNET_STATUS_RECEIVING_RESPONSE, TRUE }, 7512 { http_end_request, INTERNET_STATUS_RESPONSE_RECEIVED, TRUE }, 7513 { http_end_request, INTERNET_STATUS_REQUEST_COMPLETE, TRUE }, 7514 { internet_close_handle, INTERNET_STATUS_CLOSING_CONNECTION, FALSE, FALSE, TRUE }, 7515 { internet_close_handle, INTERNET_STATUS_CONNECTION_CLOSED, FALSE, FALSE, TRUE }, 7516 { internet_close_handle, INTERNET_STATUS_HANDLE_CLOSING, FALSE, }, 7517 { internet_close_handle, INTERNET_STATUS_HANDLE_CLOSING, FALSE, } 7518 }; 7519 7520 static const struct notification async_send_request_ex_resolve_failure_test[] = 7521 { 7522 { internet_connect, INTERNET_STATUS_HANDLE_CREATED, FALSE }, 7523 { http_open_request, INTERNET_STATUS_HANDLE_CREATED, FALSE }, 7524 { http_send_request_ex, INTERNET_STATUS_DETECTING_PROXY, TRUE, FALSE, TRUE }, 7525 { http_send_request_ex, INTERNET_STATUS_RESOLVING_NAME, TRUE }, 7526 { http_send_request_ex, INTERNET_STATUS_DETECTING_PROXY, TRUE, FALSE, TRUE }, 7527 { http_send_request_ex, INTERNET_STATUS_REQUEST_COMPLETE, TRUE }, 7528 { http_end_request, INTERNET_STATUS_REQUEST_COMPLETE, TRUE }, 7529 { internet_close_handle, INTERNET_STATUS_CLOSING_CONNECTION, FALSE, FALSE, TRUE }, 7530 { internet_close_handle, INTERNET_STATUS_CONNECTION_CLOSED, FALSE, FALSE, TRUE }, 7531 { internet_close_handle, INTERNET_STATUS_HANDLE_CLOSING, FALSE, }, 7532 { internet_close_handle, INTERNET_STATUS_HANDLE_CLOSING, FALSE, } 7533 }; 7534 7535 static const struct notification async_send_request_ex_chunked_test[] = 7536 { 7537 { internet_connect, INTERNET_STATUS_HANDLE_CREATED }, 7538 { http_open_request, INTERNET_STATUS_HANDLE_CREATED }, 7539 { http_send_request_ex, INTERNET_STATUS_DETECTING_PROXY, TRUE, FALSE, TRUE }, 7540 { http_send_request_ex, INTERNET_STATUS_COOKIE_SENT, TRUE, FALSE, TRUE }, 7541 { http_send_request_ex, INTERNET_STATUS_RESOLVING_NAME, TRUE, FALSE, TRUE }, 7542 { http_send_request_ex, INTERNET_STATUS_NAME_RESOLVED, TRUE, FALSE, TRUE }, 7543 { http_send_request_ex, INTERNET_STATUS_CONNECTING_TO_SERVER, TRUE }, 7544 { http_send_request_ex, INTERNET_STATUS_CONNECTED_TO_SERVER, TRUE }, 7545 { http_send_request_ex, INTERNET_STATUS_SENDING_REQUEST, TRUE }, 7546 { http_send_request_ex, INTERNET_STATUS_REQUEST_SENT, TRUE }, 7547 { http_send_request_ex, INTERNET_STATUS_REQUEST_COMPLETE, TRUE }, 7548 { http_end_request, INTERNET_STATUS_RECEIVING_RESPONSE, TRUE }, 7549 { http_end_request, INTERNET_STATUS_RESPONSE_RECEIVED, TRUE }, 7550 { http_end_request, INTERNET_STATUS_REQUEST_COMPLETE, TRUE }, 7551 { internet_close_handle, INTERNET_STATUS_CLOSING_CONNECTION }, 7552 { internet_close_handle, INTERNET_STATUS_CONNECTION_CLOSED }, 7553 { internet_close_handle, INTERNET_STATUS_HANDLE_CLOSING }, 7554 { internet_close_handle, INTERNET_STATUS_HANDLE_CLOSING } 7555 }; 7556 7557 static const struct notification_data notification_data[] = { 7558 { 7559 async_send_request_ex_chunked_test, 7560 ARRAY_SIZE(async_send_request_ex_chunked_test), 7561 "GET", 7562 "test.winehq.org", 7563 "tests/data.php" 7564 }, 7565 { 7566 async_send_request_ex_test, 7567 ARRAY_SIZE(async_send_request_ex_test), 7568 "POST", 7569 "test.winehq.org", 7570 "tests/post.php", 7571 "Public ID=codeweavers" 7572 }, 7573 { 7574 async_send_request_ex_test2, 7575 ARRAY_SIZE(async_send_request_ex_test2), 7576 "POST", 7577 "test.winehq.org", 7578 "tests/post.php" 7579 }, 7580 { 7581 async_send_request_ex_resolve_failure_test, 7582 ARRAY_SIZE(async_send_request_ex_resolve_failure_test), 7583 "GET", 7584 "brokenhost", 7585 "index.html", 7586 NULL, 7587 TRUE 7588 } 7589 }; 7590 7591 static void test_async_HttpSendRequestEx(const struct notification_data *nd) 7592 { 7593 BOOL ret; 7594 HINTERNET ses, req, con; 7595 struct info info; 7596 DWORD size, written, error; 7597 INTERNET_BUFFERSA b; 7598 static const char *accept[2] = {"*/*", NULL}; 7599 char buffer[32]; 7600 7601 trace("Async HttpSendRequestEx test (%s %s)\n", nd->method, nd->host); 7602 7603 InitializeCriticalSection( ¬ification_cs ); 7604 7605 info.test = nd->test; 7606 info.count = nd->count; 7607 info.index = 0; 7608 info.wait = CreateEventW( NULL, FALSE, FALSE, NULL ); 7609 info.thread = GetCurrentThreadId(); 7610 info.is_aborted = FALSE; 7611 7612 ses = InternetOpenA( "winetest", 0, NULL, NULL, INTERNET_FLAG_ASYNC ); 7613 ok( ses != NULL, "InternetOpen failed\n" ); 7614 7615 pInternetSetStatusCallbackA( ses, check_notification ); 7616 7617 setup_test( &info, internet_connect, __LINE__, ERROR_SUCCESS ); 7618 con = InternetConnectA( ses, nd->host, 80, NULL, NULL, INTERNET_SERVICE_HTTP, 0, (DWORD_PTR)&info ); 7619 ok( con != NULL, "InternetConnect failed %u\n", GetLastError() ); 7620 7621 WaitForSingleObject( info.wait, 10000 ); 7622 7623 setup_test( &info, http_open_request, __LINE__, ERROR_SUCCESS ); 7624 req = HttpOpenRequestA( con, nd->method, nd->path, NULL, NULL, accept, 0, (DWORD_PTR)&info ); 7625 ok( req != NULL, "HttpOpenRequest failed %u\n", GetLastError() ); 7626 7627 WaitForSingleObject( info.wait, 10000 ); 7628 7629 if(nd->data) { 7630 memset( &b, 0, sizeof(INTERNET_BUFFERSA) ); 7631 b.dwStructSize = sizeof(INTERNET_BUFFERSA); 7632 b.lpcszHeader = "Content-Type: application/x-www-form-urlencoded"; 7633 b.dwHeadersLength = strlen( b.lpcszHeader ); 7634 b.dwBufferTotal = nd->data ? strlen( nd->data ) : 0; 7635 } 7636 7637 setup_test( &info, http_send_request_ex, __LINE__, 7638 nd->expect_conn_failure ? ERROR_INTERNET_NAME_NOT_RESOLVED : ERROR_SUCCESS ); 7639 ret = HttpSendRequestExA( req, nd->data ? &b : NULL, NULL, 0x28, 0 ); 7640 ok( !ret && GetLastError() == ERROR_IO_PENDING, "HttpSendRequestExA failed %d %u\n", ret, GetLastError() ); 7641 7642 error = WaitForSingleObject( info.wait, 10000 ); 7643 if(error != WAIT_OBJECT_0) { 7644 skip("WaitForSingleObject returned %d, assuming DNS problem\n", error); 7645 info.is_aborted = TRUE; 7646 goto abort; 7647 } 7648 7649 size = sizeof(buffer); 7650 SetLastError( 0xdeadbeef ); 7651 ret = HttpQueryInfoA( req, HTTP_QUERY_CONTENT_ENCODING, buffer, &size, 0 ); 7652 error = GetLastError(); 7653 ok( !ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 7654 if(nd->expect_conn_failure) { 7655 ok(error == ERROR_HTTP_HEADER_NOT_FOUND, "expected ERROR_HTTP_HEADER_NOT_FOUND got %u\n", error ); 7656 }else { 7657 todo_wine 7658 ok(error == ERROR_INTERNET_INCORRECT_HANDLE_STATE, 7659 "expected ERROR_INTERNET_INCORRECT_HANDLE_STATE got %u\n", error ); 7660 } 7661 7662 if (nd->data) 7663 { 7664 written = 0; 7665 size = strlen( nd->data ); 7666 setup_test( &info, internet_writefile, __LINE__, ERROR_SUCCESS ); 7667 ret = InternetWriteFile( req, nd->data, size, &written ); 7668 ok( ret, "InternetWriteFile failed %u\n", GetLastError() ); 7669 ok( written == size, "expected %u got %u\n", written, size ); 7670 7671 WaitForSingleObject( info.wait, 10000 ); 7672 7673 SetLastError( 0xdeadbeef ); 7674 ret = HttpEndRequestA( req, (void *)nd->data, 0x28, 0 ); 7675 error = GetLastError(); 7676 ok( !ret, "HttpEndRequestA succeeded\n" ); 7677 ok( error == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER got %u\n", error ); 7678 } 7679 7680 SetLastError( 0xdeadbeef ); 7681 setup_test( &info, http_end_request, __LINE__, 7682 nd->expect_conn_failure ? ERROR_INTERNET_OPERATION_CANCELLED : ERROR_SUCCESS); 7683 ret = HttpEndRequestA( req, NULL, 0x28, 0 ); 7684 error = GetLastError(); 7685 ok( !ret, "HttpEndRequestA succeeded\n" ); 7686 ok( error == ERROR_IO_PENDING, "expected ERROR_IO_PENDING got %u\n", error ); 7687 7688 WaitForSingleObject( info.wait, 10000 ); 7689 7690 setup_test( &info, internet_close_handle, __LINE__, ERROR_SUCCESS ); 7691 abort: 7692 InternetCloseHandle( req ); 7693 InternetCloseHandle( con ); 7694 InternetCloseHandle( ses ); 7695 7696 WaitForSingleObject( info.wait, 10000 ); 7697 Sleep(100); 7698 CloseHandle( info.wait ); 7699 DeleteCriticalSection( ¬ification_cs ); 7700 } 7701 7702 static HINTERNET closetest_session, closetest_req, closetest_conn; 7703 static BOOL closetest_closed; 7704 7705 static void WINAPI closetest_callback(HINTERNET hInternet, DWORD_PTR dwContext, DWORD dwInternetStatus, 7706 LPVOID lpvStatusInformation, DWORD dwStatusInformationLength) 7707 { 7708 DWORD len, type; 7709 BOOL res; 7710 7711 if(winetest_debug > 1) 7712 trace("closetest_callback %p: %d\n", hInternet, dwInternetStatus); 7713 7714 ok(hInternet == closetest_session || hInternet == closetest_conn || hInternet == closetest_req, 7715 "Unexpected hInternet %p\n", hInternet); 7716 if(!closetest_closed) 7717 return; 7718 7719 len = sizeof(type); 7720 res = InternetQueryOptionA(closetest_req, INTERNET_OPTION_HANDLE_TYPE, &type, &len); 7721 ok(!res && GetLastError() == ERROR_INVALID_HANDLE, 7722 "InternetQueryOptionA(%p INTERNET_OPTION_HANDLE_TYPE) failed: %x %u, expected TRUE ERROR_INVALID_HANDLE\n", 7723 closetest_req, res, GetLastError()); 7724 } 7725 7726 static void test_InternetCloseHandle(void) 7727 { 7728 DWORD len, flags; 7729 BOOL res; 7730 7731 closetest_session = InternetOpenA("", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, INTERNET_FLAG_ASYNC); 7732 ok(closetest_session != NULL,"InternetOpen failed with error %u\n", GetLastError()); 7733 7734 pInternetSetStatusCallbackA(closetest_session, closetest_callback); 7735 7736 closetest_conn = InternetConnectA(closetest_session, "source.winehq.org", INTERNET_INVALID_PORT_NUMBER, 7737 NULL, NULL, INTERNET_SERVICE_HTTP, 0x0, 0xdeadbeef); 7738 ok(closetest_conn != NULL,"InternetConnect failed with error %u\n", GetLastError()); 7739 7740 closetest_req = HttpOpenRequestA(closetest_conn, "GET", "winegecko.php", NULL, NULL, NULL, 7741 INTERNET_FLAG_KEEP_CONNECTION | INTERNET_FLAG_RESYNCHRONIZE, 0xdeadbead); 7742 7743 res = HttpSendRequestA(closetest_req, NULL, -1, NULL, 0); 7744 ok(!res && (GetLastError() == ERROR_IO_PENDING), 7745 "Asynchronous HttpSendRequest NOT returning 0 with error ERROR_IO_PENDING\n"); 7746 7747 test_request_flags(closetest_req, INTERNET_REQFLAG_NO_HEADERS); 7748 7749 res = InternetCloseHandle(closetest_session); 7750 ok(res, "InternetCloseHandle failed: %u\n", GetLastError()); 7751 closetest_closed = TRUE; 7752 trace("Closed session handle\n"); 7753 7754 res = InternetCloseHandle(closetest_conn); 7755 ok(!res && GetLastError() == ERROR_INVALID_HANDLE, "InternetCloseConnection(conn) failed: %x %u\n", 7756 res, GetLastError()); 7757 7758 res = InternetCloseHandle(closetest_req); 7759 ok(!res && GetLastError() == ERROR_INVALID_HANDLE, "InternetCloseConnection(req) failed: %x %u\n", 7760 res, GetLastError()); 7761 7762 len = sizeof(flags); 7763 res = InternetQueryOptionA(closetest_req, INTERNET_OPTION_REQUEST_FLAGS, &flags, &len); 7764 ok(!res && GetLastError() == ERROR_INVALID_HANDLE, 7765 "InternetQueryOptionA(%p INTERNET_OPTION_REQUEST_FLAGS) failed: %x %u, expected TRUE ERROR_INVALID_HANDLE\n", 7766 closetest_req, res, GetLastError()); 7767 } 7768 7769 static void test_connection_failure(void) 7770 { 7771 test_request_t req; 7772 DWORD error; 7773 BOOL ret; 7774 7775 open_simple_request(&req, "localhost", 1, NULL, "/"); 7776 7777 SetLastError(0xdeadbeef); 7778 ret = HttpSendRequestA(req.request, NULL, 0, NULL, 0); 7779 error = GetLastError(); 7780 ok(!ret, "unexpected success\n"); 7781 ok(error == ERROR_INTERNET_CANNOT_CONNECT, "wrong error %u\n", error); 7782 7783 close_request(&req); 7784 } 7785 7786 static void test_default_service_port(void) 7787 { 7788 HINTERNET session, connect, request; 7789 DWORD size, error; 7790 char buffer[128]; 7791 BOOL ret; 7792 7793 if(!is_ie7plus) 7794 return; 7795 7796 session = InternetOpenA("winetest", INTERNET_OPEN_TYPE_DIRECT, NULL, NULL, 0); 7797 ok(session != NULL, "InternetOpen failed\n"); 7798 7799 connect = InternetConnectA(session, "test.winehq.org", INTERNET_INVALID_PORT_NUMBER, NULL, NULL, 7800 INTERNET_SERVICE_HTTP, 0, 0); 7801 ok(connect != NULL, "InternetConnect failed\n"); 7802 7803 request = HttpOpenRequestA(connect, NULL, "/", NULL, NULL, NULL, INTERNET_FLAG_SECURE, 0); 7804 ok(request != NULL, "HttpOpenRequest failed\n"); 7805 7806 SetLastError(0xdeadbeef); 7807 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 7808 error = GetLastError(); 7809 ok(!ret, "HttpSendRequest succeeded\n"); 7810 ok(error == ERROR_INTERNET_SECURITY_CHANNEL_ERROR || error == ERROR_INTERNET_CANNOT_CONNECT, 7811 "got %u\n", error); 7812 7813 size = sizeof(buffer); 7814 memset(buffer, 0, sizeof(buffer)); 7815 ret = HttpQueryInfoA(request, HTTP_QUERY_HOST | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 7816 ok(ret, "HttpQueryInfo failed with error %u\n", GetLastError()); 7817 ok(!strcmp(buffer, "test.winehq.org:80"), "Expected test.winehg.org:80, got '%s'\n", buffer); 7818 7819 InternetCloseHandle(request); 7820 InternetCloseHandle(connect); 7821 7822 connect = InternetConnectA(session, "test.winehq.org", INTERNET_INVALID_PORT_NUMBER, NULL, NULL, 7823 INTERNET_SERVICE_HTTP, INTERNET_FLAG_SECURE, 0); 7824 ok(connect != NULL, "InternetConnect failed\n"); 7825 7826 request = HttpOpenRequestA(connect, NULL, "/", NULL, NULL, NULL, INTERNET_FLAG_SECURE, 0); 7827 ok(request != NULL, "HttpOpenRequest failed\n"); 7828 7829 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 7830 if (!ret && GetLastError() == ERROR_INTERNET_SECURITY_CHANNEL_ERROR) 7831 { 7832 win_skip("Can't make https connection\n"); 7833 goto done; 7834 } 7835 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 7836 7837 size = sizeof(buffer); 7838 memset(buffer, 0, sizeof(buffer)); 7839 ret = HttpQueryInfoA(request, HTTP_QUERY_HOST | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 7840 ok(ret, "HttpQueryInfo failed with error %u\n", GetLastError()); 7841 ok(!strcmp(buffer, "test.winehq.org"), "Expected test.winehg.org, got '%s'\n", buffer); 7842 7843 InternetCloseHandle(request); 7844 InternetCloseHandle(connect); 7845 7846 connect = InternetConnectA(session, "test.winehq.org", INTERNET_INVALID_PORT_NUMBER, NULL, NULL, 7847 INTERNET_SERVICE_HTTP, INTERNET_FLAG_SECURE, 0); 7848 ok(connect != NULL, "InternetConnect failed\n"); 7849 7850 request = HttpOpenRequestA(connect, NULL, "/", NULL, NULL, NULL, 0, 0); 7851 ok(request != NULL, "HttpOpenRequest failed\n"); 7852 7853 ret = HttpSendRequestA(request, NULL, 0, NULL, 0); 7854 ok(ret, "HttpSendRequest failed with error %u\n", GetLastError()); 7855 7856 size = sizeof(buffer); 7857 memset(buffer, 0, sizeof(buffer)); 7858 ret = HttpQueryInfoA(request, HTTP_QUERY_HOST | HTTP_QUERY_FLAG_REQUEST_HEADERS, buffer, &size, NULL); 7859 ok(ret, "HttpQueryInfo failed with error %u\n", GetLastError()); 7860 ok(!strcmp(buffer, "test.winehq.org:443"), "Expected test.winehg.org:443, got '%s'\n", buffer); 7861 7862 done: 7863 InternetCloseHandle(request); 7864 InternetCloseHandle(connect); 7865 InternetCloseHandle(session); 7866 } 7867 7868 static void init_status_tests(void) 7869 { 7870 memset(expect, 0, sizeof(expect)); 7871 memset(optional, 0, sizeof(optional)); 7872 memset(wine_allow, 0, sizeof(wine_allow)); 7873 memset(notified, 0, sizeof(notified)); 7874 memset(status_string, 0, sizeof(status_string)); 7875 7876 #define STATUS_STRING(status) status_string[status] = #status 7877 STATUS_STRING(INTERNET_STATUS_RESOLVING_NAME); 7878 STATUS_STRING(INTERNET_STATUS_NAME_RESOLVED); 7879 STATUS_STRING(INTERNET_STATUS_CONNECTING_TO_SERVER); 7880 STATUS_STRING(INTERNET_STATUS_CONNECTED_TO_SERVER); 7881 STATUS_STRING(INTERNET_STATUS_SENDING_REQUEST); 7882 STATUS_STRING(INTERNET_STATUS_REQUEST_SENT); 7883 STATUS_STRING(INTERNET_STATUS_RECEIVING_RESPONSE); 7884 STATUS_STRING(INTERNET_STATUS_RESPONSE_RECEIVED); 7885 STATUS_STRING(INTERNET_STATUS_CTL_RESPONSE_RECEIVED); 7886 STATUS_STRING(INTERNET_STATUS_PREFETCH); 7887 STATUS_STRING(INTERNET_STATUS_CLOSING_CONNECTION); 7888 STATUS_STRING(INTERNET_STATUS_CONNECTION_CLOSED); 7889 STATUS_STRING(INTERNET_STATUS_HANDLE_CREATED); 7890 STATUS_STRING(INTERNET_STATUS_HANDLE_CLOSING); 7891 STATUS_STRING(INTERNET_STATUS_DETECTING_PROXY); 7892 STATUS_STRING(INTERNET_STATUS_REQUEST_COMPLETE); 7893 STATUS_STRING(INTERNET_STATUS_REDIRECT); 7894 STATUS_STRING(INTERNET_STATUS_INTERMEDIATE_RESPONSE); 7895 STATUS_STRING(INTERNET_STATUS_USER_INPUT_REQUIRED); 7896 STATUS_STRING(INTERNET_STATUS_STATE_CHANGE); 7897 STATUS_STRING(INTERNET_STATUS_COOKIE_SENT); 7898 STATUS_STRING(INTERNET_STATUS_COOKIE_RECEIVED); 7899 STATUS_STRING(INTERNET_STATUS_PRIVACY_IMPACTED); 7900 STATUS_STRING(INTERNET_STATUS_P3P_HEADER); 7901 STATUS_STRING(INTERNET_STATUS_P3P_POLICYREF); 7902 STATUS_STRING(INTERNET_STATUS_COOKIE_HISTORY); 7903 #undef STATUS_STRING 7904 } 7905 7906 static void WINAPI header_cb( HINTERNET handle, DWORD_PTR ctx, DWORD status, LPVOID info, DWORD len ) 7907 { 7908 BOOL ret; 7909 DWORD index, size; 7910 char buf[256]; 7911 7912 if (status == INTERNET_STATUS_SENDING_REQUEST) 7913 { 7914 ret = HttpAddRequestHeadersA( handle, "winetest: winetest", ~0u, HTTP_ADDREQ_FLAG_ADD ); 7915 ok( ret, "HttpAddRequestHeadersA failed %u\n", GetLastError() ); 7916 SetEvent( (HANDLE)ctx ); 7917 } 7918 else if (status == INTERNET_STATUS_REQUEST_SENT) 7919 { 7920 index = 0; 7921 size = sizeof(buf); 7922 ret = HttpQueryInfoA( handle, HTTP_QUERY_RAW_HEADERS_CRLF|HTTP_QUERY_FLAG_REQUEST_HEADERS, 7923 buf, &size, &index ); 7924 ok( ret, "HttpQueryInfoA failed %u\n", GetLastError() ); 7925 ok( strstr( buf, "winetest: winetest" ) != NULL, "header missing\n" ); 7926 SetEvent( (HANDLE)ctx ); 7927 } 7928 } 7929 7930 static void test_concurrent_header_access(void) 7931 { 7932 HINTERNET ses, con, req; 7933 DWORD err; 7934 BOOL ret; 7935 HANDLE wait = CreateEventW( NULL, FALSE, FALSE, NULL ); 7936 7937 ses = InternetOpenA( "winetest", 0, NULL, NULL, INTERNET_FLAG_ASYNC ); 7938 ok( ses != NULL, "InternetOpenA failed\n" ); 7939 7940 con = InternetConnectA( ses, "test.winehq.org", INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, 7941 INTERNET_SERVICE_HTTP, 0, 0 ); 7942 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 7943 7944 req = HttpOpenRequestA( con, NULL, "/", NULL, NULL, NULL, 0, (DWORD_PTR)wait ); 7945 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 7946 7947 pInternetSetStatusCallbackA( req, header_cb ); 7948 7949 SetLastError( 0xdeadbeef ); 7950 ret = HttpSendRequestA( req, NULL, 0, NULL, 0 ); 7951 err = GetLastError(); 7952 ok( !ret, "HttpSendRequestA succeeded\n" ); 7953 ok( err == ERROR_IO_PENDING, "got %u\n", ERROR_IO_PENDING ); 7954 7955 WaitForSingleObject( wait, 5000 ); 7956 WaitForSingleObject( wait, 5000 ); 7957 7958 InternetCloseHandle( req ); 7959 InternetCloseHandle( con ); 7960 InternetCloseHandle( ses ); 7961 CloseHandle( wait ); 7962 } 7963 7964 static void test_cert_string(void) 7965 { 7966 HINTERNET ses, con, req; 7967 char actual[512]; 7968 DWORD size; 7969 BOOL res; 7970 7971 ses = InternetOpenA( "winetest", 0, NULL, NULL, 0 ); 7972 ok( ses != NULL, "InternetOpenA failed\n" ); 7973 7974 con = InternetConnectA( ses, "test.winehq.org", INTERNET_DEFAULT_HTTP_PORT, NULL, NULL, 7975 INTERNET_SERVICE_HTTP, 0, 0 ); 7976 ok( con != NULL, "InternetConnectA failed %u\n", GetLastError() ); 7977 7978 req = HttpOpenRequestA( con, NULL, "/", NULL, NULL, NULL, 0, 0 ); 7979 ok( req != NULL, "HttpOpenRequestA failed %u\n", GetLastError() ); 7980 7981 size = sizeof(actual); 7982 SetLastError( 0xdeadbeef ); 7983 memset( actual, 0x55, sizeof(actual) ); 7984 res = InternetQueryOptionA( req, INTERNET_OPTION_SECURITY_CERTIFICATE, actual, &size ); 7985 ok( !res && GetLastError() == ERROR_INTERNET_INVALID_OPERATION, 7986 "InternetQueryOption failed: %u\n", GetLastError() ); 7987 ok( size == 0, "unexpected size: %u\n", size ); 7988 ok( actual[0] == 0x55, "unexpected byte: %02x\n", actual[0] ); 7989 7990 InternetCloseHandle( req ); 7991 InternetCloseHandle( con ); 7992 InternetCloseHandle( ses ); 7993 } 7994 7995 START_TEST(http) 7996 { 7997 HMODULE hdll; 7998 7999 if (!winetest_interactive) 8000 { 8001 win_skip("Skipping wininet:http due to hang ROSTESTS-357\n"); 8002 return; 8003 } 8004 8005 hdll = GetModuleHandleA("wininet.dll"); 8006 8007 if(!GetProcAddress(hdll, "InternetGetCookieExW")) { 8008 win_skip("Too old IE (older than 6.0)\n"); 8009 return; 8010 } 8011 8012 pInternetSetStatusCallbackA = (void*)GetProcAddress(hdll, "InternetSetStatusCallbackA"); 8013 pInternetSetStatusCallbackW = (void*)GetProcAddress(hdll, "InternetSetStatusCallbackW"); 8014 pInternetGetSecurityInfoByURLA = (void*)GetProcAddress(hdll, "InternetGetSecurityInfoByURLA"); 8015 8016 if(!pInternetGetSecurityInfoByURLA) { 8017 is_ie7plus = FALSE; 8018 win_skip("IE6 found. It's too old for some tests.\n"); 8019 } 8020 8021 init_events(); 8022 init_status_tests(); 8023 test_InternetCloseHandle(); 8024 InternetReadFile_test(INTERNET_FLAG_ASYNC, &test_data[0]); 8025 InternetReadFile_test(INTERNET_FLAG_ASYNC, &test_data[1]); 8026 InternetReadFile_test(0, &test_data[1]); 8027 InternetReadFile_test(INTERNET_FLAG_ASYNC, &test_data[2]); 8028 test_secure_connection(); 8029 test_security_flags(); 8030 InternetReadFile_test(0, &test_data[2]); 8031 InternetReadFileExA_test(INTERNET_FLAG_ASYNC); 8032 test_open_url_async(); 8033 test_async_HttpSendRequestEx(¬ification_data[0]); 8034 test_async_HttpSendRequestEx(¬ification_data[1]); 8035 test_async_HttpSendRequestEx(¬ification_data[2]); 8036 test_async_HttpSendRequestEx(¬ification_data[3]); 8037 InternetOpenRequest_test(); 8038 test_http_cache(); 8039 InternetLockRequestFile_test(); 8040 InternetOpenUrlA_test(); 8041 HttpHeaders_test(); 8042 test_http_connection(); 8043 test_user_agent_header(); 8044 test_bogus_accept_types_array(); 8045 InternetReadFile_chunked_test(); 8046 HttpSendRequestEx_test(); 8047 InternetReadFile_test(INTERNET_FLAG_ASYNC, &test_data[3]); 8048 test_connection_failure(); 8049 test_default_service_port(); 8050 test_concurrent_header_access(); 8051 test_cert_string(); 8052 free_events(); 8053 } 8054