2 * Copyright 2005-2009 Jacek Caban for CodeWeavers
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #include <wine/test.h>
32 static HRESULT (WINAPI *pCoInternetGetSession)(DWORD, IInternetSession **, DWORD);
33 static HRESULT (WINAPI *pReleaseBindInfo)(BINDINFO*);
34 static HRESULT (WINAPI *pCreateUri)(LPCWSTR, DWORD, DWORD_PTR, IUri**);
36 #define DEFINE_EXPECT(func) \
37 static BOOL expect_ ## func = FALSE, called_ ## func = FALSE
39 #define SET_EXPECT(func) \
40 expect_ ## func = TRUE
42 #define CHECK_EXPECT2(func) \
44 ok(expect_ ##func, "unexpected call " #func "\n"); \
45 called_ ## func = TRUE; \
48 #define CHECK_EXPECT(func) \
50 CHECK_EXPECT2(func); \
51 expect_ ## func = FALSE; \
54 #define CHECK_CALLED(func) \
56 ok(called_ ## func, "expected " #func "\n"); \
57 expect_ ## func = called_ ## func = FALSE; \
60 #define CHECK_NOT_CALLED(func) \
62 ok(!called_ ## func, "unexpected " #func "\n"); \
63 expect_ ## func = called_ ## func = FALSE; \
66 #define CLEAR_CALLED(func) \
67 expect_ ## func = called_ ## func = FALSE
69 DEFINE_EXPECT(GetBindInfo);
70 DEFINE_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
71 DEFINE_EXPECT(ReportProgress_DIRECTBIND);
72 DEFINE_EXPECT(ReportProgress_RAWMIMETYPE);
73 DEFINE_EXPECT(ReportProgress_FINDINGRESOURCE);
74 DEFINE_EXPECT(ReportProgress_CONNECTING);
75 DEFINE_EXPECT(ReportProgress_SENDINGREQUEST);
76 DEFINE_EXPECT(ReportProgress_CACHEFILENAMEAVAILABLE);
77 DEFINE_EXPECT(ReportProgress_VERIFIEDMIMETYPEAVAILABLE);
78 DEFINE_EXPECT(ReportProgress_PROTOCOLCLASSID);
79 DEFINE_EXPECT(ReportProgress_COOKIE_SENT);
80 DEFINE_EXPECT(ReportProgress_REDIRECTING);
81 DEFINE_EXPECT(ReportProgress_ENCODING);
82 DEFINE_EXPECT(ReportProgress_ACCEPTRANGES);
83 DEFINE_EXPECT(ReportProgress_PROXYDETECTING);
84 DEFINE_EXPECT(ReportProgress_LOADINGMIMEHANDLER);
85 DEFINE_EXPECT(ReportProgress_DECODING);
86 DEFINE_EXPECT(ReportData);
87 DEFINE_EXPECT(ReportData2);
88 DEFINE_EXPECT(ReportResult);
89 DEFINE_EXPECT(GetBindString_ACCEPT_MIMES);
90 DEFINE_EXPECT(GetBindString_USER_AGENT);
91 DEFINE_EXPECT(GetBindString_POST_COOKIE);
92 DEFINE_EXPECT(GetBindString_URL);
93 DEFINE_EXPECT(QueryService_HttpNegotiate);
94 DEFINE_EXPECT(QueryService_InternetProtocol);
95 DEFINE_EXPECT(QueryService_HttpSecurity);
96 DEFINE_EXPECT(QueryInterface_IWinInetInfo);
97 DEFINE_EXPECT(QueryInterface_IWinInetHttpInfo);
98 DEFINE_EXPECT(BeginningTransaction);
99 DEFINE_EXPECT(GetRootSecurityId);
100 DEFINE_EXPECT(OnResponse);
101 DEFINE_EXPECT(Switch);
102 DEFINE_EXPECT(Continue);
103 DEFINE_EXPECT(CreateInstance);
104 DEFINE_EXPECT(Start);
105 DEFINE_EXPECT(Terminate);
107 DEFINE_EXPECT(Read2);
108 DEFINE_EXPECT(SetPriority);
109 DEFINE_EXPECT(LockRequest);
110 DEFINE_EXPECT(UnlockRequest);
111 DEFINE_EXPECT(MimeFilter_CreateInstance);
112 DEFINE_EXPECT(MimeFilter_Start);
113 DEFINE_EXPECT(MimeFilter_ReportProgress);
114 DEFINE_EXPECT(MimeFilter_ReportData);
115 DEFINE_EXPECT(MimeFilter_ReportResult);
116 DEFINE_EXPECT(MimeFilter_Terminate);
117 DEFINE_EXPECT(MimeFilter_LockRequest);
118 DEFINE_EXPECT(MimeFilter_UnlockRequest);
119 DEFINE_EXPECT(MimeFilter_Read);
120 DEFINE_EXPECT(MimeFilter_Switch);
121 DEFINE_EXPECT(MimeFilter_Continue);
123 static const WCHAR wszIndexHtml[] = {'i','n','d','e','x','.','h','t','m','l',0};
124 static const WCHAR index_url[] =
125 {'f','i','l','e',':','i','n','d','e','x','.','h','t','m','l',0};
127 static const WCHAR acc_mimeW[] = {'*','/','*',0};
128 static const WCHAR user_agentW[] = {'W','i','n','e',0};
129 static const WCHAR text_htmlW[] = {'t','e','x','t','/','h','t','m','l',0};
130 static const WCHAR hostW[] = {'w','w','w','.','w','i','n','e','h','q','.','o','r','g',0};
131 static const WCHAR winehq_ipW[] = {'2','0','9','.','4','6','.','2','5','.','1','3','4',0};
132 static const WCHAR emptyW[] = {0};
133 static const WCHAR gzipW[] = {'g','z','i','p',0};
135 static HRESULT expect_hrResult;
136 static LPCWSTR file_name, http_url, expect_wsz;
137 static IInternetProtocol *async_protocol = NULL;
138 static BOOL first_data_notif, http_is_first, http_post_test, test_redirect;
139 static int state = 0, prot_state, read_report_data;
140 static DWORD bindf, ex_priority , pi;
141 static IInternetProtocol *binding_protocol, *filtered_protocol;
142 static IInternetBindInfo *prot_bind_info;
143 static IInternetProtocolSink *binding_sink, *filtered_sink;
144 static void *expect_pv;
145 static HANDLE event_complete, event_complete2, event_continue, event_continue_done;
146 static BOOL binding_test;
147 static PROTOCOLDATA protocoldata, *pdata, continue_protdata;
148 static DWORD prot_read, pi, filter_state;
149 static BOOL security_problem;
150 static BOOL async_read_pending, mimefilter_test, direct_read, wait_for_switch, emulate_prot, short_read;
161 static const WCHAR protocol_names[][10] = {
164 {'h','t','t','p','s',0},
170 static const WCHAR binding_urls[][130] = {
171 {'f','i','l','e',':','t','e','s','t','.','h','t','m','l',0},
172 {'h','t','t','p',':','/','/','w','w','w','.','w','i','n','e','h','q','.',
173 'o','r','g','/','s','i','t','e','/','a','b','o','u','t',0},
174 {'h','t','t','p','s',':','/','/','w','w','w','.','c','o','d','e','w','e','a','v','e','r','s',
175 '.','c','o','m','/','t','e','s','t','.','h','t','m','l',0},
176 {'f','t','p',':','/','/','f','t','p','.','w','i','n','e','h','q','.','o','r','g',
177 '/','p','u','b','/','o','t','h','e','r',
178 '/','w','i','n','e','l','o','g','o','.','x','c','f','.','t','a','r','.','b','z','2',0},
179 {'m','k',':','t','e','s','t',0},
180 {'t','e','s','t',':','/','/','f','i','l','e','.','h','t','m','l',0}
183 static const char *debugstr_guid(REFIID riid)
187 sprintf(buf, "{%08X-%04X-%04X-%02X%02X-%02X%02X%02X%02X%02X%02X}",
188 riid->Data1, riid->Data2, riid->Data3, riid->Data4[0],
189 riid->Data4[1], riid->Data4[2], riid->Data4[3], riid->Data4[4],
190 riid->Data4[5], riid->Data4[6], riid->Data4[7]);
195 static int strcmp_wa(LPCWSTR strw, const char *stra)
198 WideCharToMultiByte(CP_ACP, 0, strw, -1, buf, sizeof(buf), NULL, NULL);
199 return lstrcmpA(stra, buf);
202 /* lstrcmpW is not implemented on Win9x */
203 static int strcmp_ww(LPCWSTR strw1, LPCWSTR strw2)
205 CHAR stra1[512], stra2[512];
206 WideCharToMultiByte(CP_ACP, 0, strw1, -1, stra1, MAX_PATH, NULL, NULL);
207 WideCharToMultiByte(CP_ACP, 0, strw2, -1, stra2, MAX_PATH, NULL, NULL);
208 return lstrcmpA(stra1, stra2);
211 static HRESULT WINAPI HttpSecurity_QueryInterface(IHttpSecurity *iface, REFIID riid, void **ppv)
213 if(IsEqualGUID(&IID_IUnknown, riid)
214 || IsEqualGUID(&IID_IHttpSecurity, riid)) {
219 ok(0, "unexpected call\n");
220 return E_NOINTERFACE;
223 static ULONG WINAPI HttpSecurity_AddRef(IHttpSecurity *iface)
228 static ULONG WINAPI HttpSecurity_Release(IHttpSecurity *iface)
233 static HRESULT WINAPI HttpSecurity_GetWindow(IHttpSecurity* iface, REFGUID rguidReason, HWND *phwnd)
235 trace("HttpSecurity_GetWindow\n");
240 static HRESULT WINAPI HttpSecurity_OnSecurityProblem(IHttpSecurity *iface, DWORD dwProblem)
242 trace("Security problem: %u\n", dwProblem);
243 ok(dwProblem == ERROR_INTERNET_SEC_CERT_REV_FAILED, "Expected ERROR_INTERNET_SEC_CERT_REV_FAILED got %u\n", dwProblem);
245 /* Only retry once */
246 if (security_problem)
249 security_problem = TRUE;
250 SET_EXPECT(BeginningTransaction);
255 static IHttpSecurityVtbl HttpSecurityVtbl = {
256 HttpSecurity_QueryInterface,
258 HttpSecurity_Release,
259 HttpSecurity_GetWindow,
260 HttpSecurity_OnSecurityProblem
263 static IHttpSecurity http_security = { &HttpSecurityVtbl };
265 static HRESULT WINAPI HttpNegotiate_QueryInterface(IHttpNegotiate2 *iface, REFIID riid, void **ppv)
267 if(IsEqualGUID(&IID_IUnknown, riid)
268 || IsEqualGUID(&IID_IHttpNegotiate, riid)
269 || IsEqualGUID(&IID_IHttpNegotiate2, riid)) {
274 ok(0, "unexpected call\n");
275 return E_NOINTERFACE;
278 static ULONG WINAPI HttpNegotiate_AddRef(IHttpNegotiate2 *iface)
283 static ULONG WINAPI HttpNegotiate_Release(IHttpNegotiate2 *iface)
288 static HRESULT WINAPI HttpNegotiate_BeginningTransaction(IHttpNegotiate2 *iface, LPCWSTR szURL,
289 LPCWSTR szHeaders, DWORD dwReserved, LPWSTR *pszAdditionalHeaders)
293 static const WCHAR wszHeaders[] =
294 {'C','o','n','t','e','n','t','-','T','y','p','e',':',' ','a','p','p','l','i','c','a','t',
295 'i','o','n','/','x','-','w','w','w','-','f','o','r','m','-','u','r','l','e','n','c','o',
296 'd','e','d','\r','\n',0};
298 CHECK_EXPECT(BeginningTransaction);
301 ok(!strcmp_ww(szURL, binding_urls[tested_protocol]), "szURL != http_url\n");
303 ok(!strcmp_ww(szURL, http_url), "szURL != http_url\n");
304 ok(!dwReserved, "dwReserved=%d, expected 0\n", dwReserved);
305 ok(pszAdditionalHeaders != NULL, "pszAdditionalHeaders == NULL\n");
306 if(pszAdditionalHeaders)
308 ok(*pszAdditionalHeaders == NULL, "*pszAdditionalHeaders != NULL\n");
311 addl_headers = CoTaskMemAlloc(sizeof(wszHeaders));
314 http_post_test = FALSE;
315 skip("Out of memory\n");
316 return E_OUTOFMEMORY;
318 memcpy(addl_headers, wszHeaders, sizeof(wszHeaders));
319 *pszAdditionalHeaders = addl_headers;
326 static HRESULT WINAPI HttpNegotiate_OnResponse(IHttpNegotiate2 *iface, DWORD dwResponseCode,
327 LPCWSTR szResponseHeaders, LPCWSTR szRequestHeaders, LPWSTR *pszAdditionalRequestHeaders)
329 CHECK_EXPECT(OnResponse);
331 ok(dwResponseCode == 200, "dwResponseCode=%d, expected 200\n", dwResponseCode);
332 ok(szResponseHeaders != NULL, "szResponseHeaders == NULL\n");
333 ok(szRequestHeaders == NULL, "szRequestHeaders != NULL\n");
334 ok(pszAdditionalRequestHeaders == NULL, "pszAdditionalHeaders != NULL\n");
339 static HRESULT WINAPI HttpNegotiate_GetRootSecurityId(IHttpNegotiate2 *iface,
340 BYTE *pbSecurityId, DWORD *pcbSecurityId, DWORD_PTR dwReserved)
342 static const BYTE sec_id[] = {'h','t','t','p',':','t','e','s','t',1,0,0,0};
344 CHECK_EXPECT(GetRootSecurityId);
346 ok(!dwReserved, "dwReserved=%ld, expected 0\n", dwReserved);
347 ok(pbSecurityId != NULL, "pbSecurityId == NULL\n");
348 ok(pcbSecurityId != NULL, "pcbSecurityId == NULL\n");
351 ok(*pcbSecurityId == 512, "*pcbSecurityId=%d, expected 512\n", *pcbSecurityId);
352 *pcbSecurityId = sizeof(sec_id);
356 memcpy(pbSecurityId, sec_id, sizeof(sec_id));
361 static IHttpNegotiate2Vtbl HttpNegotiateVtbl = {
362 HttpNegotiate_QueryInterface,
363 HttpNegotiate_AddRef,
364 HttpNegotiate_Release,
365 HttpNegotiate_BeginningTransaction,
366 HttpNegotiate_OnResponse,
367 HttpNegotiate_GetRootSecurityId
370 static IHttpNegotiate2 http_negotiate = { &HttpNegotiateVtbl };
372 static HRESULT QueryInterface(REFIID,void**);
374 static HRESULT WINAPI ServiceProvider_QueryInterface(IServiceProvider *iface, REFIID riid, void **ppv)
376 return QueryInterface(riid, ppv);
379 static ULONG WINAPI ServiceProvider_AddRef(IServiceProvider *iface)
384 static ULONG WINAPI ServiceProvider_Release(IServiceProvider *iface)
389 static HRESULT WINAPI ServiceProvider_QueryService(IServiceProvider *iface, REFGUID guidService,
390 REFIID riid, void **ppv)
392 if(IsEqualGUID(&IID_IHttpNegotiate, guidService) || IsEqualGUID(&IID_IHttpNegotiate2, riid)) {
393 CHECK_EXPECT2(QueryService_HttpNegotiate);
394 return IHttpNegotiate2_QueryInterface(&http_negotiate, riid, ppv);
397 if(IsEqualGUID(&IID_IInternetProtocol, guidService)) {
398 ok(IsEqualGUID(&IID_IInternetProtocol, riid), "unexpected riid\n");
399 CHECK_EXPECT(QueryService_InternetProtocol);
400 return E_NOINTERFACE;
403 if(IsEqualGUID(&IID_IHttpSecurity, guidService)) {
404 ok(IsEqualGUID(&IID_IHttpSecurity, riid), "unexpected riid\n");
405 CHECK_EXPECT(QueryService_HttpSecurity);
406 return IHttpSecurity_QueryInterface(&http_security, riid, ppv);
409 ok(0, "unexpected service %s\n", debugstr_guid(guidService));
413 static const IServiceProviderVtbl ServiceProviderVtbl = {
414 ServiceProvider_QueryInterface,
415 ServiceProvider_AddRef,
416 ServiceProvider_Release,
417 ServiceProvider_QueryService
420 static IServiceProvider service_provider = { &ServiceProviderVtbl };
422 static HRESULT WINAPI ProtocolSink_QueryInterface(IInternetProtocolSink *iface, REFIID riid, void **ppv)
424 return QueryInterface(riid, ppv);
427 static ULONG WINAPI ProtocolSink_AddRef(IInternetProtocolSink *iface)
432 static ULONG WINAPI ProtocolSink_Release(IInternetProtocolSink *iface)
437 static void call_continue(PROTOCOLDATA *protocol_data)
442 if(tested_protocol == HTTP_TEST || tested_protocol == HTTPS_TEST)
443 CLEAR_CALLED(ReportProgress_COOKIE_SENT);
444 if(tested_protocol == HTTP_TEST || tested_protocol == HTTPS_TEST || tested_protocol == FTP_TEST) {
446 CLEAR_CALLED(ReportProgress_FINDINGRESOURCE);
447 CLEAR_CALLED(ReportProgress_CONNECTING);
448 CLEAR_CALLED(ReportProgress_PROXYDETECTING);
449 }else if(test_redirect) {
450 CHECK_CALLED(ReportProgress_FINDINGRESOURCE);
452 CHECK_NOT_CALLED(ReportProgress_FINDINGRESOURCE);
453 /* IE7 does call this */
454 CLEAR_CALLED(ReportProgress_CONNECTING);
457 if(tested_protocol == FTP_TEST)
458 todo_wine CHECK_CALLED(ReportProgress_SENDINGREQUEST);
459 else if (tested_protocol != HTTPS_TEST)
460 CHECK_CALLED(ReportProgress_SENDINGREQUEST);
462 CHECK_CALLED(ReportProgress_REDIRECTING);
463 if(tested_protocol == HTTP_TEST || tested_protocol == HTTPS_TEST) {
464 SET_EXPECT(OnResponse);
465 if(tested_protocol == HTTPS_TEST || test_redirect)
466 SET_EXPECT(ReportProgress_ACCEPTRANGES);
467 SET_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
468 if(bindf & BINDF_NEEDFILE)
469 SET_EXPECT(ReportProgress_CACHEFILENAMEAVAILABLE);
473 SET_EXPECT(ReportData);
474 hres = IInternetProtocol_Continue(async_protocol, protocol_data);
475 ok(hres == S_OK, "Continue failed: %08x\n", hres);
476 if(tested_protocol == FTP_TEST)
477 CLEAR_CALLED(ReportData);
478 else if (! security_problem)
479 CHECK_CALLED(ReportData);
482 if (! security_problem)
485 if(tested_protocol == HTTP_TEST || tested_protocol == HTTPS_TEST) {
486 CHECK_CALLED(OnResponse);
487 if(tested_protocol == HTTPS_TEST)
488 CHECK_CALLED(ReportProgress_ACCEPTRANGES);
489 else if(test_redirect)
490 CLEAR_CALLED(ReportProgress_ACCEPTRANGES);
491 CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
492 if(bindf & BINDF_NEEDFILE)
493 CHECK_CALLED(ReportProgress_CACHEFILENAMEAVAILABLE);
498 security_problem = FALSE;
499 SET_EXPECT(ReportProgress_CONNECTING);
504 static HRESULT WINAPI ProtocolSink_Switch(IInternetProtocolSink *iface, PROTOCOLDATA *pProtocolData)
506 if(tested_protocol == FTP_TEST)
507 CHECK_EXPECT2(Switch);
509 CHECK_EXPECT(Switch);
511 ok(pProtocolData != NULL, "pProtocolData == NULL\n");
513 ok(pProtocolData != &protocoldata, "pProtocolData == &protocoldata\n");
514 ok(pProtocolData->grfFlags == protocoldata.grfFlags, "grfFlags wrong %x/%x\n",
515 pProtocolData->grfFlags, protocoldata.grfFlags );
516 ok(pProtocolData->dwState == protocoldata.dwState, "dwState wrong %x/%x\n",
517 pProtocolData->dwState, protocoldata.dwState );
518 ok(pProtocolData->pData == protocoldata.pData, "pData wrong %p/%p\n",
519 pProtocolData->pData, protocoldata.pData );
520 ok(pProtocolData->cbData == protocoldata.cbData, "cbData wrong %x/%x\n",
521 pProtocolData->cbData, protocoldata.cbData );
524 pdata = pProtocolData;
527 SetEvent(event_complete);
528 WaitForSingleObject(event_complete2, INFINITE);
531 continue_protdata = *pProtocolData;
532 SetEvent(event_continue);
533 WaitForSingleObject(event_continue_done, INFINITE);
535 call_continue(pProtocolData);
536 SetEvent(event_complete);
542 static HRESULT WINAPI ProtocolSink_ReportProgress(IInternetProtocolSink *iface, ULONG ulStatusCode,
543 LPCWSTR szStatusText)
545 static const WCHAR null_guid[] = {'{','0','0','0','0','0','0','0','0','-','0','0','0','0','-',
546 '0','0','0','0','-','0','0','0','0','-','0','0','0','0','0','0','0','0','0','0','0','0','}',0};
547 static const WCHAR text_plain[] = {'t','e','x','t','/','p','l','a','i','n',0};
549 switch(ulStatusCode) {
550 case BINDSTATUS_MIMETYPEAVAILABLE:
551 CHECK_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
552 if(tested_protocol != FILE_TEST && !mimefilter_test && (pi & PI_MIMEVERIFICATION)) {
553 if(!short_read || !direct_read)
554 CHECK_CALLED(Read); /* set in Continue */
556 CHECK_CALLED(Read2); /* set in Read */
558 ok(szStatusText != NULL, "szStatusText == NULL\n");
560 if(tested_protocol == BIND_TEST)
561 ok(szStatusText == expect_wsz, "unexpected szStatusText\n");
562 else if (http_post_test)
563 ok(lstrlenW(text_plain) <= lstrlenW(szStatusText) &&
564 !memcmp(szStatusText, text_plain, lstrlenW(text_plain)*sizeof(WCHAR)),
565 "szStatusText != text/plain\n");
566 else if(!mimefilter_test)
567 ok(lstrlenW(text_htmlW) <= lstrlenW(szStatusText) &&
568 !memcmp(szStatusText, text_htmlW, lstrlenW(text_htmlW)*sizeof(WCHAR)),
569 "szStatusText != text/html\n");
572 case BINDSTATUS_DIRECTBIND:
573 CHECK_EXPECT2(ReportProgress_DIRECTBIND);
574 ok(szStatusText == NULL, "szStatusText != NULL\n");
576 case BINDSTATUS_RAWMIMETYPE:
577 CHECK_EXPECT2(ReportProgress_RAWMIMETYPE);
578 ok(szStatusText != NULL, "szStatusText == NULL\n");
580 ok(lstrlenW(szStatusText) < lstrlenW(text_htmlW) ||
581 !memcmp(szStatusText, text_htmlW, lstrlenW(text_htmlW)*sizeof(WCHAR)),
582 "szStatusText != text/html\n");
584 case BINDSTATUS_CACHEFILENAMEAVAILABLE:
585 CHECK_EXPECT(ReportProgress_CACHEFILENAMEAVAILABLE);
586 ok(szStatusText != NULL, "szStatusText == NULL\n");
589 ok(!strcmp_ww(szStatusText, expect_wsz), "unexpected szStatusText\n");
590 else if(tested_protocol == FILE_TEST)
591 ok(!strcmp_ww(szStatusText, file_name), "szStatusText = %s\n", wine_dbgstr_w(szStatusText));
593 ok(szStatusText != NULL, "szStatusText == NULL\n");
596 case BINDSTATUS_FINDINGRESOURCE:
597 CHECK_EXPECT2(ReportProgress_FINDINGRESOURCE);
598 ok(szStatusText != NULL, "szStatusText == NULL\n");
600 case BINDSTATUS_CONNECTING:
601 CHECK_EXPECT2(ReportProgress_CONNECTING);
602 ok(szStatusText != NULL, "szStatusText == NULL\n");
604 case BINDSTATUS_SENDINGREQUEST:
605 CHECK_EXPECT2(ReportProgress_SENDINGREQUEST);
606 if(tested_protocol == FILE_TEST) {
607 ok(szStatusText != NULL, "szStatusText == NULL\n");
609 ok(!*szStatusText, "wrong szStatusText\n");
612 case BINDSTATUS_VERIFIEDMIMETYPEAVAILABLE:
613 CHECK_EXPECT(ReportProgress_VERIFIEDMIMETYPEAVAILABLE);
614 ok(szStatusText != NULL, "szStatusText == NULL\n");
616 ok(!strcmp_ww(szStatusText, text_htmlW), "szStatusText != text/html\n");
618 case BINDSTATUS_PROTOCOLCLASSID:
619 CHECK_EXPECT(ReportProgress_PROTOCOLCLASSID);
620 ok(szStatusText != NULL, "szStatusText == NULL\n");
621 ok(!strcmp_ww(szStatusText, null_guid), "unexpected classid %s\n", wine_dbgstr_w(szStatusText));
623 case BINDSTATUS_COOKIE_SENT:
624 CHECK_EXPECT(ReportProgress_COOKIE_SENT);
625 ok(szStatusText == NULL, "szStatusText != NULL\n");
627 case BINDSTATUS_REDIRECTING:
628 CHECK_EXPECT(ReportProgress_REDIRECTING);
630 ok(!strcmp_wa(szStatusText, "http://test.winehq.org/hello.html"), "szStatusText = %s\n", wine_dbgstr_w(szStatusText));
632 ok(szStatusText == NULL, "szStatusText = %s\n", wine_dbgstr_w(szStatusText));
634 case BINDSTATUS_ENCODING:
635 CHECK_EXPECT(ReportProgress_ENCODING);
636 ok(!strcmp_wa(szStatusText, "gzip"), "szStatusText = %s\n", wine_dbgstr_w(szStatusText));
638 case BINDSTATUS_ACCEPTRANGES:
639 CHECK_EXPECT(ReportProgress_ACCEPTRANGES);
640 ok(!szStatusText, "szStatusText = %s\n", wine_dbgstr_w(szStatusText));
642 case BINDSTATUS_PROXYDETECTING:
643 CHECK_EXPECT(ReportProgress_PROXYDETECTING);
644 SET_EXPECT(ReportProgress_CONNECTING);
645 ok(!szStatusText, "szStatusText = %s\n", wine_dbgstr_w(szStatusText));
647 case BINDSTATUS_LOADINGMIMEHANDLER:
648 CHECK_EXPECT(ReportProgress_LOADINGMIMEHANDLER);
649 ok(!szStatusText, "szStatusText = %s\n", wine_dbgstr_w(szStatusText));
651 case BINDSTATUS_DECODING:
652 CHECK_EXPECT(ReportProgress_DECODING);
653 ok(!strcmp_ww(szStatusText, gzipW), "szStatusText = %s\n", wine_dbgstr_w(szStatusText));
656 ok(0, "Unexpected status %d\n", ulStatusCode);
662 static HRESULT WINAPI ProtocolSink_ReportData(IInternetProtocolSink *iface, DWORD grfBSCF,
663 ULONG ulProgress, ULONG ulProgressMax)
667 static int rec_depth;
670 if(!mimefilter_test && tested_protocol == FILE_TEST) {
671 CHECK_EXPECT2(ReportData);
673 ok(ulProgress == ulProgressMax, "ulProgress (%d) != ulProgressMax (%d)\n",
674 ulProgress, ulProgressMax);
675 ok(ulProgressMax == 13, "ulProgressMax=%d, expected 13\n", ulProgressMax);
676 /* BSCF_SKIPDRAINDATAFORFILEURLS added in IE8 */
677 ok((grfBSCF == (BSCF_FIRSTDATANOTIFICATION | BSCF_LASTDATANOTIFICATION)) ||
678 (grfBSCF == (BSCF_FIRSTDATANOTIFICATION | BSCF_LASTDATANOTIFICATION | BSCF_SKIPDRAINDATAFORFILEURLS)),
679 "grcfBSCF = %08x\n", grfBSCF);
680 }else if(direct_read) {
684 if(!read_report_data && rec_depth == 1) {
685 BOOL reported_all_data = called_ReportData2;
687 CHECK_EXPECT2(ReportData);
690 ok(grfBSCF == (BSCF_FIRSTDATANOTIFICATION|BSCF_LASTDATANOTIFICATION|BSCF_DATAFULLYAVAILABLE)
691 || grfBSCF == BSCF_FIRSTDATANOTIFICATION, /* < IE8 */
692 "grcfBSCF = %08x\n", grfBSCF);
693 CHECK_CALLED(Read); /* Set in Continue */
694 first_data_notif = FALSE;
695 }else if(first_data_notif) {
696 ok(grfBSCF == BSCF_FIRSTDATANOTIFICATION, "grcfBSCF = %08x\n", grfBSCF);
697 first_data_notif = FALSE;
698 }else if(reported_all_data) {
699 ok(grfBSCF == (BSCF_LASTDATANOTIFICATION|BSCF_INTERMEDIATEDATANOTIFICATION),
700 "grcfBSCF = %08x\n", grfBSCF);
701 }else if(!direct_read) {
702 ok(grfBSCF == BSCF_INTERMEDIATEDATANOTIFICATION, "grcfBSCF = %08x\n", grfBSCF);
710 SET_EXPECT(ReportData2);
711 SET_EXPECT(ReportResult);
712 hres = IInternetProtocol_Read(binding_test ? binding_protocol : async_protocol, expect_pv = buf, sizeof(buf), &read);
714 ok(read, "read == 0\n");
715 if(reported_all_data) {
716 ok(hres == S_FALSE, "Read failed: %08x, expected S_FALSE\n", hres);
720 if(!reported_all_data && called_ReportData2) {
722 CHECK_CALLED(ReportData2);
723 CHECK_CALLED(ReportResult);
724 ok(hres == S_OK, "Read failed: %08x\n", hres);
725 reported_all_data = TRUE;
728 CHECK_NOT_CALLED(ReportData2);
729 CHECK_NOT_CALLED(ReportResult);
731 }while(hres == S_OK);
733 wait_for_switch = FALSE;
735 CHECK_EXPECT(ReportData2);
737 ok(grfBSCF & BSCF_LASTDATANOTIFICATION, "grfBSCF = %08x\n", grfBSCF);
742 hres = IInternetProtocol_Read(binding_test ? binding_protocol : async_protocol, expect_pv = buf, sizeof(buf), &read);
745 ok(hres == S_FALSE, "Read returned: %08x, expected E_FALSE\n", hres);
746 ok(!read, "read = %d\n", read);
748 }else if(!binding_test && (tested_protocol == HTTP_TEST || tested_protocol == HTTPS_TEST
749 || tested_protocol == FTP_TEST)) {
750 if(!(grfBSCF & BSCF_LASTDATANOTIFICATION) || (grfBSCF & BSCF_DATAFULLYAVAILABLE))
751 CHECK_EXPECT(ReportData);
752 else if (http_post_test)
753 ok(ulProgress == 13, "Read %u bytes instead of 13\n", ulProgress);
755 ok(ulProgress, "ulProgress == 0\n");
757 if(first_data_notif) {
758 ok(grfBSCF == BSCF_FIRSTDATANOTIFICATION
759 || grfBSCF == (BSCF_LASTDATANOTIFICATION|BSCF_DATAFULLYAVAILABLE),
760 "grcfBSCF = %08x\n", grfBSCF);
761 first_data_notif = FALSE;
763 ok(grfBSCF == BSCF_INTERMEDIATEDATANOTIFICATION
764 || grfBSCF == (BSCF_LASTDATANOTIFICATION|BSCF_INTERMEDIATEDATANOTIFICATION)
765 || broken(grfBSCF == (BSCF_FIRSTDATANOTIFICATION|BSCF_LASTDATANOTIFICATION)),
766 "grcfBSCF = %08x\n", grfBSCF);
769 if(!(bindf & BINDF_FROMURLMON) &&
770 !(grfBSCF & BSCF_LASTDATANOTIFICATION)) {
774 CHECK_CALLED(ReportProgress_FINDINGRESOURCE);
775 CHECK_CALLED(ReportProgress_CONNECTING);
777 CHECK_NOT_CALLED(ReportProgress_FINDINGRESOURCE);
778 CHECK_NOT_CALLED(ReportProgress_CONNECTING);
780 CHECK_CALLED(ReportProgress_SENDINGREQUEST);
781 CHECK_CALLED(OnResponse);
782 CHECK_CALLED(ReportProgress_RAWMIMETYPE);
784 SetEvent(event_complete);
786 }else if(!read_report_data) {
791 CHECK_EXPECT(ReportData);
793 if(tested_protocol != BIND_TEST) {
796 SET_EXPECT(MimeFilter_Read);
797 else if(rec_depth > 1)
801 hres = IInternetProtocol_Read(binding_protocol, expect_pv=buf, sizeof(buf), &read);
803 CHECK_CALLED(MimeFilter_Read);
804 else if(rec_depth > 1)
808 }while(hres == S_OK);
816 static HRESULT WINAPI ProtocolSink_ReportResult(IInternetProtocolSink *iface, HRESULT hrResult,
817 DWORD dwError, LPCWSTR szResult)
819 CHECK_EXPECT(ReportResult);
821 if(tested_protocol == FTP_TEST)
822 ok(hrResult == E_PENDING || hrResult == S_OK, "hrResult = %08x, expected E_PENDING or S_OK\n", hrResult);
824 ok(hrResult == expect_hrResult, "hrResult = %08x, expected: %08x\n",
825 hrResult, expect_hrResult);
826 if(SUCCEEDED(hrResult) || tested_protocol == FTP_TEST)
827 ok(dwError == ERROR_SUCCESS, "dwError = %d, expected ERROR_SUCCESS\n", dwError);
829 ok(dwError != ERROR_SUCCESS ||
830 broken(tested_protocol == MK_TEST), /* Win9x, WinME and NT4 */
831 "dwError == ERROR_SUCCESS\n");
832 ok(!szResult, "szResult != NULL\n");
835 SET_EXPECT(ReportData); /* checked after main loop */
840 static IInternetProtocolSinkVtbl protocol_sink_vtbl = {
841 ProtocolSink_QueryInterface,
843 ProtocolSink_Release,
845 ProtocolSink_ReportProgress,
846 ProtocolSink_ReportData,
847 ProtocolSink_ReportResult
850 static IInternetProtocolSink protocol_sink = { &protocol_sink_vtbl };
852 static HRESULT WINAPI MimeProtocolSink_QueryInterface(IInternetProtocolSink *iface, REFIID riid, void **ppv)
854 ok(0, "unexpected call\n");
858 static ULONG WINAPI MimeProtocolSink_AddRef(IInternetProtocolSink *iface)
863 static ULONG WINAPI MimeProtocolSink_Release(IInternetProtocolSink *iface)
868 static HRESULT WINAPI MimeProtocolSink_Switch(IInternetProtocolSink *iface, PROTOCOLDATA *pProtocolData)
872 CHECK_EXPECT(MimeFilter_Switch);
875 hres = IInternetProtocolSink_Switch(filtered_sink, pProtocolData);
876 ok(hres == S_OK, "Switch failed: %08x\n", hres);
877 CHECK_CALLED(Switch);
882 static HRESULT WINAPI MimeProtocolSink_ReportProgress(IInternetProtocolSink *iface, ULONG ulStatusCode,
883 LPCWSTR szStatusText)
885 CHECK_EXPECT(MimeFilter_ReportProgress);
889 static HRESULT WINAPI MimeProtocolSink_ReportData(IInternetProtocolSink *iface, DWORD grfBSCF,
890 ULONG ulProgress, ULONG ulProgressMax)
896 CHECK_EXPECT(MimeFilter_ReportData);
900 hres = IInternetProtocol_Read(filtered_protocol, buf, sizeof(buf), &read);
901 if(tested_protocol == HTTP_TEST)
902 ok(hres == S_OK || hres == E_PENDING || hres == S_FALSE, "Read failed: %08x\n", hres);
904 ok(hres == S_OK, "Read failed: %08x\n", hres);
907 SET_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
908 hres = IInternetProtocolSink_ReportProgress(filtered_sink, BINDSTATUS_VERIFIEDMIMETYPEAVAILABLE, text_htmlW);
909 ok(hres == S_OK, "ReportProgress failed: %08x\n", hres);
910 CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
912 /* FIXME: test BINDSTATUS_CACHEFILENAMEAVAILABLE */
915 if(!read_report_data)
916 SET_EXPECT(ReportData);
917 hres = IInternetProtocolSink_ReportData(filtered_sink, grfBSCF, ulProgress, ulProgressMax);
918 ok(hres == S_OK, "ReportData failed: %08x\n", hres);
919 if(!read_report_data)
920 CHECK_CALLED(ReportData);
928 static HRESULT WINAPI MimeProtocolSink_ReportResult(IInternetProtocolSink *iface, HRESULT hrResult,
929 DWORD dwError, LPCWSTR szResult)
933 CHECK_EXPECT(MimeFilter_ReportResult);
935 ok(hrResult == S_OK, "hrResult = %08x\n", hrResult);
936 ok(dwError == ERROR_SUCCESS, "dwError = %u\n", dwError);
937 ok(!szResult, "szResult = %s\n", wine_dbgstr_w(szResult));
939 SET_EXPECT(ReportResult);
940 hres = IInternetProtocolSink_ReportResult(filtered_sink, hrResult, dwError, szResult);
941 ok(SUCCEEDED(hres), "ReportResult failed: %08x\n", hres);
942 CHECK_CALLED(ReportResult);
947 static IInternetProtocolSinkVtbl mime_protocol_sink_vtbl = {
948 MimeProtocolSink_QueryInterface,
949 MimeProtocolSink_AddRef,
950 MimeProtocolSink_Release,
951 MimeProtocolSink_Switch,
952 MimeProtocolSink_ReportProgress,
953 MimeProtocolSink_ReportData,
954 MimeProtocolSink_ReportResult
957 static IInternetProtocolSink mime_protocol_sink = { &mime_protocol_sink_vtbl };
959 static HRESULT QueryInterface(REFIID riid, void **ppv)
961 static const IID IID_undocumented = {0x58DFC7D0,0x5381,0x43E5,{0x9D,0x72,0x4C,0xDD,0xE4,0xCB,0x0F,0x1A}};
965 if(IsEqualGUID(&IID_IUnknown, riid) || IsEqualGUID(&IID_IInternetProtocolSink, riid))
966 *ppv = &protocol_sink;
967 if(IsEqualGUID(&IID_IServiceProvider, riid))
968 *ppv = &service_provider;
969 if(IsEqualGUID(&IID_IUriContainer, riid))
970 return E_NOINTERFACE; /* TODO */
972 /* NOTE: IE8 queries for undocumented {58DFC7D0-5381-43E5-9D72-4CDDE4CB0F1A} interface. */
973 if(IsEqualGUID(&IID_undocumented, riid))
974 return E_NOINTERFACE;
979 ok(0, "unexpected call %s\n", debugstr_guid(riid));
980 return E_NOINTERFACE;
983 static HRESULT WINAPI BindInfo_QueryInterface(IInternetBindInfo *iface, REFIID riid, void **ppv)
985 if(IsEqualGUID(&IID_IUnknown, riid) || IsEqualGUID(&IID_IInternetBindInfo, riid)) {
989 return E_NOINTERFACE;
992 static ULONG WINAPI BindInfo_AddRef(IInternetBindInfo *iface)
997 static ULONG WINAPI BindInfo_Release(IInternetBindInfo *iface)
1002 static HRESULT WINAPI BindInfo_GetBindInfo(IInternetBindInfo *iface, DWORD *grfBINDF, BINDINFO *pbindinfo)
1006 static const CHAR szPostData[] = "mode=Test";
1008 CHECK_EXPECT(GetBindInfo);
1010 ok(grfBINDF != NULL, "grfBINDF == NULL\n");
1011 ok(pbindinfo != NULL, "pbindinfo == NULL\n");
1012 ok(pbindinfo->cbSize == sizeof(BINDINFO), "wrong size of pbindinfo: %d\n", pbindinfo->cbSize);
1016 *grfBINDF |= BINDF_FROMURLMON;
1017 cbSize = pbindinfo->cbSize;
1018 memset(pbindinfo, 0, cbSize);
1019 pbindinfo->cbSize = cbSize;
1023 /* Must be GMEM_FIXED, GMEM_MOVABLE does not work properly
1024 * with urlmon on native (Win98 and WinXP) */
1025 U(pbindinfo->stgmedData).hGlobal = GlobalAlloc(GPTR, sizeof(szPostData));
1026 if (!U(pbindinfo->stgmedData).hGlobal)
1028 http_post_test = FALSE;
1029 skip("Out of memory\n");
1030 return E_OUTOFMEMORY;
1032 lstrcpy((LPSTR)U(pbindinfo->stgmedData).hGlobal, szPostData);
1033 pbindinfo->cbstgmedData = sizeof(szPostData)-1;
1034 pbindinfo->dwBindVerb = BINDVERB_POST;
1035 pbindinfo->stgmedData.tymed = TYMED_HGLOBAL;
1041 static HRESULT WINAPI BindInfo_GetBindString(IInternetBindInfo *iface, ULONG ulStringType,
1042 LPOLESTR *ppwzStr, ULONG cEl, ULONG *pcElFetched)
1044 ok(ppwzStr != NULL, "ppwzStr == NULL\n");
1045 ok(pcElFetched != NULL, "pcElFetched == NULL\n");
1047 switch(ulStringType) {
1048 case BINDSTRING_ACCEPT_MIMES:
1049 CHECK_EXPECT(GetBindString_ACCEPT_MIMES);
1050 ok(cEl == 256, "cEl=%d, expected 256\n", cEl);
1052 ok(*pcElFetched == 256, "*pcElFetched=%d, expected 256\n", *pcElFetched);
1056 *ppwzStr = CoTaskMemAlloc(sizeof(acc_mimeW));
1057 memcpy(*ppwzStr, acc_mimeW, sizeof(acc_mimeW));
1060 case BINDSTRING_USER_AGENT:
1061 CHECK_EXPECT(GetBindString_USER_AGENT);
1062 ok(cEl == 1, "cEl=%d, expected 1\n", cEl);
1064 ok(*pcElFetched == 0, "*pcElFetch=%d, expectd 0\n", *pcElFetched);
1068 *ppwzStr = CoTaskMemAlloc(sizeof(user_agentW));
1069 memcpy(*ppwzStr, user_agentW, sizeof(user_agentW));
1072 case BINDSTRING_POST_COOKIE:
1073 CHECK_EXPECT(GetBindString_POST_COOKIE);
1074 ok(cEl == 1, "cEl=%d, expected 1\n", cEl);
1076 ok(*pcElFetched == 0, "*pcElFetch=%d, expectd 0\n", *pcElFetched);
1078 case BINDSTRING_URL: {
1081 CHECK_EXPECT(GetBindString_URL);
1082 ok(cEl == 1, "cEl=%d, expected 1\n", cEl);
1083 ok(*pcElFetched == 0, "*pcElFetch=%d, expectd 0\n", *pcElFetched);
1086 size = (lstrlenW(binding_urls[tested_protocol])+1)*sizeof(WCHAR);
1087 *ppwzStr = CoTaskMemAlloc(size);
1088 memcpy(*ppwzStr, binding_urls[tested_protocol], size);
1092 ok(0, "unexpected call\n");
1098 static IInternetBindInfoVtbl bind_info_vtbl = {
1099 BindInfo_QueryInterface,
1102 BindInfo_GetBindInfo,
1103 BindInfo_GetBindString
1106 static IInternetBindInfo bind_info = { &bind_info_vtbl };
1108 static HRESULT WINAPI InternetPriority_QueryInterface(IInternetPriority *iface,
1109 REFIID riid, void **ppv)
1111 ok(0, "unexpected call\n");
1112 return E_NOINTERFACE;
1115 static ULONG WINAPI InternetPriority_AddRef(IInternetPriority *iface)
1120 static ULONG WINAPI InternetPriority_Release(IInternetPriority *iface)
1125 static HRESULT WINAPI InternetPriority_SetPriority(IInternetPriority *iface, LONG nPriority)
1127 CHECK_EXPECT(SetPriority);
1128 ok(nPriority == ex_priority, "nPriority=%d\n", nPriority);
1132 static HRESULT WINAPI InternetPriority_GetPriority(IInternetPriority *iface, LONG *pnPriority)
1134 ok(0, "unexpected call\n");
1139 static const IInternetPriorityVtbl InternetPriorityVtbl = {
1140 InternetPriority_QueryInterface,
1141 InternetPriority_AddRef,
1142 InternetPriority_Release,
1143 InternetPriority_SetPriority,
1144 InternetPriority_GetPriority
1147 static IInternetPriority InternetPriority = { &InternetPriorityVtbl };
1149 static ULONG WINAPI Protocol_AddRef(IInternetProtocol *iface)
1154 static ULONG WINAPI Protocol_Release(IInternetProtocol *iface)
1159 static HRESULT WINAPI Protocol_Abort(IInternetProtocol *iface, HRESULT hrReason,
1162 ok(0, "unexpected call\n");
1166 static HRESULT WINAPI Protocol_Suspend(IInternetProtocol *iface)
1168 ok(0, "unexpected call\n");
1172 static HRESULT WINAPI Protocol_Resume(IInternetProtocol *iface)
1174 ok(0, "unexpected call\n");
1178 static HRESULT WINAPI Protocol_Seek(IInternetProtocol *iface,
1179 LARGE_INTEGER dlibMove, DWORD dwOrigin, ULARGE_INTEGER *plibNewPosition)
1181 ok(0, "unexpected call\n");
1185 static HRESULT WINAPI ProtocolEmul_QueryInterface(IInternetProtocol *iface, REFIID riid, void **ppv)
1187 if(IsEqualGUID(&IID_IUnknown, riid) || IsEqualGUID(&IID_IInternetProtocol, riid)) {
1192 if(IsEqualGUID(&IID_IInternetProtocolEx, riid)) {
1193 trace("IID_IInternetProtocolEx not supported\n");
1195 return E_NOINTERFACE;
1198 if(IsEqualGUID(&IID_IInternetPriority, riid)) {
1199 *ppv = &InternetPriority;
1203 if(IsEqualGUID(&IID_IWinInetInfo, riid)) {
1204 CHECK_EXPECT(QueryInterface_IWinInetInfo);
1206 return E_NOINTERFACE;
1209 if(IsEqualGUID(&IID_IWinInetHttpInfo, riid)) {
1210 CHECK_EXPECT(QueryInterface_IWinInetHttpInfo);
1212 return E_NOINTERFACE;
1215 ok(0, "unexpected riid %s\n", debugstr_guid(riid));
1217 return E_NOINTERFACE;
1220 static DWORD WINAPI thread_proc(PVOID arg)
1224 memset(&protocoldata, -1, sizeof(protocoldata));
1228 SET_EXPECT(ReportProgress_FINDINGRESOURCE);
1229 hres = IInternetProtocolSink_ReportProgress(binding_sink,
1230 BINDSTATUS_FINDINGRESOURCE, hostW);
1231 CHECK_CALLED(ReportProgress_FINDINGRESOURCE);
1232 ok(hres == S_OK, "ReportProgress failed: %08x\n", hres);
1234 SET_EXPECT(ReportProgress_CONNECTING);
1235 hres = IInternetProtocolSink_ReportProgress(binding_sink,
1236 BINDSTATUS_CONNECTING, winehq_ipW);
1237 CHECK_CALLED(ReportProgress_CONNECTING);
1238 ok(hres == S_OK, "ReportProgress failed: %08x\n", hres);
1240 SET_EXPECT(ReportProgress_SENDINGREQUEST);
1241 hres = IInternetProtocolSink_ReportProgress(binding_sink,
1242 BINDSTATUS_SENDINGREQUEST, NULL);
1243 CHECK_CALLED(ReportProgress_SENDINGREQUEST);
1244 ok(hres == S_OK, "ReportProgress failed: %08x\n", hres);
1248 hres = IInternetProtocolSink_Switch(binding_sink, &protocoldata);
1249 CHECK_CALLED(Switch);
1250 ok(hres == S_OK, "Switch failed: %08x\n", hres);
1255 SET_EXPECT(MimeFilter_Switch);
1258 hres = IInternetProtocolSink_Switch(binding_sink, &protocoldata);
1259 ok(hres == S_OK, "Switch failed: %08x\n", hres);
1261 CHECK_CALLED(MimeFilter_Switch);
1263 CHECK_CALLED(Switch);
1267 SET_EXPECT(MimeFilter_Switch);
1270 hres = IInternetProtocolSink_Switch(binding_sink, &protocoldata);
1271 ok(hres == S_OK, "Switch failed: %08x\n", hres);
1273 CHECK_CALLED(MimeFilter_Switch);
1275 CHECK_CALLED(Switch);
1279 SET_EXPECT(MimeFilter_Switch);
1282 hres = IInternetProtocolSink_Switch(binding_sink, &protocoldata);
1283 ok(hres == S_OK, "Switch failed: %08x\n", hres);
1285 CHECK_CALLED(MimeFilter_Switch);
1287 CHECK_CALLED(Switch);
1290 SetEvent(event_complete);
1295 static HRESULT WINAPI ProtocolEmul_Start(IInternetProtocol *iface, LPCWSTR szUrl,
1296 IInternetProtocolSink *pOIProtSink, IInternetBindInfo *pOIBindInfo,
1297 DWORD grfPI, HANDLE_PTR dwReserved)
1299 BINDINFO bindinfo, exp_bindinfo;
1303 CHECK_EXPECT(Start);
1305 ok(pOIProtSink != NULL, "pOIProtSink == NULL\n");
1306 ok(pOIBindInfo != NULL, "pOIBindInfo == NULL\n");
1307 ok(pOIProtSink != &protocol_sink, "unexpected pOIProtSink\n");
1308 ok(pOIBindInfo != &bind_info, "unexpected pOIBindInfo\n");
1309 ok(!grfPI, "grfPI = %x\n", grfPI);
1310 ok(!dwReserved, "dwReserved = %lx\n", dwReserved);
1313 ok(pOIProtSink == binding_sink, "pOIProtSink != binding_sink\n");
1315 memset(&bindinfo, 0, sizeof(bindinfo));
1316 bindinfo.cbSize = sizeof(bindinfo);
1317 memcpy(&exp_bindinfo, &bindinfo, sizeof(bindinfo));
1318 SET_EXPECT(GetBindInfo);
1319 hres = IInternetBindInfo_GetBindInfo(pOIBindInfo, &cbindf, &bindinfo);
1320 ok(hres == S_OK, "GetBindInfo failed: %08x\n", hres);
1321 CHECK_CALLED(GetBindInfo);
1322 ok(cbindf == (bindf|BINDF_FROMURLMON), "bindf = %x, expected %x\n",
1323 cbindf, (bindf|BINDF_FROMURLMON));
1324 ok(!memcmp(&exp_bindinfo, &bindinfo, sizeof(bindinfo)), "unexpected bindinfo\n");
1325 pReleaseBindInfo(&bindinfo);
1327 SET_EXPECT(ReportProgress_SENDINGREQUEST);
1328 hres = IInternetProtocolSink_ReportProgress(pOIProtSink, BINDSTATUS_SENDINGREQUEST, emptyW);
1329 ok(hres == S_OK, "ReportProgress(BINDSTATUS_SENDINGREQUEST) failed: %08x\n", hres);
1330 CHECK_CALLED(ReportProgress_SENDINGREQUEST);
1332 if(tested_protocol == HTTP_TEST || tested_protocol == HTTPS_TEST) {
1333 IServiceProvider *service_provider;
1334 IHttpNegotiate *http_negotiate;
1335 IHttpNegotiate2 *http_negotiate2;
1336 LPWSTR ua = (LPWSTR)0xdeadbeef, accept_mimes[256];
1337 LPWSTR additional_headers = NULL;
1339 DWORD fetched = 0, size = 100;
1342 SET_EXPECT(GetBindString_USER_AGENT);
1343 hres = IInternetBindInfo_GetBindString(pOIBindInfo, BINDSTRING_USER_AGENT,
1345 CHECK_CALLED(GetBindString_USER_AGENT);
1346 ok(hres == S_OK, "GetBindString(BINDSTRING_USER_AGETNT) failed: %08x\n", hres);
1347 ok(fetched == 1, "fetched = %d, expected 254\n", fetched);
1348 ok(ua != NULL, "ua = %p\n", ua);
1349 ok(!strcmp_ww(ua, user_agentW), "unexpected user agent %s\n", wine_dbgstr_w(ua));
1353 SET_EXPECT(GetBindString_ACCEPT_MIMES);
1354 hres = IInternetBindInfo_GetBindString(pOIBindInfo, BINDSTRING_ACCEPT_MIMES,
1355 accept_mimes, 256, &fetched);
1356 CHECK_CALLED(GetBindString_ACCEPT_MIMES);
1359 "GetBindString(BINDSTRING_ACCEPT_MIMES) failed: %08x\n", hres);
1360 ok(fetched == 1, "fetched = %d, expected 1\n", fetched);
1361 ok(!strcmp_ww(acc_mimeW, accept_mimes[0]), "unexpected mimes %s\n", wine_dbgstr_w(accept_mimes[0]));
1362 CoTaskMemFree(accept_mimes[0]);
1364 hres = IInternetBindInfo_QueryInterface(pOIBindInfo, &IID_IServiceProvider,
1365 (void**)&service_provider);
1366 ok(hres == S_OK, "QueryInterface failed: %08x\n", hres);
1368 SET_EXPECT(QueryService_HttpNegotiate);
1369 hres = IServiceProvider_QueryService(service_provider, &IID_IHttpNegotiate,
1370 &IID_IHttpNegotiate, (void**)&http_negotiate);
1371 CHECK_CALLED(QueryService_HttpNegotiate);
1372 ok(hres == S_OK, "QueryService failed: %08x\n", hres);
1374 SET_EXPECT(BeginningTransaction);
1375 hres = IHttpNegotiate_BeginningTransaction(http_negotiate, binding_urls[tested_protocol],
1376 NULL, 0, &additional_headers);
1377 CHECK_CALLED(BeginningTransaction);
1378 IHttpNegotiate_Release(http_negotiate);
1379 ok(hres == S_OK, "BeginningTransction failed: %08x\n", hres);
1380 ok(additional_headers == NULL, "additional_headers=%p\n", additional_headers);
1382 SET_EXPECT(QueryService_HttpNegotiate);
1383 hres = IServiceProvider_QueryService(service_provider, &IID_IHttpNegotiate2,
1384 &IID_IHttpNegotiate2, (void**)&http_negotiate2);
1385 CHECK_CALLED(QueryService_HttpNegotiate);
1386 ok(hres == S_OK, "QueryService failed: %08x\n", hres);
1389 SET_EXPECT(GetRootSecurityId);
1390 hres = IHttpNegotiate2_GetRootSecurityId(http_negotiate2, sec_id, &size, 0);
1391 CHECK_CALLED(GetRootSecurityId);
1392 IHttpNegotiate2_Release(http_negotiate2);
1393 ok(hres == E_FAIL, "GetRootSecurityId failed: %08x, expected E_FAIL\n", hres);
1394 ok(size == 13, "size=%d\n", size);
1396 IServiceProvider_Release(service_provider);
1398 CreateThread(NULL, 0, thread_proc, NULL, 0, &tid);
1403 SET_EXPECT(ReportProgress_CACHEFILENAMEAVAILABLE);
1404 hres = IInternetProtocolSink_ReportProgress(pOIProtSink,
1405 BINDSTATUS_CACHEFILENAMEAVAILABLE, expect_wsz = emptyW);
1406 ok(hres == S_OK, "ReportProgress(BINDSTATUS_CACHEFILENAMEAVAILABLE) failed: %08x\n", hres);
1407 CHECK_CALLED(ReportProgress_CACHEFILENAMEAVAILABLE);
1409 if(mimefilter_test) {
1410 SET_EXPECT(MimeFilter_CreateInstance);
1411 SET_EXPECT(MimeFilter_Start);
1412 SET_EXPECT(ReportProgress_LOADINGMIMEHANDLER);
1414 SET_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
1415 hres = IInternetProtocolSink_ReportProgress(pOIProtSink, BINDSTATUS_VERIFIEDMIMETYPEAVAILABLE,
1416 mimefilter_test ? gzipW : (expect_wsz = text_htmlW));
1418 "ReportProgress(BINDSTATUS_VERIFIEDMIMETYPEAVAILABLE) failed: %08x\n", hres);
1419 if(mimefilter_test) {
1420 CHECK_CALLED(MimeFilter_CreateInstance);
1421 CHECK_CALLED(MimeFilter_Start);
1422 CHECK_CALLED(ReportProgress_LOADINGMIMEHANDLER);
1423 todo_wine CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
1425 CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
1429 SET_EXPECT(MimeFilter_ReportData);
1431 SET_EXPECT(ReportData);
1432 hres = IInternetProtocolSink_ReportData(pOIProtSink,
1433 BSCF_FIRSTDATANOTIFICATION | BSCF_LASTDATANOTIFICATION, 13, 13);
1434 ok(hres == S_OK, "ReportData failed: %08x\n", hres);
1436 CHECK_CALLED(MimeFilter_ReportData);
1438 CHECK_CALLED(ReportData);
1440 if(tested_protocol == BIND_TEST) {
1441 hres = IInternetProtocol_Terminate(binding_protocol, 0);
1442 ok(hres == E_FAIL, "Termiante failed: %08x\n", hres);
1446 SET_EXPECT(MimeFilter_ReportResult);
1448 SET_EXPECT(ReportResult);
1449 hres = IInternetProtocolSink_ReportResult(pOIProtSink, S_OK, 0, NULL);
1450 ok(hres == S_OK, "ReportResult failed: %08x\n", hres);
1452 CHECK_CALLED(MimeFilter_ReportResult);
1454 CHECK_CALLED(ReportResult);
1459 static HRESULT WINAPI ProtocolEmul_Continue(IInternetProtocol *iface,
1460 PROTOCOLDATA *pProtocolData)
1465 CHECK_EXPECT(Continue);
1467 ok(pProtocolData != NULL, "pProtocolData == NULL\n");
1468 if(!pProtocolData || tested_protocol == BIND_TEST)
1471 ok(pProtocolData != &protocoldata, "pProtocolData == &protocoldata\n");
1472 ok(pProtocolData->grfFlags == protocoldata.grfFlags, "grfFlags wrong %x/%x\n",
1473 pProtocolData->grfFlags, protocoldata.grfFlags );
1474 ok(pProtocolData->dwState == protocoldata.dwState, "dwState wrong %x/%x\n",
1475 pProtocolData->dwState, protocoldata.dwState );
1476 ok(pProtocolData->pData == protocoldata.pData, "pData wrong %p/%p\n",
1477 pProtocolData->pData, protocoldata.pData );
1478 ok(pProtocolData->cbData == protocoldata.cbData, "cbData wrong %x/%x\n",
1479 pProtocolData->cbData, protocoldata.cbData );
1482 switch(prot_state) {
1484 IServiceProvider *service_provider;
1485 IHttpNegotiate *http_negotiate;
1486 static WCHAR header[] = {'?',0};
1488 hres = IInternetProtocolSink_QueryInterface(binding_sink, &IID_IServiceProvider,
1489 (void**)&service_provider);
1490 ok(hres == S_OK, "Could not get IServiceProvicder\n");
1492 SET_EXPECT(QueryService_HttpNegotiate);
1493 hres = IServiceProvider_QueryService(service_provider, &IID_IHttpNegotiate,
1494 &IID_IHttpNegotiate, (void**)&http_negotiate);
1495 IServiceProvider_Release(service_provider);
1496 CHECK_CALLED(QueryService_HttpNegotiate);
1497 ok(hres == S_OK, "Could not get IHttpNegotiate\n");
1499 SET_EXPECT(OnResponse);
1500 hres = IHttpNegotiate_OnResponse(http_negotiate, 200, header, NULL, NULL);
1501 IHttpNegotiate_Release(http_negotiate);
1502 CHECK_CALLED(OnResponse);
1503 IHttpNegotiate_Release(http_negotiate);
1504 ok(hres == S_OK, "OnResponse failed: %08x\n", hres);
1506 if(mimefilter_test) {
1507 SET_EXPECT(MimeFilter_CreateInstance);
1508 SET_EXPECT(MimeFilter_Start);
1509 SET_EXPECT(ReportProgress_LOADINGMIMEHANDLER);
1510 }else if(!(pi & PI_MIMEVERIFICATION)) {
1511 SET_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
1513 hres = IInternetProtocolSink_ReportProgress(binding_sink,
1514 BINDSTATUS_MIMETYPEAVAILABLE, mimefilter_test ? gzipW : text_htmlW);
1515 if(mimefilter_test) {
1516 CHECK_CALLED(MimeFilter_CreateInstance);
1517 CHECK_CALLED(MimeFilter_Start);
1518 CHECK_CALLED(ReportProgress_LOADINGMIMEHANDLER);
1519 }else if(!(pi & PI_MIMEVERIFICATION)) {
1520 CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
1523 "ReportProgress(BINDSTATUS_MIMETYPEAVAILABLE) failed: %08x\n", hres);
1525 bscf |= BSCF_FIRSTDATANOTIFICATION;
1530 bscf = BSCF_INTERMEDIATEDATANOTIFICATION;
1535 if(mimefilter_test) {
1536 SET_EXPECT(MimeFilter_ReportData);
1537 }else if(pi & PI_MIMEVERIFICATION) {
1539 SET_EXPECT(Read); /* checked in ReportData for short_read */
1541 if(!mimefilter_test)
1542 SET_EXPECT(Read); /* checked in BINDSTATUS_MIMETYPEAVAILABLE or ReportData */
1543 SET_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
1546 SET_EXPECT(ReportData);
1548 SET_EXPECT(ReportData);
1551 hres = IInternetProtocolSink_ReportData(binding_sink, bscf, pr, 400);
1552 ok(hres == S_OK, "ReportData failed: %08x\n", hres);
1554 if(mimefilter_test) {
1555 SET_EXPECT(MimeFilter_ReportData);
1556 }else if(pi & PI_MIMEVERIFICATION) {
1557 if(!short_read && pr < 200)
1560 CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
1563 CHECK_CALLED(ReportData);
1572 static HRESULT WINAPI ProtocolEmul_Terminate(IInternetProtocol *iface, DWORD dwOptions)
1574 CHECK_EXPECT(Terminate);
1575 ok(!dwOptions, "dwOptions=%d\n", dwOptions);
1579 static HRESULT WINAPI ProtocolEmul_Read(IInternetProtocol *iface, void *pv,
1580 ULONG cb, ULONG *pcbRead)
1582 if(read_report_data)
1583 CHECK_EXPECT2(Read2);
1585 if(mimefilter_test || short_read) {
1586 if(!read_report_data)
1587 CHECK_EXPECT2(Read);
1588 }else if((pi & PI_MIMEVERIFICATION)) {
1589 if(!read_report_data)
1590 CHECK_EXPECT2(Read);
1592 if(prot_read < 300) {
1593 ok(pv != expect_pv, "pv == expect_pv\n");
1595 ok(cb == 2048-prot_read, "cb=%d\n", cb);
1597 ok(cb == 700, "cb=%d\n", cb);
1599 ok(expect_pv <= pv && (BYTE*)pv < (BYTE*)expect_pv + cb, "pv != expect_pv\n");
1602 if(!read_report_data)
1605 ok(pv == expect_pv, "pv != expect_pv\n");
1606 ok(cb == 1000, "cb=%d\n", cb);
1607 ok(!*pcbRead, "*pcbRead = %d\n", *pcbRead);
1609 ok(pcbRead != NULL, "pcbRead == NULL\n");
1611 if(prot_state == 3 || (short_read && prot_state != 4)) {
1616 SET_EXPECT(Read2); /* checked in BINDSTATUS_MIMETYPEAVAILABLE */
1617 SET_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
1620 SET_EXPECT(MimeFilter_ReportData);
1621 else if(direct_read)
1622 SET_EXPECT(ReportData2);
1624 hres = IInternetProtocolSink_ReportData(binding_sink,
1625 BSCF_LASTDATANOTIFICATION|BSCF_INTERMEDIATEDATANOTIFICATION, 0, 0);
1627 ok(hres == S_OK, "ReportData failed: %08x\n", hres);
1629 CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
1631 CHECK_CALLED(MimeFilter_ReportData);
1632 else if(direct_read)
1633 CHECK_CALLED(ReportData2);
1636 SET_EXPECT(MimeFilter_ReportResult);
1638 SET_EXPECT(ReportResult);
1639 hres = IInternetProtocolSink_ReportResult(binding_sink, S_OK, ERROR_SUCCESS, NULL);
1640 ok(hres == S_OK, "ReportResult failed: %08x\n", hres);
1642 CHECK_CALLED(MimeFilter_ReportResult);
1644 CHECK_CALLED(ReportResult);
1646 memset(pv, 'x', 100);
1647 prot_read += *pcbRead = 100;
1649 }if(prot_state == 4) {
1654 if((async_read_pending = !async_read_pending)) {
1656 return tested_protocol == HTTP_TEST || tested_protocol == HTTPS_TEST ? E_PENDING : S_FALSE;
1659 memset(pv, 'x', 100);
1660 prot_read += *pcbRead = 100;
1664 static HRESULT WINAPI ProtocolEmul_LockRequest(IInternetProtocol *iface, DWORD dwOptions)
1666 CHECK_EXPECT(LockRequest);
1667 ok(dwOptions == 0, "dwOptions=%x\n", dwOptions);
1671 static HRESULT WINAPI ProtocolEmul_UnlockRequest(IInternetProtocol *iface)
1673 CHECK_EXPECT(UnlockRequest);
1677 static const IInternetProtocolVtbl ProtocolVtbl = {
1678 ProtocolEmul_QueryInterface,
1682 ProtocolEmul_Continue,
1684 ProtocolEmul_Terminate,
1689 ProtocolEmul_LockRequest,
1690 ProtocolEmul_UnlockRequest
1693 static IInternetProtocol Protocol = { &ProtocolVtbl };
1695 static HRESULT WINAPI MimeProtocol_QueryInterface(IInternetProtocol *iface, REFIID riid, void **ppv)
1697 if(IsEqualGUID(&IID_IUnknown, riid) || IsEqualGUID(&IID_IInternetProtocol, riid)) {
1702 if(IsEqualGUID(&IID_IInternetProtocolSink, riid)) {
1703 *ppv = &mime_protocol_sink;
1707 ok(0, "unexpected riid %s\n", debugstr_guid(riid));
1709 return E_NOINTERFACE;
1712 static HRESULT WINAPI MimeProtocol_Start(IInternetProtocol *iface, LPCWSTR szUrl,
1713 IInternetProtocolSink *pOIProtSink, IInternetBindInfo *pOIBindInfo,
1714 DWORD grfPI, HANDLE_PTR dwReserved)
1716 PROTOCOLFILTERDATA *data;
1717 LPOLESTR url_str = NULL;
1723 CHECK_EXPECT(MimeFilter_Start);
1725 ok(!strcmp_ww(szUrl, gzipW), "wrong url %s\n", wine_dbgstr_w(szUrl));
1726 ok(grfPI == (PI_FILTER_MODE|PI_FORCE_ASYNC), "grfPI=%x, expected PI_FILTER_MODE|PI_FORCE_ASYNC\n", grfPI);
1727 ok(dwReserved, "dwReserved == 0\n");
1728 ok(pOIProtSink != NULL, "pOIProtSink == NULL\n");
1729 ok(pOIBindInfo != NULL, "pOIBindInfo == NULL\n");
1732 ok(pOIProtSink != binding_sink, "pOIProtSink == protocol_sink\n");
1733 ok(pOIBindInfo == prot_bind_info, "pOIBindInfo != bind_info\n");
1735 ok(pOIProtSink == &protocol_sink, "pOIProtSink != protocol_sink\n");
1736 ok(pOIBindInfo == &bind_info, "pOIBindInfo != bind_info\n");
1739 data = (void*)dwReserved;
1740 ok(data->cbSize == sizeof(*data), "data->cbSize = %d\n", data->cbSize);
1741 ok(!data->pProtocolSink, "data->pProtocolSink != NULL\n");
1742 ok(data->pProtocol != NULL, "data->pProtocol == NULL\n");
1743 ok(!data->pUnk, "data->pUnk != NULL\n");
1744 ok(!data->dwFilterFlags, "data->dwProtocolFlags = %x\n", data->dwFilterFlags);
1746 IInternetProtocolSink *prot_sink;
1748 IInternetProtocol_QueryInterface(data->pProtocol, &IID_IInternetProtocolSink, (void**)&prot_sink);
1749 ok(prot_sink == pOIProtSink, "QI(data->pProtocol, IID_IInternetProtocolSink) != pOIProtSink\n");
1750 IInternetProtocolSink_Release(prot_sink);
1752 ok(data->pProtocol != binding_protocol, "data->pProtocol == binding_protocol\n");
1754 filtered_protocol = data->pProtocol;
1755 IInternetProtocol_AddRef(filtered_protocol);
1757 IInternetProtocol *prot;
1759 IInternetProtocol_QueryInterface(data->pProtocol, &IID_IInternetProtocol, (void**)&prot);
1760 ok(prot == async_protocol, "QI(data->pProtocol, IID_IInternetProtocol) != async_protocol\n");
1761 IInternetProtocol_Release(prot);
1763 ok(data->pProtocol != async_protocol, "data->pProtocol == async_protocol\n");
1766 filtered_sink = pOIProtSink;
1768 SET_EXPECT(ReportProgress_DECODING);
1769 hres = IInternetProtocolSink_ReportProgress(pOIProtSink, BINDSTATUS_DECODING, gzipW);
1770 ok(hres == S_OK, "ReportProgress(BINDSTATUS_DECODING) failed: %08x\n", hres);
1771 CHECK_CALLED(ReportProgress_DECODING);
1773 SET_EXPECT(GetBindInfo);
1774 memset(&bindinfo, 0, sizeof(bindinfo));
1775 bindinfo.cbSize = sizeof(bindinfo);
1776 hres = IInternetBindInfo_GetBindInfo(pOIBindInfo, &cbindf, &bindinfo);
1777 ok(hres == S_OK, "GetBindInfo failed: %08x\n", hres);
1778 ok(cbindf == (bindf|BINDF_FROMURLMON), "cbindf = %x, expected %x\n", cbindf, bindf);
1779 CHECK_CALLED(GetBindInfo);
1781 SET_EXPECT(GetBindString_URL);
1782 hres = IInternetBindInfo_GetBindString(pOIBindInfo, BINDSTRING_URL, &url_str, 1, &fetched);
1783 ok(hres == S_OK, "GetBindString(BINDSTRING_URL) failed: %08x\n", hres);
1784 ok(fetched == 1, "fetched = %d\n", fetched);
1785 ok(!strcmp_ww(url_str, binding_urls[tested_protocol]), "wrong url_str %s\n", wine_dbgstr_w(url_str));
1786 CoTaskMemFree(url_str);
1787 CHECK_CALLED(GetBindString_URL);
1792 static HRESULT WINAPI Protocol_Continue(IInternetProtocol *iface,
1793 PROTOCOLDATA *pProtocolData)
1795 CHECK_EXPECT(MimeFilter_Continue);
1799 static HRESULT WINAPI MimeProtocol_Terminate(IInternetProtocol *iface, DWORD dwOptions)
1803 CHECK_EXPECT(MimeFilter_Terminate);
1805 ok(!dwOptions, "dwOptions = %x\n", dwOptions);
1807 SET_EXPECT(Terminate);
1808 hres = IInternetProtocol_Terminate(filtered_protocol, dwOptions);
1809 ok(hres == S_OK, "Terminate failed: %08x\n", hres);
1810 CHECK_CALLED(Terminate);
1815 static HRESULT WINAPI MimeProtocol_Read(IInternetProtocol *iface, void *pv,
1816 ULONG cb, ULONG *pcbRead)
1822 CHECK_EXPECT(MimeFilter_Read);
1824 ok(pv != NULL, "pv == NULL\n");
1825 ok(cb != 0, "cb == 0\n");
1826 ok(pcbRead != NULL, "pcbRead == NULL\n");
1828 if(read_report_data)
1832 hres = IInternetProtocol_Read(filtered_protocol, buf, sizeof(buf), &read);
1833 ok(hres == S_OK || hres == S_FALSE || hres == E_PENDING, "Read failed: %08x\n", hres);
1834 if(read_report_data)
1835 CHECK_CALLED(Read2);
1840 ok(*pcbRead == 0, "*pcbRead=%d, expected 0\n", *pcbRead);
1844 memset(pv, 'x', read);
1848 static HRESULT WINAPI MimeProtocol_LockRequest(IInternetProtocol *iface, DWORD dwOptions)
1852 CHECK_EXPECT(MimeFilter_LockRequest);
1854 ok(!dwOptions, "dwOptions = %x\n", dwOptions);
1856 SET_EXPECT(LockRequest);
1857 hres = IInternetProtocol_LockRequest(filtered_protocol, dwOptions);
1858 ok(hres == S_OK, "LockRequest failed: %08x\n", hres);
1859 CHECK_CALLED(LockRequest);
1864 static HRESULT WINAPI MimeProtocol_UnlockRequest(IInternetProtocol *iface)
1868 CHECK_EXPECT(MimeFilter_UnlockRequest);
1870 SET_EXPECT(UnlockRequest);
1871 hres = IInternetProtocol_UnlockRequest(filtered_protocol);
1872 ok(hres == S_OK, "UnlockRequest failed: %08x\n", hres);
1873 CHECK_CALLED(UnlockRequest);
1878 static const IInternetProtocolVtbl MimeProtocolVtbl = {
1879 MimeProtocol_QueryInterface,
1885 MimeProtocol_Terminate,
1890 MimeProtocol_LockRequest,
1891 MimeProtocol_UnlockRequest
1894 static IInternetProtocol MimeProtocol = { &MimeProtocolVtbl };
1896 static HRESULT WINAPI ClassFactory_QueryInterface(IClassFactory *iface, REFIID riid, void **ppv)
1898 ok(0, "unexpected call\n");
1899 return E_NOINTERFACE;
1902 static ULONG WINAPI ClassFactory_AddRef(IClassFactory *iface)
1907 static ULONG WINAPI ClassFactory_Release(IClassFactory *iface)
1912 static HRESULT WINAPI ClassFactory_CreateInstance(IClassFactory *iface, IUnknown *pOuter,
1913 REFIID riid, void **ppv)
1915 CHECK_EXPECT(CreateInstance);
1917 ok(pOuter == (IUnknown*)prot_bind_info, "pOuter != protocol_unk\n");
1918 ok(IsEqualGUID(&IID_IUnknown, riid), "unexpected riid %s\n", debugstr_guid(riid));
1919 ok(ppv != NULL, "ppv == NULL\n");
1925 static HRESULT WINAPI ClassFactory_LockServer(IClassFactory *iface, BOOL dolock)
1927 ok(0, "unexpected call\n");
1931 static const IClassFactoryVtbl ClassFactoryVtbl = {
1932 ClassFactory_QueryInterface,
1933 ClassFactory_AddRef,
1934 ClassFactory_Release,
1935 ClassFactory_CreateInstance,
1936 ClassFactory_LockServer
1939 static IClassFactory ClassFactory = { &ClassFactoryVtbl };
1941 static HRESULT WINAPI MimeFilter_CreateInstance(IClassFactory *iface, IUnknown *outer, REFIID riid, void **ppv)
1943 CHECK_EXPECT(MimeFilter_CreateInstance);
1945 ok(!outer, "outer = %p\n", outer);
1946 ok(IsEqualGUID(&IID_IInternetProtocol, riid), "unexpected riid %s\n", debugstr_guid(riid));
1948 *ppv = &MimeProtocol;
1952 static const IClassFactoryVtbl MimeFilterCFVtbl = {
1953 ClassFactory_QueryInterface,
1954 ClassFactory_AddRef,
1955 ClassFactory_Release,
1956 MimeFilter_CreateInstance,
1957 ClassFactory_LockServer
1960 static IClassFactory mimefilter_cf = { &MimeFilterCFVtbl };
1962 #define TEST_BINDING 0x01
1963 #define TEST_FILTER 0x02
1964 #define TEST_FIRST_HTTP 0x04
1965 #define TEST_DIRECT_READ 0x08
1966 #define TEST_POST 0x10
1967 #define TEST_EMULATEPROT 0x20
1968 #define TEST_SHORT_READ 0x40
1969 #define TEST_REDIRECT 0x80
1971 static void init_test(int prot, DWORD flags)
1973 tested_protocol = prot;
1974 binding_test = (flags & TEST_BINDING) != 0;
1975 first_data_notif = TRUE;
1978 async_read_pending = TRUE;
1979 mimefilter_test = (flags & TEST_FILTER) != 0;
1981 ResetEvent(event_complete);
1982 ResetEvent(event_complete2);
1983 ResetEvent(event_continue);
1984 ResetEvent(event_continue_done);
1985 async_protocol = binding_protocol = filtered_protocol = NULL;
1986 filtered_sink = NULL;
1987 http_is_first = (flags & TEST_FIRST_HTTP) != 0;
1988 first_data_notif = TRUE;
1990 direct_read = (flags & TEST_DIRECT_READ) != 0;
1991 http_post_test = (flags & TEST_POST) != 0;
1992 emulate_prot = (flags & TEST_EMULATEPROT) != 0;
1993 wait_for_switch = TRUE;
1994 short_read = (flags & TEST_SHORT_READ) != 0;
1995 test_redirect = (flags & TEST_REDIRECT) != 0;
1998 static void test_priority(IInternetProtocol *protocol)
2000 IInternetPriority *priority;
2004 hres = IInternetProtocol_QueryInterface(protocol, &IID_IInternetPriority,
2006 ok(hres == S_OK, "QueryInterface(IID_IInternetPriority) failed: %08x\n", hres);
2010 hres = IInternetPriority_GetPriority(priority, &pr);
2011 ok(hres == S_OK, "GetPriority failed: %08x\n", hres);
2012 ok(pr == 0, "pr=%d, expected 0\n", pr);
2014 hres = IInternetPriority_SetPriority(priority, 1);
2015 ok(hres == S_OK, "SetPriority failed: %08x\n", hres);
2017 hres = IInternetPriority_GetPriority(priority, &pr);
2018 ok(hres == S_OK, "GetPriority failed: %08x\n", hres);
2019 ok(pr == 1, "pr=%d, expected 1\n", pr);
2021 IInternetPriority_Release(priority);
2024 static BOOL file_protocol_start(IInternetProtocol *protocol, LPCWSTR url,
2025 IInternetProtocolEx *protocolex, IUri *uri, BOOL is_first)
2029 SET_EXPECT(GetBindInfo);
2030 if(!(bindf & BINDF_FROMURLMON))
2031 SET_EXPECT(ReportProgress_DIRECTBIND);
2033 SET_EXPECT(ReportProgress_SENDINGREQUEST);
2034 SET_EXPECT(ReportProgress_CACHEFILENAMEAVAILABLE);
2035 if(bindf & BINDF_FROMURLMON)
2036 SET_EXPECT(ReportProgress_VERIFIEDMIMETYPEAVAILABLE);
2038 SET_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
2040 SET_EXPECT(ReportData);
2042 SET_EXPECT(ReportResult);
2044 expect_hrResult = S_OK;
2047 hres = IInternetProtocolEx_StartEx(protocolex, uri, &protocol_sink, &bind_info, 0, 0);
2048 ok(hres == S_OK, "StartEx failed: %08x\n", hres);
2050 hres = IInternetProtocol_Start(protocol, url, &protocol_sink, &bind_info, 0, 0);
2051 if(hres == INET_E_RESOURCE_NOT_FOUND) {
2052 win_skip("Start failed\n");
2055 ok(hres == S_OK, "Start failed: %08x\n", hres);
2058 CHECK_CALLED(GetBindInfo);
2059 if(!(bindf & BINDF_FROMURLMON))
2060 CHECK_CALLED(ReportProgress_DIRECTBIND);
2062 CHECK_CALLED(ReportProgress_SENDINGREQUEST);
2063 CHECK_CALLED(ReportProgress_CACHEFILENAMEAVAILABLE);
2064 if(bindf & BINDF_FROMURLMON)
2065 CHECK_CALLED(ReportProgress_VERIFIEDMIMETYPEAVAILABLE);
2067 CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
2069 CHECK_CALLED(ReportData);
2071 CHECK_CALLED(ReportResult);
2076 static void test_file_protocol_url(LPCWSTR url)
2078 IInternetProtocolInfo *protocol_info;
2080 IClassFactory *factory;
2081 IInternetProtocol *protocol;
2086 hres = CoGetClassObject(&CLSID_FileProtocol, CLSCTX_INPROC_SERVER, NULL,
2087 &IID_IUnknown, (void**)&unk);
2088 ok(hres == S_OK, "CoGetClassObject failed: %08x\n", hres);
2092 hres = IUnknown_QueryInterface(unk, &IID_IInternetProtocolInfo, (void**)&protocol_info);
2093 ok(hres == E_NOINTERFACE,
2094 "Could not get IInternetProtocolInfo interface: %08x, expected E_NOINTERFACE\n", hres);
2096 hres = IUnknown_QueryInterface(unk, &IID_IClassFactory, (void**)&factory);
2097 ok(hres == S_OK, "Could not get IClassFactory interface\n");
2098 IUnknown_Release(unk);
2102 hres = IClassFactory_CreateInstance(factory, NULL, &IID_IInternetProtocol, (void**)&protocol);
2103 ok(hres == S_OK, "Could not get IInternetProtocol: %08x\n", hres);
2105 if(SUCCEEDED(hres)) {
2106 if(file_protocol_start(protocol, url, NULL, NULL, TRUE)) {
2107 hres = IInternetProtocol_Read(protocol, buf, 2, &cb);
2108 ok(hres == S_OK, "Read failed: %08x\n", hres);
2109 ok(cb == 2, "cb=%u expected 2\n", cb);
2110 hres = IInternetProtocol_Read(protocol, buf, sizeof(buf), &cb);
2111 ok(hres == S_FALSE, "Read failed: %08x\n", hres);
2112 hres = IInternetProtocol_Read(protocol, buf, sizeof(buf), &cb);
2113 ok(hres == S_FALSE, "Read failed: %08x expected S_FALSE\n", hres);
2114 ok(cb == 0, "cb=%u expected 0\n", cb);
2115 hres = IInternetProtocol_UnlockRequest(protocol);
2116 ok(hres == S_OK, "UnlockRequest failed: %08x\n", hres);
2119 if(file_protocol_start(protocol, url, NULL, NULL, FALSE)) {
2120 hres = IInternetProtocol_Read(protocol, buf, 2, &cb);
2121 ok(hres == S_FALSE, "Read failed: %08x\n", hres);
2122 hres = IInternetProtocol_LockRequest(protocol, 0);
2123 ok(hres == S_OK, "LockRequest failed: %08x\n", hres);
2124 hres = IInternetProtocol_UnlockRequest(protocol);
2125 ok(hres == S_OK, "UnlockRequest failed: %08x\n", hres);
2128 IInternetProtocol_Release(protocol);
2131 hres = IClassFactory_CreateInstance(factory, NULL, &IID_IInternetProtocol, (void**)&protocol);
2132 ok(hres == S_OK, "Could not get IInternetProtocol: %08x\n", hres);
2133 if(SUCCEEDED(hres)) {
2134 if(file_protocol_start(protocol, url, NULL, NULL, TRUE)) {
2135 hres = IInternetProtocol_LockRequest(protocol, 0);
2136 ok(hres == S_OK, "LockRequest failed: %08x\n", hres);
2137 hres = IInternetProtocol_Terminate(protocol, 0);
2138 ok(hres == S_OK, "Terminate failed: %08x\n", hres);
2139 hres = IInternetProtocol_Read(protocol, buf, 2, &cb);
2140 ok(hres == S_OK, "Read failed: %08x\n\n", hres);
2141 hres = IInternetProtocol_UnlockRequest(protocol);
2142 ok(hres == S_OK, "UnlockRequest failed: %08x\n", hres);
2143 hres = IInternetProtocol_Read(protocol, buf, 2, &cb);
2144 ok(hres == S_OK, "Read failed: %08x\n", hres);
2145 hres = IInternetProtocol_Terminate(protocol, 0);
2146 ok(hres == S_OK, "Terminate failed: %08x\n", hres);
2149 IInternetProtocol_Release(protocol);
2152 hres = IClassFactory_CreateInstance(factory, NULL, &IID_IInternetProtocol, (void**)&protocol);
2153 ok(hres == S_OK, "Could not get IInternetProtocol: %08x\n", hres);
2154 if(SUCCEEDED(hres)) {
2155 if(file_protocol_start(protocol, url, NULL, NULL, TRUE)) {
2156 hres = IInternetProtocol_Terminate(protocol, 0);
2157 ok(hres == S_OK, "Terminate failed: %08x\n", hres);
2158 hres = IInternetProtocol_Read(protocol, buf, 2, &cb);
2159 ok(hres == S_OK, "Read failed: %08x\n", hres);
2160 ok(cb == 2, "cb=%u expected 2\n", cb);
2163 IInternetProtocol_Release(protocol);
2167 IInternetProtocolEx *protocolex;
2170 hres = pCreateUri(url, Uri_CREATE_FILE_USE_DOS_PATH, 0, &uri);
2171 ok(hres == S_OK, "CreateUri failed: %08x\n", hres);
2173 hres = IClassFactory_CreateInstance(factory, NULL, &IID_IInternetProtocolEx, (void**)&protocolex);
2174 ok(hres == S_OK, "Could not get IInternetProtocolEx: %08x\n", hres);
2176 if(file_protocol_start(NULL, NULL, protocolex, uri, TRUE)) {
2177 hres = IInternetProtocolEx_Read(protocolex, buf, 2, &cb);
2178 ok(hres == S_OK, "Read failed: %08x\n", hres);
2179 hres = IInternetProtocolEx_LockRequest(protocolex, 0);
2180 ok(hres == S_OK, "LockRequest failed: %08x\n", hres);
2181 hres = IInternetProtocolEx_UnlockRequest(protocolex);
2182 ok(hres == S_OK, "UnlockRequest failed: %08x\n", hres);
2186 IInternetProtocolEx_Release(protocolex);
2188 win_skip("Skipping file protocol StartEx tests\n");
2191 IClassFactory_Release(factory);
2194 static void test_file_protocol_fail(void)
2196 IInternetProtocol *protocol;
2199 static const WCHAR index_url2[] =
2200 {'f','i','l','e',':','/','/','i','n','d','e','x','.','h','t','m','l',0};
2202 hres = CoCreateInstance(&CLSID_FileProtocol, NULL, CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER,
2203 &IID_IInternetProtocol, (void**)&protocol);
2204 ok(hres == S_OK, "CoCreateInstance failed: %08x\n", hres);
2208 SET_EXPECT(GetBindInfo);
2209 expect_hrResult = MK_E_SYNTAX;
2210 hres = IInternetProtocol_Start(protocol, wszIndexHtml, &protocol_sink, &bind_info, 0, 0);
2211 ok(hres == MK_E_SYNTAX ||
2212 hres == E_INVALIDARG,
2213 "Start failed: %08x, expected MK_E_SYNTAX or E_INVALIDARG\n", hres);
2214 CLEAR_CALLED(GetBindInfo); /* GetBindInfo not called in IE7 */
2216 SET_EXPECT(GetBindInfo);
2217 if(!(bindf & BINDF_FROMURLMON))
2218 SET_EXPECT(ReportProgress_DIRECTBIND);
2219 SET_EXPECT(ReportProgress_SENDINGREQUEST);
2220 SET_EXPECT(ReportResult);
2221 expect_hrResult = INET_E_RESOURCE_NOT_FOUND;
2222 hres = IInternetProtocol_Start(protocol, index_url, &protocol_sink, &bind_info, 0, 0);
2223 ok(hres == INET_E_RESOURCE_NOT_FOUND,
2224 "Start failed: %08x expected INET_E_RESOURCE_NOT_FOUND\n", hres);
2225 CHECK_CALLED(GetBindInfo);
2226 if(!(bindf & BINDF_FROMURLMON))
2227 CHECK_CALLED(ReportProgress_DIRECTBIND);
2228 CHECK_CALLED(ReportProgress_SENDINGREQUEST);
2229 CHECK_CALLED(ReportResult);
2231 IInternetProtocol_Release(protocol);
2233 hres = CoCreateInstance(&CLSID_FileProtocol, NULL, CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER,
2234 &IID_IInternetProtocol, (void**)&protocol);
2235 ok(hres == S_OK, "CoCreateInstance failed: %08x\n", hres);
2239 SET_EXPECT(GetBindInfo);
2240 if(!(bindf & BINDF_FROMURLMON))
2241 SET_EXPECT(ReportProgress_DIRECTBIND);
2242 SET_EXPECT(ReportProgress_SENDINGREQUEST);
2243 SET_EXPECT(ReportResult);
2244 expect_hrResult = INET_E_RESOURCE_NOT_FOUND;
2246 hres = IInternetProtocol_Start(protocol, index_url2, &protocol_sink, &bind_info, 0, 0);
2247 ok(hres == INET_E_RESOURCE_NOT_FOUND,
2248 "Start failed: %08x, expected INET_E_RESOURCE_NOT_FOUND\n", hres);
2249 CHECK_CALLED(GetBindInfo);
2250 if(!(bindf & BINDF_FROMURLMON))
2251 CHECK_CALLED(ReportProgress_DIRECTBIND);
2252 CHECK_CALLED(ReportProgress_SENDINGREQUEST);
2253 CHECK_CALLED(ReportResult);
2255 SET_EXPECT(GetBindInfo);
2256 hres = IInternetProtocol_Start(protocol, NULL, &protocol_sink, &bind_info, 0, 0);
2257 ok(hres == E_INVALIDARG, "Start failed: %08x, expected E_INVALIDARG\n", hres);
2258 CLEAR_CALLED(GetBindInfo); /* GetBindInfo not called in IE7 */
2260 SET_EXPECT(GetBindInfo);
2261 hres = IInternetProtocol_Start(protocol, emptyW, &protocol_sink, &bind_info, 0, 0);
2262 ok(hres == E_INVALIDARG, "Start failed: %08x, expected E_INVALIDARG\n", hres);
2263 CLEAR_CALLED(GetBindInfo); /* GetBindInfo not called in IE7 */
2265 IInternetProtocol_Release(protocol);
2268 static void test_file_protocol(void) {
2269 WCHAR buf[INTERNET_MAX_URL_LENGTH], file_name_buf[MAX_PATH];
2274 static const WCHAR wszFile[] = {'f','i','l','e',':',0};
2275 static const WCHAR wszFile2[] = {'f','i','l','e',':','/','/',0};
2276 static const WCHAR wszFile3[] = {'f','i','l','e',':','/','/','/',0};
2277 static const WCHAR wszFile4[] = {'f','i','l','e',':','\\','\\',0};
2278 static const char html_doc[] = "<HTML></HTML>";
2280 trace("Testing file protocol...\n");
2281 init_test(FILE_TEST, 0);
2283 SetLastError(0xdeadbeef);
2284 file = CreateFileW(wszIndexHtml, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS,
2285 FILE_ATTRIBUTE_NORMAL, NULL);
2286 if(!file && GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)
2288 win_skip("Detected Win9x or WinMe\n");
2291 ok(file != INVALID_HANDLE_VALUE, "CreateFile failed\n");
2292 if(file == INVALID_HANDLE_VALUE)
2294 WriteFile(file, html_doc, sizeof(html_doc)-1, &size, NULL);
2297 file_name = wszIndexHtml;
2299 test_file_protocol_url(index_url);
2300 bindf = BINDF_FROMURLMON;
2301 test_file_protocol_url(index_url);
2302 bindf = BINDF_FROMURLMON | BINDF_NEEDFILE;
2303 test_file_protocol_url(index_url);
2305 memcpy(buf, wszFile, sizeof(wszFile));
2306 len = sizeof(wszFile)/sizeof(WCHAR)-1;
2307 len += GetCurrentDirectoryW(sizeof(buf)/sizeof(WCHAR)-len, buf+len);
2309 memcpy(buf+len, wszIndexHtml, sizeof(wszIndexHtml));
2311 file_name = buf + sizeof(wszFile)/sizeof(WCHAR)-1;
2313 test_file_protocol_url(buf);
2314 bindf = BINDF_FROMURLMON;
2315 test_file_protocol_url(buf);
2317 memcpy(buf, wszFile2, sizeof(wszFile2));
2318 len = GetCurrentDirectoryW(sizeof(file_name_buf)/sizeof(WCHAR), file_name_buf);
2319 file_name_buf[len++] = '\\';
2320 memcpy(file_name_buf+len, wszIndexHtml, sizeof(wszIndexHtml));
2321 lstrcpyW(buf+sizeof(wszFile2)/sizeof(WCHAR)-1, file_name_buf);
2322 file_name = file_name_buf;
2324 test_file_protocol_url(buf);
2325 bindf = BINDF_FROMURLMON;
2326 test_file_protocol_url(buf);
2328 buf[sizeof(wszFile2)/sizeof(WCHAR)] = '|';
2329 test_file_protocol_url(buf);
2331 memcpy(buf, wszFile3, sizeof(wszFile3));
2332 len = sizeof(wszFile3)/sizeof(WCHAR)-1;
2333 len += GetCurrentDirectoryW(sizeof(buf)/sizeof(WCHAR)-len, buf+len);
2335 memcpy(buf+len, wszIndexHtml, sizeof(wszIndexHtml));
2337 file_name = buf + sizeof(wszFile3)/sizeof(WCHAR)-1;
2339 test_file_protocol_url(buf);
2340 bindf = BINDF_FROMURLMON;
2341 test_file_protocol_url(buf);
2343 memcpy(buf, wszFile4, sizeof(wszFile4));
2344 len = GetCurrentDirectoryW(sizeof(file_name_buf)/sizeof(WCHAR), file_name_buf);
2345 file_name_buf[len++] = '\\';
2346 memcpy(file_name_buf+len, wszIndexHtml, sizeof(wszIndexHtml));
2347 lstrcpyW(buf+sizeof(wszFile4)/sizeof(WCHAR)-1, file_name_buf);
2348 file_name = file_name_buf;
2350 test_file_protocol_url(buf);
2351 bindf = BINDF_FROMURLMON;
2352 test_file_protocol_url(buf);
2354 buf[sizeof(wszFile4)/sizeof(WCHAR)] = '|';
2355 test_file_protocol_url(buf);
2357 DeleteFileW(wszIndexHtml);
2360 test_file_protocol_fail();
2361 bindf = BINDF_FROMURLMON;
2362 test_file_protocol_fail();
2365 static BOOL http_protocol_start(LPCWSTR url)
2367 static BOOL got_user_agent = FALSE;
2370 SET_EXPECT(GetBindInfo);
2371 if (!(bindf & BINDF_FROMURLMON))
2372 SET_EXPECT(ReportProgress_DIRECTBIND);
2374 SET_EXPECT(GetBindString_USER_AGENT);
2375 SET_EXPECT(GetBindString_ACCEPT_MIMES);
2376 SET_EXPECT(QueryService_HttpNegotiate);
2377 SET_EXPECT(BeginningTransaction);
2378 SET_EXPECT(GetRootSecurityId);
2380 SET_EXPECT(GetBindString_POST_COOKIE);
2382 hres = IInternetProtocol_Start(async_protocol, url, &protocol_sink, &bind_info, 0, 0);
2383 ok(hres == S_OK, "Start failed: %08x\n", hres);
2387 CHECK_CALLED(GetBindInfo);
2388 if (!(bindf & BINDF_FROMURLMON))
2389 CHECK_CALLED(ReportProgress_DIRECTBIND);
2390 if (!got_user_agent)
2392 CHECK_CALLED(GetBindString_USER_AGENT);
2393 got_user_agent = TRUE;
2395 CHECK_CALLED(GetBindString_ACCEPT_MIMES);
2396 CHECK_CALLED(QueryService_HttpNegotiate);
2397 CHECK_CALLED(BeginningTransaction);
2398 /* GetRootSecurityId called on WinXP but not on Win98 */
2399 CLEAR_CALLED(GetRootSecurityId);
2401 CHECK_CALLED(GetBindString_POST_COOKIE);
2406 static void test_protocol_terminate(IInternetProtocol *protocol)
2412 hres = IInternetProtocol_LockRequest(protocol, 0);
2413 ok(hres == S_OK, "LockRequest failed: %08x\n", hres);
2415 hres = IInternetProtocol_Read(protocol, buf, 1, &cb);
2416 ok(hres == S_FALSE, "Read failed: %08x\n", hres);
2418 hres = IInternetProtocol_Terminate(protocol, 0);
2419 ok(hres == S_OK, "Terminate failed: %08x\n", hres);
2421 /* This wait is to give the internet handles being freed in Terminate
2422 * enough time to actually terminate in all cases. Internet handles
2423 * terminate asynchronously and native reuses the main InternetOpen
2424 * handle. The only case in which this seems to be necessary is on
2425 * wine with native wininet and urlmon, resulting in the next time
2426 * test_http_protocol_url being called the first data notification actually
2427 * being an extra last data notification from the previous connection
2428 * about once out of every ten times. */
2431 hres = IInternetProtocol_UnlockRequest(protocol);
2432 ok(hres == S_OK, "UnlockRequest failed: %08x\n", hres);
2435 static void test_http_info(IInternetProtocol *protocol)
2437 IWinInetHttpInfo *info;
2440 hres = IInternetProtocol_QueryInterface(protocol, &IID_IWinInetHttpInfo, (void**)&info);
2441 ok(hres == S_OK, "Could not get IWinInterHttpInfo iface: %08x\n", hres);
2445 IWinInetHttpInfo_Release(info);
2448 /* is_first refers to whether this is the first call to this function
2450 static void test_http_protocol_url(LPCWSTR url, int prot, DWORD flags)
2452 IInternetProtocolInfo *protocol_info;
2453 IClassFactory *factory;
2457 init_test(prot, flags);
2460 hres = CoGetClassObject(prot == HTTPS_TEST ? &CLSID_HttpSProtocol : &CLSID_HttpProtocol,
2461 CLSCTX_INPROC_SERVER, NULL, &IID_IUnknown, (void**)&unk);
2462 ok(hres == S_OK, "CoGetClassObject failed: %08x\n", hres);
2466 hres = IUnknown_QueryInterface(unk, &IID_IInternetProtocolInfo, (void**)&protocol_info);
2467 ok(hres == E_NOINTERFACE,
2468 "Could not get IInternetProtocolInfo interface: %08x, expected E_NOINTERFACE\n",
2471 hres = IUnknown_QueryInterface(unk, &IID_IClassFactory, (void**)&factory);
2472 ok(hres == S_OK, "Could not get IClassFactory interface\n");
2473 IUnknown_Release(unk);
2477 hres = IClassFactory_CreateInstance(factory, NULL, &IID_IInternetProtocol,
2478 (void**)&async_protocol);
2479 ok(hres == S_OK, "Could not get IInternetProtocol: %08x\n", hres);
2480 if(SUCCEEDED(hres)) {
2485 test_priority(async_protocol);
2486 test_http_info(async_protocol);
2488 SET_EXPECT(ReportProgress_COOKIE_SENT);
2489 SET_EXPECT(ReportProgress_FINDINGRESOURCE);
2490 SET_EXPECT(ReportProgress_CONNECTING);
2491 SET_EXPECT(ReportProgress_SENDINGREQUEST);
2493 SET_EXPECT(ReportProgress_REDIRECTING);
2494 SET_EXPECT(ReportProgress_PROXYDETECTING);
2495 if(prot == HTTP_TEST)
2496 SET_EXPECT(ReportProgress_CACHEFILENAMEAVAILABLE);
2498 SET_EXPECT(QueryService_HttpSecurity);
2499 if(!(bindf & BINDF_FROMURLMON)) {
2500 SET_EXPECT(OnResponse);
2501 SET_EXPECT(ReportProgress_RAWMIMETYPE);
2502 SET_EXPECT(ReportData);
2507 if(!http_protocol_start(url))
2511 SET_EXPECT(ReportResult);
2512 expect_hrResult = S_OK;
2515 while(wait_for_switch) {
2517 WaitForSingleObject(event_continue, INFINITE);
2518 CHECK_CALLED(Switch);
2519 call_continue(&continue_protdata);
2520 SetEvent(event_continue_done);
2523 hres = IInternetProtocol_Read(async_protocol, buf, 1, &cb);
2524 ok((hres == E_PENDING && cb==0) ||
2525 (hres == S_OK && cb==1), "Read failed: %08x (%d bytes)\n", hres, cb);
2527 WaitForSingleObject(event_complete, INFINITE);
2528 if(bindf & BINDF_FROMURLMON)
2529 CHECK_CALLED(Switch);
2531 CHECK_CALLED(ReportData);
2532 if(prot == HTTPS_TEST)
2533 CLEAR_CALLED(QueryService_HttpSecurity);
2536 if(bindf & BINDF_FROMURLMON)
2539 SET_EXPECT(ReportData);
2540 hres = IInternetProtocol_Read(async_protocol, buf, sizeof(buf), &cb);
2541 if(hres == E_PENDING) {
2542 hres = IInternetProtocol_Read(async_protocol, buf, 1, &cb);
2543 ok((hres == E_PENDING && cb==0) ||
2544 (hres == S_OK && cb==1), "Read failed: %08x (%d bytes)\n", hres, cb);
2545 WaitForSingleObject(event_complete, INFINITE);
2546 if(bindf & BINDF_FROMURLMON)
2547 CHECK_CALLED(Switch);
2549 CHECK_CALLED(ReportData);
2551 if(bindf & BINDF_FROMURLMON)
2552 CHECK_NOT_CALLED(Switch);
2554 CHECK_NOT_CALLED(ReportData);
2558 ok(hres == S_FALSE, "Read failed: %08x\n", hres);
2559 CHECK_CALLED(ReportResult);
2561 if(prot == HTTPS_TEST)
2562 CLEAR_CALLED(ReportProgress_SENDINGREQUEST);
2564 test_protocol_terminate(async_protocol);
2565 ref = IInternetProtocol_Release(async_protocol);
2566 ok(!ref, "ref=%x\n", hres);
2569 IClassFactory_Release(factory);
2572 static void test_http_protocol(void)
2574 static const WCHAR winehq_url[] =
2575 {'h','t','t','p',':','/','/','w','w','w','.','w','i','n','e','h','q','.',
2576 'o','r','g','/','s','i','t','e','/','a','b','o','u','t',0};
2577 static const WCHAR posttest_url[] =
2578 {'h','t','t','p',':','/','/','c','r','o','s','s','o','v','e','r','.',
2579 'c','o','d','e','w','e','a','v','e','r','s','.','c','o','m','/',
2580 'p','o','s','t','t','e','s','t','.','p','h','p',0};
2581 static const WCHAR redirect_url[] =
2582 {'h','t','t','p',':','/','/','t','e','s','t','.','w','i','n','e','h','q','.','o','r','g','/',
2583 't','e','s','t','r','e','d','i','r','e','c','t',0};
2585 trace("Testing http protocol (not from urlmon)...\n");
2586 bindf = BINDF_ASYNCHRONOUS | BINDF_ASYNCSTORAGE | BINDF_PULLDATA;
2587 test_http_protocol_url(winehq_url, HTTP_TEST, TEST_FIRST_HTTP);
2589 trace("Testing http protocol (from urlmon)...\n");
2590 bindf = BINDF_ASYNCHRONOUS | BINDF_ASYNCSTORAGE | BINDF_PULLDATA | BINDF_FROMURLMON;
2591 test_http_protocol_url(winehq_url, HTTP_TEST, 0);
2593 trace("Testing http protocol (to file)...\n");
2594 bindf = BINDF_ASYNCHRONOUS | BINDF_ASYNCSTORAGE | BINDF_PULLDATA | BINDF_FROMURLMON | BINDF_NEEDFILE;
2595 test_http_protocol_url(winehq_url, HTTP_TEST, 0);
2597 trace("Testing http protocol (post data)...\n");
2598 /* Without this flag we get a ReportProgress_CACHEFILENAMEAVAILABLE
2599 * notification with BINDVERB_POST */
2600 bindf = BINDF_ASYNCHRONOUS | BINDF_ASYNCSTORAGE | BINDF_PULLDATA | BINDF_FROMURLMON | BINDF_NOWRITECACHE;
2601 test_http_protocol_url(posttest_url, HTTP_TEST, TEST_FIRST_HTTP|TEST_POST);
2603 trace("Testing http protocol (direct read)...\n");
2604 bindf = BINDF_ASYNCHRONOUS | BINDF_ASYNCSTORAGE | BINDF_PULLDATA | BINDF_FROMURLMON;
2605 test_http_protocol_url(winehq_url, HTTP_TEST, TEST_DIRECT_READ);
2607 trace("Testing http protocol (redirected)...\n");
2608 bindf = BINDF_ASYNCHRONOUS | BINDF_ASYNCSTORAGE | BINDF_PULLDATA | BINDF_FROMURLMON;
2609 test_http_protocol_url(redirect_url, HTTP_TEST, TEST_REDIRECT);
2612 static void test_https_protocol(void)
2614 static const WCHAR codeweavers_url[] =
2615 {'h','t','t','p','s',':','/','/','w','w','w','.','c','o','d','e','w','e','a','v','e','r','s',
2616 '.','c','o','m','/','t','e','s','t','.','h','t','m','l',0};
2618 trace("Testing https protocol (from urlmon)...\n");
2619 bindf = BINDF_ASYNCHRONOUS | BINDF_ASYNCSTORAGE | BINDF_PULLDATA | BINDF_FROMURLMON | BINDF_NOWRITECACHE;
2620 test_http_protocol_url(codeweavers_url, HTTPS_TEST, TEST_FIRST_HTTP);
2624 static void test_ftp_protocol(void)
2626 IInternetProtocolInfo *protocol_info;
2627 IClassFactory *factory;
2634 static const WCHAR ftp_urlW[] = {'f','t','p',':','/','/','f','t','p','.','w','i','n','e','h','q','.','o','r','g',
2635 '/','p','u','b','/','o','t','h','e','r','/',
2636 'w','i','n','e','l','o','g','o','.','x','c','f','.','t','a','r','.','b','z','2',0};
2638 trace("Testing ftp protocol...\n");
2640 bindf = BINDF_ASYNCHRONOUS | BINDF_ASYNCSTORAGE | BINDF_PULLDATA | BINDF_FROMURLMON | BINDF_NOWRITECACHE;
2642 tested_protocol = FTP_TEST;
2643 first_data_notif = TRUE;
2644 expect_hrResult = E_PENDING;
2646 hres = CoGetClassObject(&CLSID_FtpProtocol, CLSCTX_INPROC_SERVER, NULL, &IID_IUnknown, (void**)&unk);
2647 ok(hres == S_OK, "CoGetClassObject failed: %08x\n", hres);
2651 hres = IUnknown_QueryInterface(unk, &IID_IInternetProtocolInfo, (void**)&protocol_info);
2652 ok(hres == E_NOINTERFACE, "Could not get IInternetProtocolInfo interface: %08x, expected E_NOINTERFACE\n", hres);
2654 hres = IUnknown_QueryInterface(unk, &IID_IClassFactory, (void**)&factory);
2655 ok(hres == S_OK, "Could not get IClassFactory interface\n");
2656 IUnknown_Release(unk);
2660 hres = IClassFactory_CreateInstance(factory, NULL, &IID_IInternetProtocol,
2661 (void**)&async_protocol);
2662 IClassFactory_Release(factory);
2663 ok(hres == S_OK, "Could not get IInternetProtocol: %08x\n", hres);
2665 test_priority(async_protocol);
2666 test_http_info(async_protocol);
2668 SET_EXPECT(GetBindInfo);
2669 SET_EXPECT(ReportProgress_FINDINGRESOURCE);
2670 SET_EXPECT(ReportProgress_CONNECTING);
2671 SET_EXPECT(ReportProgress_SENDINGREQUEST);
2674 hres = IInternetProtocol_Start(async_protocol, ftp_urlW, &protocol_sink, &bind_info, 0, 0);
2675 ok(hres == S_OK, "Start failed: %08x\n", hres);
2676 CHECK_CALLED(GetBindInfo);
2678 SET_EXPECT(ReportResult);
2680 hres = IInternetProtocol_Read(async_protocol, buf, 1, &cb);
2681 ok((hres == E_PENDING && cb==0) ||
2682 (hres == S_OK && cb==1), "Read failed: %08x (%d bytes)\n", hres, cb);
2684 WaitForSingleObject(event_complete, INFINITE);
2688 hres = IInternetProtocol_Read(async_protocol, buf, sizeof(buf), &cb);
2689 if(hres == E_PENDING)
2690 WaitForSingleObject(event_complete, INFINITE);
2695 ok(hres == S_FALSE, "Read failed: %08x\n", hres);
2696 CHECK_CALLED(ReportResult);
2697 CHECK_CALLED(Switch);
2699 test_protocol_terminate(async_protocol);
2701 ref = IInternetProtocol_Release(async_protocol);
2702 ok(!ref, "ref=%d\n", ref);
2705 static void test_gopher_protocol(void)
2707 IInternetProtocolInfo *protocol_info;
2708 IClassFactory *factory;
2712 trace("Testing gopher protocol...\n");
2714 hres = CoGetClassObject(&CLSID_GopherProtocol, CLSCTX_INPROC_SERVER, NULL, &IID_IUnknown, (void**)&unk);
2716 hres == REGDB_E_CLASSNOTREG, /* Gopher protocol has been removed as of Vista */
2717 "CoGetClassObject failed: %08x\n", hres);
2721 hres = IUnknown_QueryInterface(unk, &IID_IInternetProtocolInfo, (void**)&protocol_info);
2722 ok(hres == E_NOINTERFACE, "Could not get IInternetProtocolInfo interface: %08x, expected E_NOINTERFACE\n", hres);
2724 hres = IUnknown_QueryInterface(unk, &IID_IClassFactory, (void**)&factory);
2725 ok(hres == S_OK, "Could not get IClassFactory interface\n");
2726 IUnknown_Release(unk);
2730 hres = IClassFactory_CreateInstance(factory, NULL, &IID_IInternetProtocol,
2731 (void**)&async_protocol);
2732 IClassFactory_Release(factory);
2733 ok(hres == S_OK, "Could not get IInternetProtocol: %08x\n", hres);
2735 test_priority(async_protocol);
2737 IInternetProtocol_Release(async_protocol);
2740 static void test_mk_protocol(void)
2742 IInternetProtocolInfo *protocol_info;
2743 IInternetProtocol *protocol;
2744 IClassFactory *factory;
2748 static const WCHAR wrong_url1[] = {'t','e','s','t',':','@','M','S','I','T','S','t','o','r','e',
2749 ':',':','/','t','e','s','t','.','h','t','m','l',0};
2750 static const WCHAR wrong_url2[] = {'m','k',':','/','t','e','s','t','.','h','t','m','l',0};
2752 trace("Testing mk protocol...\n");
2753 init_test(MK_TEST, 0);
2755 hres = CoGetClassObject(&CLSID_MkProtocol, CLSCTX_INPROC_SERVER, NULL,
2756 &IID_IUnknown, (void**)&unk);
2757 ok(hres == S_OK, "CoGetClassObject failed: %08x\n", hres);
2759 hres = IUnknown_QueryInterface(unk, &IID_IInternetProtocolInfo, (void**)&protocol_info);
2760 ok(hres == E_NOINTERFACE,
2761 "Could not get IInternetProtocolInfo interface: %08x, expected E_NOINTERFACE\n",
2764 hres = IUnknown_QueryInterface(unk, &IID_IClassFactory, (void**)&factory);
2765 ok(hres == S_OK, "Could not get IClassFactory interface\n");
2766 IUnknown_Release(unk);
2770 hres = IClassFactory_CreateInstance(factory, NULL, &IID_IInternetProtocol,
2772 IClassFactory_Release(factory);
2773 ok(hres == S_OK, "Could not get IInternetProtocol: %08x\n", hres);
2775 SET_EXPECT(GetBindInfo);
2776 hres = IInternetProtocol_Start(protocol, wrong_url1, &protocol_sink, &bind_info, 0, 0);
2777 ok(hres == MK_E_SYNTAX || hres == INET_E_INVALID_URL,
2778 "Start failed: %08x, expected MK_E_SYNTAX or INET_E_INVALID_URL\n", hres);
2779 CLEAR_CALLED(GetBindInfo);
2781 SET_EXPECT(GetBindInfo);
2782 SET_EXPECT(ReportProgress_DIRECTBIND);
2783 SET_EXPECT(ReportProgress_SENDINGREQUEST);
2784 SET_EXPECT(ReportProgress_MIMETYPEAVAILABLE);
2785 SET_EXPECT(ReportResult);
2786 expect_hrResult = INET_E_RESOURCE_NOT_FOUND;
2788 hres = IInternetProtocol_Start(protocol, wrong_url2, &protocol_sink, &bind_info, 0, 0);
2789 ok(hres == INET_E_RESOURCE_NOT_FOUND ||
2790 hres == INET_E_INVALID_URL, /* win2k3 */
2791 "Start failed: %08x, expected INET_E_RESOURCE_NOT_FOUND or INET_E_INVALID_URL\n", hres);
2793 if (hres == INET_E_RESOURCE_NOT_FOUND) {
2794 CHECK_CALLED(GetBindInfo);
2795 CLEAR_CALLED(ReportProgress_DIRECTBIND);
2796 CHECK_CALLED(ReportProgress_SENDINGREQUEST);
2797 CHECK_CALLED(ReportProgress_MIMETYPEAVAILABLE);
2798 CHECK_CALLED(ReportResult);
2800 CLEAR_CALLED(GetBindInfo);
2801 CLEAR_CALLED(ReportProgress_DIRECTBIND);
2802 CLEAR_CALLED(ReportProgress_SENDINGREQUEST);
2803 CLEAR_CALLED(ReportProgress_MIMETYPEAVAILABLE);
2804 CLEAR_CALLED(ReportResult);
2807 IInternetProtocol_Release(protocol);
2810 static void test_CreateBinding(void)
2812 IInternetProtocol *protocol;
2813 IInternetPriority *priority;
2814 IInternetSession *session;
2815 IWinInetHttpInfo *http_info;
2816 IWinInetInfo *inet_info;
2822 static const WCHAR test_url[] =
2823 {'t','e','s','t',':','/','/','f','i','l','e','.','h','t','m','l',0};
2824 static const WCHAR wsz_test[] = {'t','e','s','t',0};
2826 trace("Testing CreateBinding...\n");
2827 init_test(BIND_TEST, TEST_BINDING);
2829 hres = pCoInternetGetSession(0, &session, 0);
2830 ok(hres == S_OK, "CoInternetGetSession failed: %08x\n", hres);
2832 hres = IInternetSession_RegisterNameSpace(session, &ClassFactory, &IID_NULL, wsz_test, 0, NULL, 0);
2833 ok(hres == S_OK, "RegisterNameSpace failed: %08x\n", hres);
2835 hres = IInternetSession_CreateBinding(session, NULL, test_url, NULL, NULL, &protocol, 0);
2836 binding_protocol = protocol;
2837 ok(hres == S_OK, "CreateBinding failed: %08x\n", hres);
2838 ok(protocol != NULL, "protocol == NULL\n");
2840 hres = IInternetProtocol_QueryInterface(protocol, &IID_IInternetBindInfo, (void**)&prot_bind_info);
2841 ok(hres == S_OK, "QueryInterface(IID_IInternetBindInfo) failed: %08x\n", hres);
2843 hres = IInternetProtocol_QueryInterface(protocol, &IID_IInternetProtocolSink, (void**)&binding_sink);
2844 ok(hres == S_OK, "Could not get IInternetProtocolSink: %08x\n", hres);
2846 hres = IInternetProtocol_Start(protocol, test_url, NULL, &bind_info, 0, 0);
2847 ok(hres == E_INVALIDARG, "Start failed: %08x, expected E_INVALIDARG\n", hres);
2848 hres = IInternetProtocol_Start(protocol, test_url, &protocol_sink, NULL, 0, 0);
2849 ok(hres == E_INVALIDARG, "Start failed: %08x, expected E_INVALIDARG\n", hres);
2850 hres = IInternetProtocol_Start(protocol, NULL, &protocol_sink, &bind_info, 0, 0);
2851 ok(hres == E_INVALIDARG, "Start failed: %08x, expected E_INVALIDARG\n", hres);
2853 hres = IInternetProtocol_QueryInterface(protocol, &IID_IInternetPriority, (void**)&priority);
2854 ok(hres == S_OK, "QueryInterface(IID_IInternetPriority) failed: %08x\n", hres);
2857 hres = IInternetPriority_GetPriority(priority, &p);
2858 ok(hres == S_OK, "GetPriority failed: %08x\n", hres);
2859 ok(!p, "p=%d\n", p);
2862 hres = IInternetPriority_SetPriority(priority, 100);
2863 ok(hres == S_OK, "SetPriority failed: %08x\n", hres);
2866 hres = IInternetPriority_GetPriority(priority, &p);
2867 ok(hres == S_OK, "GetPriority failed: %08x\n", hres);
2868 ok(p == 100, "p=%d\n", p);
2870 hres = IInternetProtocol_QueryInterface(protocol, &IID_IWinInetInfo, (void**)&inet_info);
2871 ok(hres == E_NOINTERFACE, "Could not get IWinInetInfo protocol: %08x\n", hres);
2873 SET_EXPECT(QueryService_InternetProtocol);
2874 SET_EXPECT(CreateInstance);
2875 SET_EXPECT(ReportProgress_PROTOCOLCLASSID);
2876 SET_EXPECT(SetPriority);
2879 expect_hrResult = S_OK;
2880 hres = IInternetProtocol_Start(protocol, test_url, &protocol_sink, &bind_info, 0, 0);
2881 ok(hres == S_OK, "Start failed: %08x\n", hres);
2883 CHECK_CALLED(QueryService_InternetProtocol);
2884 CHECK_CALLED(CreateInstance);
2885 CHECK_CALLED(ReportProgress_PROTOCOLCLASSID);
2886 CHECK_CALLED(SetPriority);
2887 CHECK_CALLED(Start);
2889 SET_EXPECT(QueryInterface_IWinInetInfo);
2890 hres = IInternetProtocol_QueryInterface(protocol, &IID_IWinInetInfo, (void**)&inet_info);
2891 ok(hres == E_NOINTERFACE, "Could not get IWinInetInfo protocol: %08x\n", hres);
2892 CHECK_CALLED(QueryInterface_IWinInetInfo);
2894 SET_EXPECT(QueryInterface_IWinInetInfo);
2895 hres = IInternetProtocol_QueryInterface(protocol, &IID_IWinInetInfo, (void**)&inet_info);
2896 ok(hres == E_NOINTERFACE, "Could not get IWinInetInfo protocol: %08x\n", hres);
2897 CHECK_CALLED(QueryInterface_IWinInetInfo);
2899 SET_EXPECT(QueryInterface_IWinInetHttpInfo);
2900 hres = IInternetProtocol_QueryInterface(protocol, &IID_IWinInetHttpInfo, (void**)&http_info);
2901 ok(hres == E_NOINTERFACE, "Could not get IWinInetInfo protocol: %08x\n", hres);
2902 CHECK_CALLED(QueryInterface_IWinInetHttpInfo);
2906 hres = IInternetProtocol_Read(protocol, expect_pv = buf, sizeof(buf), &read);
2907 ok(hres == S_OK, "Read failed: %08x\n", hres);
2908 ok(read == 100, "read = %d\n", read);
2913 hres = IInternetProtocol_Read(protocol, expect_pv = buf, sizeof(buf), &read);
2914 ok(hres == S_FALSE, "Read failed: %08x\n", hres);
2915 ok(!read, "read = %d\n", read);
2919 hres = IInternetPriority_GetPriority(priority, &p);
2920 ok(hres == S_OK, "GetPriority failed: %08x\n", hres);
2921 ok(p == 100, "p=%d\n", p);
2923 hres = IInternetPriority_SetPriority(priority, 101);
2924 ok(hres == S_OK, "SetPriority failed: %08x\n", hres);
2926 SET_EXPECT(Terminate);
2927 hres = IInternetProtocol_Terminate(protocol, 0xdeadbeef);
2928 ok(hres == S_OK, "Terminate failed: %08x\n", hres);
2929 CHECK_CALLED(Terminate);
2931 SET_EXPECT(Continue);
2932 hres = IInternetProtocolSink_Switch(binding_sink, &protocoldata);
2933 ok(hres == S_OK, "Switch failed: %08x\n", hres);
2934 CHECK_CALLED(Continue);
2936 hres = IInternetProtocolSink_ReportProgress(binding_sink,
2937 BINDSTATUS_CACHEFILENAMEAVAILABLE, expect_wsz = emptyW);
2938 ok(hres == S_OK, "ReportProgress(BINDSTATUS_CACHEFILENAMEAVAILABLE) failed: %08x\n", hres);
2940 hres = IInternetProtocolSink_ReportResult(binding_sink, S_OK, ERROR_SUCCESS, NULL);
2941 ok(hres == E_FAIL, "ReportResult failed: %08x, expected E_FAIL\n", hres);
2943 hres = IInternetProtocolSink_ReportData(binding_sink, 0, 0, 0);
2944 ok(hres == S_OK, "ReportData failed: %08x\n", hres);
2946 IInternetProtocolSink_Release(binding_sink);
2947 IInternetPriority_Release(priority);
2948 IInternetBindInfo_Release(prot_bind_info);
2949 IInternetProtocol_Release(protocol);
2951 hres = IInternetSession_UnregisterNameSpace(session, &ClassFactory, wsz_test);
2952 ok(hres == S_OK, "UnregisterNameSpace failed: %08x\n", hres);
2954 IInternetSession_Release(session);
2957 static void test_binding(int prot, DWORD grf_pi, DWORD test_flags)
2959 IInternetProtocol *protocol;
2960 IInternetSession *session;
2966 init_test(prot, test_flags|TEST_BINDING);
2968 hres = pCoInternetGetSession(0, &session, 0);
2969 ok(hres == S_OK, "CoInternetGetSession failed: %08x\n", hres);
2971 if(test_flags & TEST_EMULATEPROT) {
2972 hres = IInternetSession_RegisterNameSpace(session, &ClassFactory, &IID_NULL, protocol_names[prot], 0, NULL, 0);
2973 ok(hres == S_OK, "RegisterNameSpace failed: %08x\n", hres);
2976 hres = IInternetSession_CreateBinding(session, NULL, binding_urls[prot], NULL, NULL, &protocol, 0);
2977 binding_protocol = protocol;
2978 ok(hres == S_OK, "CreateBinding failed: %08x\n", hres);
2979 ok(protocol != NULL, "protocol == NULL\n");
2981 hres = IInternetProtocol_QueryInterface(protocol, &IID_IInternetBindInfo, (void**)&prot_bind_info);
2982 ok(hres == S_OK, "QueryInterface(IID_IInternetBindInfo) failed: %08x\n", hres);
2984 hres = IInternetProtocol_QueryInterface(protocol, &IID_IInternetProtocolSink, (void**)&binding_sink);
2985 ok(hres == S_OK, "QueryInterface(IID_IInternetProtocolSink) failed: %08x\n", hres);
2988 SET_EXPECT(QueryService_InternetProtocol);
2989 SET_EXPECT(CreateInstance);
2990 SET_EXPECT(ReportProgress_PROTOCOLCLASSID);
2991 SET_EXPECT(SetPriority);
2994 expect_hrResult = S_OK;
2995 hres = IInternetProtocol_Start(protocol, binding_urls[prot], &protocol_sink, &bind_info, pi, 0);
2996 ok(hres == S_OK, "Start failed: %08x\n", hres);
2998 CHECK_CALLED(QueryService_InternetProtocol);
2999 CHECK_CALLED(CreateInstance);
3000 CHECK_CALLED(ReportProgress_PROTOCOLCLASSID);
3001 CHECK_CALLED(SetPriority);
3002 CHECK_CALLED(Start);
3004 if(prot == HTTP_TEST || prot == HTTPS_TEST) {
3005 while(prot_state < 4) {
3006 WaitForSingleObject(event_complete, INFINITE);
3007 if(mimefilter_test && filtered_protocol) {
3008 SET_EXPECT(Continue);
3009 IInternetProtocol_Continue(filtered_protocol, pdata);
3010 CHECK_CALLED(Continue);
3012 SET_EXPECT(Continue);
3013 IInternetProtocol_Continue(protocol, pdata);
3014 CHECK_CALLED(Continue);
3016 SetEvent(event_complete2);
3019 CHECK_CALLED(ReportData); /* Set in ReportResult */
3020 WaitForSingleObject(event_complete, INFINITE);
3023 SET_EXPECT(MimeFilter_LockRequest);
3025 SET_EXPECT(LockRequest);
3026 hres = IInternetProtocol_LockRequest(protocol, 0);
3027 ok(hres == S_OK, "LockRequest failed: %08x\n", hres);
3029 CHECK_CALLED(MimeFilter_LockRequest);
3031 CHECK_CALLED(LockRequest);
3034 SET_EXPECT(MimeFilter_UnlockRequest);
3036 SET_EXPECT(UnlockRequest);
3037 hres = IInternetProtocol_UnlockRequest(protocol);
3038 ok(hres == S_OK, "UnlockRequest failed: %08x\n", hres);
3040 CHECK_CALLED(MimeFilter_UnlockRequest);
3042 CHECK_CALLED(UnlockRequest);
3046 SET_EXPECT(MimeFilter_Terminate);
3048 SET_EXPECT(Terminate);
3049 hres = IInternetProtocol_Terminate(protocol, 0);
3050 ok(hres == S_OK, "Terminate failed: %08x\n", hres);
3052 CLEAR_CALLED(MimeFilter_Terminate);
3054 CHECK_CALLED(Terminate);
3056 if(filtered_protocol)
3057 IInternetProtocol_Release(filtered_protocol);
3058 IInternetBindInfo_Release(prot_bind_info);
3059 IInternetProtocolSink_Release(binding_sink);
3060 ref = IInternetProtocol_Release(protocol);
3061 ok(!ref, "ref=%u, expected 0\n", ref);
3063 if(test_flags & TEST_EMULATEPROT) {
3064 hres = IInternetSession_UnregisterNameSpace(session, &ClassFactory, protocol_names[prot]);
3065 ok(hres == S_OK, "UnregisterNameSpace failed: %08x\n", hres);
3068 IInternetSession_Release(session);
3071 static void register_filter(void)
3073 IInternetSession *session;
3076 static const WCHAR gzipW[] = {'g','z','i','p',0};
3078 hres = pCoInternetGetSession(0, &session, 0);
3079 ok(hres == S_OK, "CoInternetGetSession failed: %08x\n", hres);
3081 hres = IInternetSession_RegisterMimeFilter(session, &mimefilter_cf, &IID_IInternetProtocol, gzipW);
3082 ok(hres == S_OK, "RegisterMimeFilter failed: %08x\n", hres);
3084 IInternetSession_Release(session);
3087 START_TEST(protocol)
3091 hurlmon = GetModuleHandle("urlmon.dll");
3092 pCoInternetGetSession = (void*) GetProcAddress(hurlmon, "CoInternetGetSession");
3093 pReleaseBindInfo = (void*) GetProcAddress(hurlmon, "ReleaseBindInfo");
3094 pCreateUri = (void*) GetProcAddress(hurlmon, "CreateUri");
3096 if (!pCoInternetGetSession || !pReleaseBindInfo) {
3097 win_skip("Various needed functions not present in IE 4.0\n");
3101 OleInitialize(NULL);
3103 event_complete = CreateEvent(NULL, FALSE, FALSE, NULL);
3104 event_complete2 = CreateEvent(NULL, FALSE, FALSE, NULL);
3105 event_continue = CreateEvent(NULL, FALSE, FALSE, NULL);
3106 event_continue_done = CreateEvent(NULL, FALSE, FALSE, NULL);
3110 test_file_protocol();
3111 test_http_protocol();
3112 test_https_protocol();
3113 test_ftp_protocol();
3114 test_gopher_protocol();
3116 test_CreateBinding();
3118 bindf &= ~BINDF_FROMURLMON;
3119 trace("Testing file binding (mime verification, emulate prot)...\n");
3120 test_binding(FILE_TEST, PI_MIMEVERIFICATION, TEST_EMULATEPROT);
3121 trace("Testing http binding (mime verification, emulate prot)...\n");
3122 test_binding(HTTP_TEST, PI_MIMEVERIFICATION, TEST_EMULATEPROT);
3123 trace("Testing http binding (mime verification, emulate prot, short read, direct read)...\n");
3124 test_binding(HTTP_TEST, PI_MIMEVERIFICATION, TEST_EMULATEPROT|TEST_SHORT_READ|TEST_DIRECT_READ);
3125 trace("Testing file binding (mime verification, emulate prot, mime filter)...\n");
3126 test_binding(FILE_TEST, PI_MIMEVERIFICATION, TEST_EMULATEPROT|TEST_FILTER);
3127 trace("Testing http binding (mime verification, emulate prot, mime filter)...\n");
3128 test_binding(HTTP_TEST, PI_MIMEVERIFICATION, TEST_EMULATEPROT|TEST_FILTER);
3129 trace("Testing http binding (mime verification, emulate prot, direct read)...\n");
3130 test_binding(HTTP_TEST, PI_MIMEVERIFICATION, TEST_EMULATEPROT|TEST_DIRECT_READ);
3132 CloseHandle(event_complete);
3133 CloseHandle(event_complete2);
3134 CloseHandle(event_continue);
3135 CloseHandle(event_continue_done);