ieframe: Added GoForward tests.
[wine] / dlls / ieframe / tests / webbrowser.c
1 /*
2  * Copyright 2006 Jacek Caban for CodeWeavers
3  *
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.
8  *
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.
13  *
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
17  */
18
19 #define COBJMACROS
20 #define CONST_VTABLE
21
22 #include <wine/test.h>
23 #include <stdarg.h>
24 #include <stdio.h>
25
26 #include "windef.h"
27 #include "winbase.h"
28 #include "initguid.h"
29 #include "ole2.h"
30 #include "exdisp.h"
31 #include "htiframe.h"
32 #include "mshtmhst.h"
33 #include "mshtmcid.h"
34 #include "mshtml.h"
35 #include "idispids.h"
36 #include "olectl.h"
37 #include "mshtmdid.h"
38 #include "shobjidl.h"
39 #include "shdeprecated.h"
40 #include "shlguid.h"
41 #include "exdispid.h"
42 #include "mimeinfo.h"
43 #include "hlink.h"
44 #include "docobjectservice.h"
45
46 DEFINE_GUID(GUID_NULL,0,0,0,0,0,0,0,0,0,0,0);
47 DEFINE_OLEGUID(CGID_DocHostCmdPriv, 0x000214D4L, 0, 0);
48
49 #define DEFINE_EXPECT(func) \
50     static BOOL expect_ ## func = FALSE, called_ ## func = FALSE
51
52 #define SET_EXPECT(func) \
53     expect_ ## func = TRUE
54
55 #define CHECK_EXPECT2(func) \
56     do { \
57         ok(expect_ ##func, "unexpected call " #func "\n"); \
58         called_ ## func = TRUE; \
59     }while(0)
60
61 #define CHECK_EXPECT(func) \
62     do { \
63         CHECK_EXPECT2(func); \
64         expect_ ## func = FALSE; \
65     }while(0)
66
67 #define CHECK_CALLED(func) \
68     do { \
69         ok(called_ ## func, "expected " #func "\n"); \
70         expect_ ## func = called_ ## func = FALSE; \
71     }while(0)
72
73 #define CLEAR_CALLED(func) \
74     expect_ ## func = called_ ## func = FALSE
75
76 DEFINE_EXPECT(GetContainer);
77 DEFINE_EXPECT(Site_GetWindow);
78 DEFINE_EXPECT(ShowObject);
79 DEFINE_EXPECT(CanInPlaceActivate);
80 DEFINE_EXPECT(OnInPlaceActivate);
81 DEFINE_EXPECT(OnUIActivate);
82 DEFINE_EXPECT(GetWindowContext);
83 DEFINE_EXPECT(Frame_GetWindow);
84 DEFINE_EXPECT(Frame_SetActiveObject);
85 DEFINE_EXPECT(UIWindow_SetActiveObject);
86 DEFINE_EXPECT(SetMenu);
87 DEFINE_EXPECT(Invoke_AMBIENT_USERMODE);
88 DEFINE_EXPECT(Invoke_AMBIENT_DLCONTROL);
89 DEFINE_EXPECT(Invoke_AMBIENT_USERAGENT);
90 DEFINE_EXPECT(Invoke_AMBIENT_PALETTE);
91 DEFINE_EXPECT(Invoke_AMBIENT_SILENT);
92 DEFINE_EXPECT(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
93 DEFINE_EXPECT(Invoke_STATUSTEXTCHANGE);
94 DEFINE_EXPECT(Invoke_PROPERTYCHANGE);
95 DEFINE_EXPECT(Invoke_DOWNLOADBEGIN);
96 DEFINE_EXPECT(Invoke_BEFORENAVIGATE2);
97 DEFINE_EXPECT(Invoke_SETSECURELOCKICON);
98 DEFINE_EXPECT(Invoke_FILEDOWNLOAD);
99 DEFINE_EXPECT(Invoke_COMMANDSTATECHANGE);
100 DEFINE_EXPECT(Invoke_DOWNLOADCOMPLETE);
101 DEFINE_EXPECT(Invoke_ONMENUBAR);
102 DEFINE_EXPECT(Invoke_ONADDRESSBAR);
103 DEFINE_EXPECT(Invoke_ONSTATUSBAR);
104 DEFINE_EXPECT(Invoke_ONTOOLBAR);
105 DEFINE_EXPECT(Invoke_ONFULLSCREEN);
106 DEFINE_EXPECT(Invoke_ONTHEATERMODE);
107 DEFINE_EXPECT(Invoke_WINDOWSETRESIZABLE);
108 DEFINE_EXPECT(Invoke_TITLECHANGE);
109 DEFINE_EXPECT(Invoke_NAVIGATECOMPLETE2);
110 DEFINE_EXPECT(Invoke_PROGRESSCHANGE);
111 DEFINE_EXPECT(Invoke_DOCUMENTCOMPLETE);
112 DEFINE_EXPECT(Invoke_282);
113 DEFINE_EXPECT(EnableModeless_TRUE);
114 DEFINE_EXPECT(EnableModeless_FALSE);
115 DEFINE_EXPECT(GetHostInfo);
116 DEFINE_EXPECT(GetOptionKeyPath);
117 DEFINE_EXPECT(GetOverridesKeyPath);
118 DEFINE_EXPECT(SetStatusText);
119 DEFINE_EXPECT(UpdateUI);
120 DEFINE_EXPECT(Exec_SETDOWNLOADSTATE_0);
121 DEFINE_EXPECT(Exec_SETDOWNLOADSTATE_1);
122 DEFINE_EXPECT(Exec_SETPROGRESSMAX);
123 DEFINE_EXPECT(Exec_SETPROGRESSPOS);
124 DEFINE_EXPECT(Exec_UPDATECOMMANDS);
125 DEFINE_EXPECT(Exec_SETTITLE);
126 DEFINE_EXPECT(QueryStatus_SETPROGRESSTEXT);
127 DEFINE_EXPECT(Exec_STOP);
128 DEFINE_EXPECT(Exec_IDM_STOP);
129 DEFINE_EXPECT(Exec_DocHostCommandHandler_2300);
130 DEFINE_EXPECT(QueryStatus_STOP);
131 DEFINE_EXPECT(QueryStatus_IDM_STOP);
132 DEFINE_EXPECT(DocHost_EnableModeless_TRUE);
133 DEFINE_EXPECT(DocHost_EnableModeless_FALSE);
134 DEFINE_EXPECT(DocHost_TranslateAccelerator);
135 DEFINE_EXPECT(GetDropTarget);
136 DEFINE_EXPECT(TranslateUrl);
137 DEFINE_EXPECT(ShowUI);
138 DEFINE_EXPECT(HideUI);
139 DEFINE_EXPECT(OnUIDeactivate);
140 DEFINE_EXPECT(OnInPlaceDeactivate);
141 DEFINE_EXPECT(RequestUIActivate);
142 DEFINE_EXPECT(ControlSite_TranslateAccelerator);
143 DEFINE_EXPECT(OnFocus);
144 DEFINE_EXPECT(GetExternal);
145
146 static const WCHAR wszItem[] = {'i','t','e','m',0};
147 static const WCHAR emptyW[] = {0};
148
149 static VARIANT_BOOL exvb;
150
151 static IWebBrowser2 *wb;
152
153 static HWND container_hwnd, shell_embedding_hwnd;
154 static BOOL is_downloading, is_first_load, use_container_olecmd, test_close, is_http, use_container_dochostui;
155 static HRESULT hr_dochost_TranslateAccelerator = E_NOTIMPL;
156 static HRESULT hr_site_TranslateAccelerator = E_NOTIMPL;
157 static const char *current_url;
158 static int wb_version;
159
160 #define DWL_EXPECT_BEFORE_NAVIGATE  0x01
161 #define DWL_FROM_PUT_HREF           0x02
162 #define DWL_FROM_GOBACK             0x04
163 #define DWL_FROM_GOFORWARD          0x08
164 #define DWL_HTTP                    0x10
165 #define DWL_REFRESH                 0x20
166
167 static DWORD dwl_flags;
168
169
170 /* Returns true if the user interface is in English. Note that this does not
171  * presume of the formatting of dates, numbers, etc.
172  */
173 static BOOL is_lang_english(void)
174 {
175     static HMODULE hkernel32 = NULL;
176     static LANGID (WINAPI *pGetThreadUILanguage)(void) = NULL;
177     static LANGID (WINAPI *pGetUserDefaultUILanguage)(void) = NULL;
178
179     if (!hkernel32)
180     {
181         hkernel32 = GetModuleHandleA("kernel32.dll");
182         pGetThreadUILanguage = (void*)GetProcAddress(hkernel32, "GetThreadUILanguage");
183         pGetUserDefaultUILanguage = (void*)GetProcAddress(hkernel32, "GetUserDefaultUILanguage");
184     }
185     if (pGetThreadUILanguage)
186         return PRIMARYLANGID(pGetThreadUILanguage()) == LANG_ENGLISH;
187     if (pGetUserDefaultUILanguage)
188         return PRIMARYLANGID(pGetUserDefaultUILanguage()) == LANG_ENGLISH;
189
190     return PRIMARYLANGID(GetUserDefaultLangID()) == LANG_ENGLISH;
191 }
192
193 static int strcmp_wa(LPCWSTR strw, const char *stra)
194 {
195     CHAR buf[512];
196     WideCharToMultiByte(CP_ACP, 0, strw, -1, buf, sizeof(buf), NULL, NULL);
197     return lstrcmpA(stra, buf);
198 }
199
200 static BOOL iface_cmp(IUnknown *iface1, IUnknown *iface2)
201 {
202     IUnknown *unk1, *unk2;
203
204     if(iface1 == iface2)
205         return TRUE;
206
207     IUnknown_QueryInterface(iface1, &IID_IUnknown, (void**)&unk1);
208     IUnknown_Release(unk1);
209     IUnknown_QueryInterface(iface2, &IID_IUnknown, (void**)&unk2);
210     IUnknown_Release(unk2);
211
212     return unk1 == unk2;
213 }
214
215 static const char *debugstr_guid(REFIID riid)
216 {
217     static char buf[50];
218
219     sprintf(buf, "{%08X-%04X-%04X-%02X%02X-%02X%02X%02X%02X%02X%02X}",
220             riid->Data1, riid->Data2, riid->Data3, riid->Data4[0],
221             riid->Data4[1], riid->Data4[2], riid->Data4[3], riid->Data4[4],
222             riid->Data4[5], riid->Data4[6], riid->Data4[7]);
223
224     return buf;
225 }
226
227 static BSTR a2bstr(const char *str)
228 {
229     BSTR ret;
230     int len;
231
232     len = MultiByteToWideChar(CP_ACP, 0, str, -1, NULL, 0);
233     ret = SysAllocStringLen(NULL, len);
234     MultiByteToWideChar(CP_ACP, 0, str, -1, ret, len);
235
236     return ret;
237 }
238
239 #define create_webbrowser() _create_webbrowser(__LINE__)
240 static IWebBrowser2 *_create_webbrowser(unsigned line)
241 {
242     IWebBrowser2 *ret;
243     HRESULT hres;
244
245     wb_version = 2;
246
247     hres = CoCreateInstance(&CLSID_WebBrowser, NULL, CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER,
248             &IID_IWebBrowser2, (void**)&ret);
249     ok_(__FILE__,line)(hres == S_OK, "Creating WebBrowser object failed: %08x\n", hres);
250     return ret;
251 }
252
253 #define test_LocationURL(a,b) _test_LocationURL(__LINE__,a,b)
254 static void _test_LocationURL(unsigned line, IWebBrowser2 *wb, const char *exurl)
255 {
256     BSTR url = (void*)0xdeadbeef;
257     HRESULT hres;
258
259     hres = IWebBrowser2_get_LocationURL(wb, &url);
260     ok_(__FILE__,line) (hres == (*exurl ? S_OK : S_FALSE), "get_LocationURL failed: %08x\n", hres);
261     if (hres == S_OK)
262     {
263         ok_(__FILE__,line) (!strcmp_wa(url, exurl), "unexpected URL: %s\n", wine_dbgstr_w(url));
264         SysFreeString(url);
265     }
266 }
267
268 #define test_ready_state(ex) _test_ready_state(__LINE__,ex);
269 static void _test_ready_state(unsigned line, READYSTATE exstate)
270 {
271     READYSTATE state;
272     HRESULT hres;
273
274     hres = IWebBrowser2_get_ReadyState(wb, &state);
275     ok_(__FILE__,line)(hres == S_OK, "get_ReadyState failed: %08x\n", hres);
276     ok_(__FILE__,line)(state == exstate, "ReadyState = %d, expected %d\n", state, exstate);
277 }
278
279 #define get_document(u) _get_document(__LINE__,u)
280 static IDispatch *_get_document(unsigned line, IWebBrowser2 *wb)
281 {
282     IHTMLDocument2 *html_doc;
283     IDispatch *disp;
284     HRESULT hres;
285
286     disp = NULL;
287     hres = IWebBrowser2_get_Document(wb, &disp);
288     ok_(__FILE__,line)(hres == S_OK, "get_Document failed: %08x\n", hres);
289     ok_(__FILE__,line)(disp != NULL, "doc_disp == NULL\n");
290
291     hres = IDispatch_QueryInterface(disp, &IID_IHTMLDocument2, (void**)&html_doc);
292     ok_(__FILE__,line)(hres == S_OK, "Could not get IHTMLDocument iface: %08x\n", hres);
293     ok(disp == (IDispatch*)html_doc, "disp != html_doc\n");
294     IHTMLDocument2_Release(html_doc);
295
296     return disp;
297 }
298
299 #define get_dochost(u) _get_dochost(__LINE__,u)
300 static IOleClientSite *_get_dochost(unsigned line, IWebBrowser2 *unk)
301 {
302     IOleClientSite *client_site;
303     IOleObject *oleobj;
304     IDispatch *doc;
305     HRESULT hres;
306
307     doc = _get_document(line, unk);
308     hres = IDispatch_QueryInterface(doc, &IID_IOleObject, (void**)&oleobj);
309     IDispatch_Release(doc);
310     ok_(__FILE__,line)(hres == S_OK, "Got 0x%08x\n", hres);
311
312     hres = IOleObject_GetClientSite(oleobj, &client_site);
313     IOleObject_Release(oleobj);
314     ok_(__FILE__,line)(hres == S_OK, "Got 0x%08x\n", hres);
315
316     return client_site;
317 }
318
319 static HRESULT QueryInterface(REFIID,void**);
320
321 static HRESULT WINAPI OleCommandTarget_QueryInterface(IOleCommandTarget *iface,
322         REFIID riid, void **ppv)
323 {
324     ok(0, "unexpected call\n");
325     return E_NOINTERFACE;
326 }
327
328 static ULONG WINAPI OleCommandTarget_AddRef(IOleCommandTarget *iface)
329 {
330     return 2;
331 }
332
333 static ULONG WINAPI OleCommandTarget_Release(IOleCommandTarget *iface)
334 {
335     return 1;
336 }
337
338 static HRESULT WINAPI OleCommandTarget_QueryStatus(IOleCommandTarget *iface, const GUID *pguidCmdGroup,
339         ULONG cCmds, OLECMD prgCmds[], OLECMDTEXT *pCmdText)
340 {
341     ok(!pguidCmdGroup, "pguidCmdGroup != MULL\n");
342     ok(cCmds == 1, "cCmds=%d, expected 1\n", cCmds);
343     ok(!pCmdText, "pCmdText != NULL\n");
344
345     switch(prgCmds[0].cmdID) {
346     case OLECMDID_STOP:
347         CHECK_EXPECT2(QueryStatus_STOP);
348         prgCmds[0].cmdf = OLECMDF_SUPPORTED;
349         return S_OK;
350     case OLECMDID_SETPROGRESSTEXT:
351         CHECK_EXPECT(QueryStatus_SETPROGRESSTEXT);
352         prgCmds[0].cmdf = OLECMDF_ENABLED;
353         return S_OK;
354     case IDM_STOP:
355         /* Note:
356          *  IDM_STOP is a command specific to CGID_MSHTML (not an OLECMDID command).
357          *  This command appears here for the ExecWB and QueryStatusWB tests in order
358          *  to help demonstrate that these routines use a NULL pguidCmdGroup.
359          */
360         CHECK_EXPECT(QueryStatus_IDM_STOP);
361         prgCmds[0].cmdf = 0;
362         return S_OK;
363     default:
364         ok(0, "unexpected command %d\n", prgCmds[0].cmdID);
365     }
366
367     return E_FAIL;
368 }
369
370 static HRESULT WINAPI OleCommandTarget_Exec(IOleCommandTarget *iface, const GUID *pguidCmdGroup,
371         DWORD nCmdID, DWORD nCmdexecopt, VARIANT *pvaIn, VARIANT *pvaOut)
372 {
373     if(!pguidCmdGroup) {
374         switch(nCmdID) {
375         case OLECMDID_SETPROGRESSMAX:
376             CHECK_EXPECT2(Exec_SETPROGRESSMAX);
377             ok(nCmdexecopt == OLECMDEXECOPT_DONTPROMPTUSER, "nCmdexecopts=%08x\n", nCmdexecopt);
378             ok(pvaIn != NULL, "pvaIn == NULL\n");
379             if(pvaIn)
380                 ok(V_VT(pvaIn) == VT_I4, "V_VT(pvaIn)=%d, expected VT_I4\n", V_VT(pvaIn));
381             ok(pvaOut == NULL, "pvaOut=%p, expected NULL\n", pvaOut);
382             return S_OK;
383         case OLECMDID_SETPROGRESSPOS:
384             CHECK_EXPECT2(Exec_SETPROGRESSPOS);
385             ok(nCmdexecopt == OLECMDEXECOPT_DONTPROMPTUSER, "nCmdexecopts=%08x\n", nCmdexecopt);
386             ok(pvaIn != NULL, "pvaIn == NULL\n");
387             if(pvaIn)
388                 ok(V_VT(pvaIn) == VT_I4, "V_VT(pvaIn)=%d, expected VT_I4\n", V_VT(pvaIn));
389             ok(pvaOut == NULL, "pvaOut=%p, expected NULL\n", pvaOut);
390             return S_OK;
391         case OLECMDID_SETDOWNLOADSTATE:
392             if(is_downloading)
393                 ok(nCmdexecopt == OLECMDEXECOPT_DONTPROMPTUSER || !nCmdexecopt,
394                    "nCmdexecopts=%08x\n", nCmdexecopt);
395             else
396                 ok(!nCmdexecopt, "nCmdexecopts=%08x\n", nCmdexecopt);
397             ok(pvaOut == NULL, "pvaOut=%p\n", pvaOut);
398             ok(pvaIn != NULL, "pvaIn == NULL\n");
399             ok(V_VT(pvaIn) == VT_I4, "V_VT(pvaIn)=%d\n", V_VT(pvaIn));
400             switch(V_I4(pvaIn)) {
401             case 0:
402                 CHECK_EXPECT2(Exec_SETDOWNLOADSTATE_0);
403                 break;
404             case 1:
405                 CHECK_EXPECT2(Exec_SETDOWNLOADSTATE_1);
406                 break;
407             default:
408                 ok(0, "unexpevted V_I4(pvaIn)=%d\n", V_I4(pvaIn));
409             }
410             return S_OK;
411         case OLECMDID_UPDATECOMMANDS:
412             CHECK_EXPECT2(Exec_UPDATECOMMANDS);
413             ok(nCmdexecopt == OLECMDEXECOPT_DONTPROMPTUSER, "nCmdexecopts=%08x\n", nCmdexecopt);
414             ok(!pvaIn, "pvaIn != NULL\n");
415             ok(!pvaOut, "pvaOut=%p, expected NULL\n", pvaOut);
416             return S_OK;
417         case OLECMDID_SETTITLE:
418             CHECK_EXPECT(Exec_SETTITLE);
419             /* TODO: test args */
420             return S_OK;
421         case OLECMDID_STOP:
422             CHECK_EXPECT(Exec_STOP);
423             return S_OK;
424         case IDM_STOP:
425             /* Note:
426              *  IDM_STOP is a command specific to CGID_MSHTML (not an OLECMDID command).
427              *  This command appears here for the ExecWB and QueryStatusWB tests in order
428              *  to help demonstrate that these routines use a NULL pguidCmdGroup.
429              */
430             CHECK_EXPECT(Exec_IDM_STOP);
431             return OLECMDERR_E_NOTSUPPORTED;
432         case OLECMDID_UPDATETRAVELENTRY_DATARECOVERY:
433         case 6058: /* TODO */
434             return E_NOTIMPL;
435         default:
436             ok(0, "unexpected nsCmdID %d\n", nCmdID);
437         }
438     }else if(IsEqualGUID(&CGID_Explorer, pguidCmdGroup)) {
439         switch(nCmdID) {
440         case 20: /* TODO */
441         case 24: /* TODO */
442         case 25: /* IE5 */
443         case 37: /* TODO */
444         case 39: /* TODO */
445         case 66: /* TODO */
446         case 67: /* TODO */
447         case 69: /* TODO */
448         case 101: /* TODO (IE8) */
449         case 109: /* TODO (IE9) */
450         case 113: /* TODO (IE10) */
451             return E_FAIL;
452         default:
453             ok(0, "unexpected nCmdID %d\n", nCmdID);
454         }
455     }else if(IsEqualGUID(&CGID_ShellDocView, pguidCmdGroup)) {
456         switch(nCmdID) {
457         case 105: /* TODO */
458         case 134: /* TODO (IE10) */
459         case 136: /* TODO (IE10) */
460         case 138: /* TODO */
461         case 140: /* TODO (Win7) */
462         case 144: /* TODO */
463             return E_FAIL;
464         default:
465             ok(0, "unexpected nCmdID %d\n", nCmdID);
466         }
467     }else if(IsEqualGUID(&CGID_DocHostCmdPriv, pguidCmdGroup)) {
468         switch(nCmdID) {
469         case 11: /* TODO */
470             break;
471         default:
472             ok(0, "unexpected nCmdID %d of CGID_DocHostCmdPriv\n", nCmdID);
473         }
474     }else if(IsEqualGUID(&CGID_DocHostCommandHandler, pguidCmdGroup)) {
475         switch(nCmdID) {
476         case 6041: /* TODO */
477             break;
478         case 2300:
479             CHECK_EXPECT(Exec_DocHostCommandHandler_2300);
480             return E_NOTIMPL;
481         default:
482             ok(0, "unexpected nCmdID %d of CGID_DocHostCommandHandler\n", nCmdID);
483         }
484     }else {
485         ok(0, "unexpected pguidCmdGroup %s\n", debugstr_guid(pguidCmdGroup));
486     }
487
488     return E_FAIL;
489 }
490
491 static IOleCommandTargetVtbl OleCommandTargetVtbl = {
492     OleCommandTarget_QueryInterface,
493     OleCommandTarget_AddRef,
494     OleCommandTarget_Release,
495     OleCommandTarget_QueryStatus,
496     OleCommandTarget_Exec
497 };
498
499 static IOleCommandTarget OleCommandTarget = { &OleCommandTargetVtbl };
500
501 static HRESULT WINAPI OleContainer_QueryInterface(IOleContainer *iface, REFIID riid, void **ppv)
502 {
503     if(IsEqualGUID(&IID_ITargetContainer, riid))
504         return E_NOINTERFACE; /* TODO */
505
506     if(IsEqualGUID(&IID_IOleCommandTarget, riid)) {
507         if(use_container_olecmd)
508         {
509             *ppv = &OleCommandTarget;
510             return S_OK;
511         }
512         else
513             return E_NOINTERFACE;
514     }
515
516     ok(0, "unexpected call\n");
517     return E_NOINTERFACE;
518 }
519
520 static ULONG WINAPI OleContainer_AddRef(IOleContainer *iface)
521 {
522     return 2;
523 }
524
525 static ULONG WINAPI OleContainer_Release(IOleContainer *iface)
526 {
527     return 1;
528 }
529
530 static HRESULT WINAPI OleContainer_ParseDisplayName(IOleContainer *iface, IBindCtx *pbc,
531         LPOLESTR pszDiaplayName, ULONG *pchEaten, IMoniker **ppmkOut)
532 {
533     ok(0, "unexpected call\n");
534     return E_NOTIMPL;
535 }
536
537 static HRESULT WINAPI OleContainer_EnumObjects(IOleContainer *iface, DWORD grfFlags,
538         IEnumUnknown **ppenum)
539 {
540     ok(0, "unexpected call\n");
541     return E_NOTIMPL;
542 }
543
544 static HRESULT WINAPI OleContainer_LockContainer(IOleContainer *iface, BOOL fLock)
545 {
546     ok(0, "unexpected call\n");
547     return E_NOTIMPL;
548 }
549
550 static const IOleContainerVtbl OleContainerVtbl = {
551     OleContainer_QueryInterface,
552     OleContainer_AddRef,
553     OleContainer_Release,
554     OleContainer_ParseDisplayName,
555     OleContainer_EnumObjects,
556     OleContainer_LockContainer
557 };
558
559 static IOleContainer OleContainer = { &OleContainerVtbl };
560
561 static HRESULT WINAPI Dispatch_QueryInterface(IDispatch *iface, REFIID riid, void **ppv)
562 {
563     return QueryInterface(riid, ppv);
564 }
565
566 static ULONG WINAPI Dispatch_AddRef(IDispatch *iface)
567 {
568     return 2;
569 }
570
571 static ULONG WINAPI Dispatch_Release(IDispatch *iface)
572 {
573     return 1;
574 }
575
576 static HRESULT WINAPI Dispatch_GetTypeInfoCount(IDispatch *iface, UINT *pctinfo)
577 {
578     ok(0, "unexpected call\n");
579     return E_NOTIMPL;
580 }
581
582 static HRESULT WINAPI Dispatch_GetTypeInfo(IDispatch *iface, UINT iTInfo, LCID lcid,
583         ITypeInfo **ppTInfo)
584 {
585     ok(0, "unexpected call\n");
586     return E_NOTIMPL;
587 }
588
589 static HRESULT WINAPI Dispatch_GetIDsOfNames(IDispatch *iface, REFIID riid, LPOLESTR *rgszNames,
590         UINT cNames, LCID lcid, DISPID *rgDispId)
591 {
592     ok(0, "unexpected call\n");
593     return E_NOTIMPL;
594 }
595
596 static HRESULT WINAPI Dispatch_Invoke(IDispatch *iface, DISPID dispIdMember, REFIID riid,
597         LCID lcid, WORD wFlags, DISPPARAMS *pDispParams, VARIANT *pVarResult,
598         EXCEPINFO *pExcepInfo, UINT *puArgErr)
599 {
600     ok(IsEqualGUID(&IID_NULL, riid), "riid != IID_NULL\n");
601     ok(pDispParams != NULL, "pDispParams == NULL\n");
602     ok(pExcepInfo == NULL, "pExcepInfo=%p, expected NULL\n", pExcepInfo);
603     ok(V_VT(pVarResult) == VT_EMPTY, "V_VT(pVarResult)=%d\n", V_VT(pVarResult));
604     ok(wFlags == DISPATCH_PROPERTYGET, "wFlags=%08x, expected DISPATCH_PROPERTYGET\n", wFlags);
605     ok(pDispParams->rgvarg == NULL, "pDispParams->rgvarg = %p\n", pDispParams->rgvarg);
606     ok(pDispParams->rgdispidNamedArgs == NULL,
607        "pDispParams->rgdispidNamedArgs = %p\n", pDispParams->rgdispidNamedArgs);
608     ok(pDispParams->cArgs == 0, "pDispParams->cArgs = %d\n", pDispParams->cArgs);
609     ok(pDispParams->cNamedArgs == 0, "pDispParams->cNamedArgs = %d\n", pDispParams->cNamedArgs);
610
611     switch(dispIdMember) {
612     case DISPID_AMBIENT_USERMODE:
613         CHECK_EXPECT2(Invoke_AMBIENT_USERMODE);
614         return E_FAIL;
615     case DISPID_AMBIENT_DLCONTROL:
616         CHECK_EXPECT(Invoke_AMBIENT_DLCONTROL);
617         ok(puArgErr != NULL, "puArgErr=%p\n", puArgErr);
618         return E_FAIL;
619     case DISPID_AMBIENT_USERAGENT:
620        CHECK_EXPECT(Invoke_AMBIENT_USERAGENT);
621         ok(puArgErr != NULL, "puArgErr=%p\n", puArgErr);
622         return E_FAIL;
623     case DISPID_AMBIENT_PALETTE:
624         CHECK_EXPECT(Invoke_AMBIENT_PALETTE);
625         ok(puArgErr != NULL, "puArgErr=%p\n", puArgErr);
626         return E_FAIL;
627     case DISPID_AMBIENT_OFFLINEIFNOTCONNECTED:
628         CHECK_EXPECT(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
629         ok(puArgErr == NULL, "puArgErr=%p\n", puArgErr);
630         V_VT(pVarResult) = VT_BOOL;
631         V_BOOL(pVarResult) = VARIANT_FALSE;
632         return S_OK;
633     case DISPID_AMBIENT_SILENT:
634         CHECK_EXPECT(Invoke_AMBIENT_SILENT);
635         ok(puArgErr == NULL, "puArgErr=%p\n", puArgErr);
636         V_VT(pVarResult) = VT_BOOL;
637         V_BOOL(pVarResult) = VARIANT_FALSE;
638         return S_OK;
639     }
640
641     ok(0, "unexpected dispIdMember %d\n", dispIdMember);
642     return E_NOTIMPL;
643 }
644
645 static IDispatchVtbl DispatchVtbl = {
646     Dispatch_QueryInterface,
647     Dispatch_AddRef,
648     Dispatch_Release,
649     Dispatch_GetTypeInfoCount,
650     Dispatch_GetTypeInfo,
651     Dispatch_GetIDsOfNames,
652     Dispatch_Invoke
653 };
654
655 static IDispatch Dispatch = { &DispatchVtbl };
656
657 static HRESULT WINAPI WebBrowserEvents2_QueryInterface(IDispatch *iface, REFIID riid, void **ppv)
658 {
659     *ppv = NULL;
660
661     if(IsEqualGUID(&DIID_DWebBrowserEvents2, riid)) {
662         *ppv = iface;
663         return S_OK;
664     }
665
666     ok(0, "unexpected riid %s\n", debugstr_guid(riid));
667     return E_NOINTERFACE;
668 }
669
670 #define test_invoke_bool(p,s) _test_invoke_bool(__LINE__,p,s)
671 static void _test_invoke_bool(unsigned line, const DISPPARAMS *params, BOOL strict)
672 {
673     ok_(__FILE__,line) (params->rgvarg != NULL, "rgvarg == NULL\n");
674     ok_(__FILE__,line) (params->cArgs == 1, "cArgs=%d, expected 1\n", params->cArgs);
675     ok_(__FILE__,line) (V_VT(params->rgvarg) == VT_BOOL, "V_VT(arg)=%d\n", V_VT(params->rgvarg));
676     if(strict)
677         ok_(__FILE__,line) (V_BOOL(params->rgvarg) == exvb, "V_VT(arg)=%x, expected %x\n",
678                             V_BOOL(params->rgvarg), exvb);
679     else
680         ok_(__FILE__,line) (!V_BOOL(params->rgvarg) == !exvb, "V_VT(arg)=%x, expected %x\n",
681                             V_BOOL(params->rgvarg), exvb);
682 }
683
684 static void test_OnBeforeNavigate(const VARIANT *disp, const VARIANT *url, const VARIANT *flags,
685         const VARIANT *frame, const VARIANT *post_data, const VARIANT *headers, const VARIANT *cancel)
686 {
687     ok(V_VT(disp) == VT_DISPATCH, "V_VT(disp)=%d, expected VT_DISPATCH\n", V_VT(disp));
688     ok(V_DISPATCH(disp) != NULL, "V_DISPATCH(disp) == NULL\n");
689     ok(V_DISPATCH(disp) == (IDispatch*)wb, "V_DISPATCH(disp)=%p, wb=%p\n", V_DISPATCH(disp), wb);
690
691     ok(V_VT(url) == (VT_BYREF|VT_VARIANT), "V_VT(url)=%x, expected VT_BYREF|VT_VARIANT\n", V_VT(url));
692     ok(V_VARIANTREF(url) != NULL, "V_VARIANTREF(url) == NULL)\n");
693     if(V_VARIANTREF(url)) {
694         ok(V_VT(V_VARIANTREF(url)) == VT_BSTR, "V_VT(V_VARIANTREF(url))=%d, expected VT_BSTR\n",
695            V_VT(V_VARIANTREF(url)));
696         ok(V_BSTR(V_VARIANTREF(url)) != NULL, "V_BSTR(V_VARIANTREF(url)) == NULL\n");
697         ok(!strcmp_wa(V_BSTR(V_VARIANTREF(url)), current_url), "unexpected url %s, expected %s\n",
698            wine_dbgstr_w(V_BSTR(V_VARIANTREF(url))), current_url);
699     }
700
701     ok(V_VT(flags) == (VT_BYREF|VT_VARIANT), "V_VT(flags)=%x, expected VT_BYREF|VT_VARIANT\n",
702        V_VT(flags));
703     ok(V_VT(flags) == (VT_BYREF|VT_VARIANT), "V_VT(flags)=%x, expected VT_BYREF|VT_VARIANT\n",
704        V_VT(flags));
705     ok(V_VARIANTREF(flags) != NULL, "V_VARIANTREF(flags) == NULL)\n");
706     if(V_VARIANTREF(flags)) {
707         ok(V_VT(V_VARIANTREF(flags)) == VT_I4, "V_VT(V_VARIANTREF(flags))=%d, expected VT_I4\n",
708            V_VT(V_VARIANTREF(flags)));
709         if(is_first_load) {
710             ok(V_I4(V_VARIANTREF(flags)) == 0, "V_I4(V_VARIANTREF(flags)) = %x, expected 0\n",
711                V_I4(V_VARIANTREF(flags)));
712         }else {
713             ok((V_I4(V_VARIANTREF(flags)) & ~0x40) == 0, "V_I4(V_VARIANTREF(flags)) = %x, expected 0x40 or 0\n",
714                V_I4(V_VARIANTREF(flags)));
715         }
716     }
717
718     ok(V_VT(frame) == (VT_BYREF|VT_VARIANT), "V_VT(frame)=%x, expected VT_BYREF|VT_VARIANT\n",
719        V_VT(frame));
720     ok(V_VT(frame) == (VT_BYREF|VT_VARIANT), "V_VT(frame)=%x, expected VT_BYREF|VT_VARIANT\n",
721        V_VT(frame));
722     ok(V_VARIANTREF(frame) != NULL, "V_VARIANTREF(frame) == NULL)\n");
723     if(V_VARIANTREF(frame)) {
724         ok(V_VT(V_VARIANTREF(frame)) == VT_BSTR, "V_VT(V_VARIANTREF(frame))=%d, expected VT_BSTR\n",
725            V_VT(V_VARIANTREF(frame)));
726         ok(V_BSTR(V_VARIANTREF(frame)) == NULL, "V_BSTR(V_VARIANTREF(frame)) = %p, expected NULL\n",
727            V_BSTR(V_VARIANTREF(frame)));
728     }
729
730     ok(V_VT(post_data) == (VT_BYREF|VT_VARIANT), "V_VT(post_data)=%x, expected VT_BYREF|VT_VARIANT\n",
731        V_VT(post_data));
732     ok(V_VT(post_data) == (VT_BYREF|VT_VARIANT), "V_VT(post_data)=%x, expected VT_BYREF|VT_VARIANT\n",
733        V_VT(post_data));
734     ok(V_VARIANTREF(post_data) != NULL, "V_VARIANTREF(post_data) == NULL)\n");
735     if(V_VARIANTREF(post_data)) {
736         ok(V_VT(V_VARIANTREF(post_data)) == (VT_VARIANT|VT_BYREF),
737            "V_VT(V_VARIANTREF(post_data))=%d, expected VT_VARIANT|VT_BYREF\n",
738            V_VT(V_VARIANTREF(post_data)));
739         ok(V_VARIANTREF(V_VARIANTREF(post_data)) != NULL,
740            "V_VARIANTREF(V_VARIANTREF(post_data)) == NULL\n");
741         if(V_VARIANTREF(V_VARIANTREF(post_data))) {
742             ok(V_VT(V_VARIANTREF(V_VARIANTREF(post_data))) == VT_EMPTY,
743                "V_VT(V_VARIANTREF(V_VARIANTREF(post_data))) = %d, expected VT_EMPTY\n",
744                V_VT(V_VARIANTREF(V_VARIANTREF(post_data))));
745
746             if(V_VT(V_VARIANTREF(V_VARIANTREF(post_data))) == (VT_UI1|VT_ARRAY)) {
747                 const SAFEARRAY *sa = V_ARRAY(V_VARIANTREF(V_VARIANTREF(post_data)));
748
749                 ok(sa->cDims == 1, "sa->cDims = %d, expected 1\n", sa->cDims);
750                 ok(sa->fFeatures == 0, "sa->fFeatures = %d, expected 0\n", sa->fFeatures);
751             }
752         }
753     }
754
755     ok(V_VT(headers) == (VT_BYREF|VT_VARIANT), "V_VT(headers)=%x, expected VT_BYREF|VT_VARIANT\n",
756        V_VT(headers));
757     ok(V_VARIANTREF(headers) != NULL, "V_VARIANTREF(headers) == NULL)\n");
758     if(V_VARIANTREF(headers)) {
759         ok(V_VT(V_VARIANTREF(headers)) == VT_BSTR, "V_VT(V_VARIANTREF(headers))=%d, expected VT_BSTR\n",
760            V_VT(V_VARIANTREF(headers)));
761         ok(V_BSTR(V_VARIANTREF(headers)) == NULL, "V_BSTR(V_VARIANTREF(headers)) = %p, expected NULL\n",
762            V_BSTR(V_VARIANTREF(headers)));
763     }
764
765     ok(V_VT(cancel) == (VT_BYREF|VT_BOOL), "V_VT(cancel)=%x, expected VT_BYREF|VT_BOOL\n",
766        V_VT(cancel));
767     ok(V_BOOLREF(cancel) != NULL, "V_BOOLREF(pDispParams->rgvarg[0] == NULL)\n");
768     if(V_BOOLREF(cancel))
769         ok(*V_BOOLREF(cancel) == VARIANT_FALSE, "*V_BOOLREF(cancel) = %x, expected VARIANT_FALSE\n",
770            *V_BOOLREF(cancel));
771 }
772
773 static void test_navigatecomplete2(DISPPARAMS *dp)
774 {
775     VARIANT *v;
776
777     CHECK_EXPECT(Invoke_NAVIGATECOMPLETE2);
778
779     ok(dp->rgvarg != NULL, "rgvarg == NULL\n");
780     ok(dp->cArgs == 2, "cArgs=%d, expected 2\n", dp->cArgs);
781
782     ok(V_VT(dp->rgvarg) == (VT_BYREF|VT_VARIANT), "V_VT(dp->rgvarg) = %d\n", V_VT(dp->rgvarg));
783     v = V_VARIANTREF(dp->rgvarg);
784     ok(V_VT(v) == VT_BSTR, "V_VT(url) = %d\n", V_VT(v));
785     ok(!strcmp_wa(V_BSTR(v), current_url), "url=%s, expected %s\n", wine_dbgstr_w(V_BSTR(v)), current_url);
786
787     ok(V_VT(dp->rgvarg+1) == VT_DISPATCH, "V_VT(dp->rgvarg+1) = %d\n", V_VT(dp->rgvarg+1));
788     ok(V_DISPATCH(dp->rgvarg+1) == (IDispatch*)wb, "V_DISPATCH=%p, wb=%p\n", V_DISPATCH(dp->rgvarg+1), wb);
789
790     test_ready_state((dwl_flags & (DWL_FROM_PUT_HREF|DWL_FROM_GOBACK|DWL_FROM_GOFORWARD))
791                      ? READYSTATE_COMPLETE : READYSTATE_LOADING);
792 }
793
794 static void test_documentcomplete(DISPPARAMS *dp)
795 {
796     VARIANT *v;
797
798     CHECK_EXPECT(Invoke_DOCUMENTCOMPLETE);
799
800     ok(dp->rgvarg != NULL, "rgvarg == NULL\n");
801     ok(dp->cArgs == 2, "cArgs=%d, expected 2\n", dp->cArgs);
802
803     ok(V_VT(dp->rgvarg) == (VT_BYREF|VT_VARIANT), "V_VT(dp->rgvarg) = %d\n", V_VT(dp->rgvarg));
804     v = V_VARIANTREF(dp->rgvarg);
805     ok(V_VT(v) == VT_BSTR, "V_VT(url) = %d\n", V_VT(v));
806     ok(!strcmp_wa(V_BSTR(v), current_url), "url=%s, expected %s\n", wine_dbgstr_w(V_BSTR(v)), current_url);
807
808     ok(V_VT(dp->rgvarg+1) == VT_DISPATCH, "V_VT(dp->rgvarg+1) = %d\n", V_VT(dp->rgvarg+1));
809     ok(V_DISPATCH(dp->rgvarg+1) == (IDispatch*)wb, "V_DISPATCH=%p, wb=%p\n", V_DISPATCH(dp->rgvarg+1), wb);
810
811     test_ready_state(READYSTATE_COMPLETE);
812 }
813
814 static HRESULT WINAPI WebBrowserEvents2_Invoke(IDispatch *iface, DISPID dispIdMember, REFIID riid,
815         LCID lcid, WORD wFlags, DISPPARAMS *pDispParams, VARIANT *pVarResult,
816         EXCEPINFO *pExcepInfo, UINT *puArgErr)
817 {
818     ok(IsEqualGUID(&IID_NULL, riid), "riid != IID_NULL\n");
819     ok(pDispParams != NULL, "pDispParams == NULL\n");
820     ok(pExcepInfo == NULL, "pExcepInfo=%p, expected NULL\n", pExcepInfo);
821     ok(pVarResult == NULL, "pVarResult=%p\n", pVarResult);
822     ok(wFlags == DISPATCH_METHOD, "wFlags=%08x, expected DISPATCH_METHOD\n", wFlags);
823     ok(pDispParams->rgdispidNamedArgs == NULL,
824        "pDispParams->rgdispidNamedArgs = %p\n", pDispParams->rgdispidNamedArgs);
825     ok(pDispParams->cNamedArgs == 0, "pDispParams->cNamedArgs = %d\n", pDispParams->cNamedArgs);
826
827     switch(dispIdMember) {
828     case DISPID_STATUSTEXTCHANGE:
829         CHECK_EXPECT2(Invoke_STATUSTEXTCHANGE);
830
831         ok(pDispParams->rgvarg != NULL, "rgvarg == NULL\n");
832         ok(pDispParams->cArgs == 1, "cArgs=%d, expected 1\n", pDispParams->cArgs);
833         ok(V_VT(pDispParams->rgvarg) == VT_BSTR, "V_VT(pDispParams->rgvarg)=%d, expected VT_BSTR\n",
834            V_VT(pDispParams->rgvarg));
835         /* TODO: Check text */
836         break;
837
838     case DISPID_PROPERTYCHANGE:
839         CHECK_EXPECT2(Invoke_PROPERTYCHANGE);
840
841         ok(pDispParams->rgvarg != NULL, "rgvarg == NULL\n");
842         ok(pDispParams->cArgs == 1, "cArgs=%d, expected 1\n", pDispParams->cArgs);
843         /* TODO: Check args */
844         break;
845
846     case DISPID_DOWNLOADBEGIN:
847         CHECK_EXPECT(Invoke_DOWNLOADBEGIN);
848
849         ok(pDispParams->rgvarg == NULL, "rgvarg=%p, expected NULL\n", pDispParams->rgvarg);
850         ok(pDispParams->cArgs == 0, "cArgs=%d, expected 0\n", pDispParams->cArgs);
851         test_ready_state(READYSTATE_LOADING);
852         break;
853
854     case DISPID_BEFORENAVIGATE2:
855         CHECK_EXPECT(Invoke_BEFORENAVIGATE2);
856
857         ok(pDispParams->rgvarg != NULL, "rgvarg == NULL\n");
858         ok(pDispParams->cArgs == 7, "cArgs=%d, expected 7\n", pDispParams->cArgs);
859         test_OnBeforeNavigate(pDispParams->rgvarg+6, pDispParams->rgvarg+5, pDispParams->rgvarg+4,
860                               pDispParams->rgvarg+3, pDispParams->rgvarg+2, pDispParams->rgvarg+1,
861                               pDispParams->rgvarg);
862         test_ready_state((dwl_flags & (DWL_FROM_PUT_HREF|DWL_FROM_GOFORWARD)) ? READYSTATE_COMPLETE : READYSTATE_LOADING);
863         break;
864
865     case DISPID_SETSECURELOCKICON:
866         CHECK_EXPECT2(Invoke_SETSECURELOCKICON);
867
868         ok(pDispParams->rgvarg != NULL, "rgvarg == NULL\n");
869         ok(pDispParams->cArgs == 1, "cArgs=%d, expected 1\n", pDispParams->cArgs);
870         /* TODO: Check args */
871         break;
872
873     case DISPID_FILEDOWNLOAD:
874         CHECK_EXPECT(Invoke_FILEDOWNLOAD);
875
876         ok(pDispParams->rgvarg != NULL, "rgvarg == NULL\n");
877         ok(pDispParams->cArgs == 2, "cArgs=%d, expected 2\n", pDispParams->cArgs);
878         /* TODO: Check args */
879         break;
880
881     case DISPID_COMMANDSTATECHANGE:
882         CHECK_EXPECT2(Invoke_COMMANDSTATECHANGE);
883
884         ok(pDispParams->rgvarg != NULL, "rgvarg == NULL\n");
885         ok(pDispParams->cArgs == 2, "cArgs=%d, expected 2\n", pDispParams->cArgs);
886
887         ok(V_VT(pDispParams->rgvarg) == VT_BOOL, "V_VT(pDispParams->rgvarg) = %d\n", V_VT(pDispParams->rgvarg));
888         ok(V_VT(pDispParams->rgvarg+1) == VT_I4, "V_VT(pDispParams->rgvarg+1) = %d\n", V_VT(pDispParams->rgvarg+1));
889
890         /* TODO: Check args */
891         break;
892
893     case DISPID_DOWNLOADCOMPLETE:
894         CHECK_EXPECT(Invoke_DOWNLOADCOMPLETE);
895
896         ok(pDispParams->rgvarg == NULL, "rgvarg=%p, expected NULL\n", pDispParams->rgvarg);
897         ok(pDispParams->cArgs == 0, "cArgs=%d, expected 0\n", pDispParams->cArgs);
898         test_ready_state(READYSTATE_LOADING);
899         break;
900
901     case DISPID_ONMENUBAR:
902         CHECK_EXPECT(Invoke_ONMENUBAR);
903         test_invoke_bool(pDispParams, TRUE);
904         break;
905
906     case DISPID_ONADDRESSBAR:
907         CHECK_EXPECT(Invoke_ONADDRESSBAR);
908         test_invoke_bool(pDispParams, TRUE);
909         break;
910
911     case DISPID_ONSTATUSBAR:
912         CHECK_EXPECT(Invoke_ONSTATUSBAR);
913         test_invoke_bool(pDispParams, TRUE);
914         break;
915
916     case DISPID_ONTOOLBAR:
917         CHECK_EXPECT(Invoke_ONTOOLBAR);
918         test_invoke_bool(pDispParams, FALSE);
919         break;
920
921     case DISPID_ONFULLSCREEN:
922         CHECK_EXPECT(Invoke_ONFULLSCREEN);
923         test_invoke_bool(pDispParams, TRUE);
924         break;
925
926     case DISPID_ONTHEATERMODE:
927         CHECK_EXPECT(Invoke_ONTHEATERMODE);
928         test_invoke_bool(pDispParams, TRUE);
929         break;
930
931     case DISPID_WINDOWSETRESIZABLE:
932         CHECK_EXPECT(Invoke_WINDOWSETRESIZABLE);
933         test_invoke_bool(pDispParams, TRUE);
934         break;
935
936     case DISPID_TITLECHANGE:
937         CHECK_EXPECT2(Invoke_TITLECHANGE);
938         /* FIXME */
939         break;
940
941     case DISPID_NAVIGATECOMPLETE2:
942         test_navigatecomplete2(pDispParams);
943         break;
944
945     case DISPID_PROGRESSCHANGE:
946         CHECK_EXPECT2(Invoke_PROGRESSCHANGE);
947         /* FIXME */
948         break;
949
950     case DISPID_DOCUMENTCOMPLETE:
951         test_documentcomplete(pDispParams);
952         break;
953
954     case 282: /* FIXME */
955         CHECK_EXPECT2(Invoke_282);
956         break;
957
958     case 290: /* FIXME: IE10 */
959         break;
960
961     default:
962         ok(0, "unexpected dispIdMember %d\n", dispIdMember);
963     }
964
965     return S_OK;
966 }
967
968 static IDispatchVtbl WebBrowserEvents2Vtbl = {
969     WebBrowserEvents2_QueryInterface,
970     Dispatch_AddRef,
971     Dispatch_Release,
972     Dispatch_GetTypeInfoCount,
973     Dispatch_GetTypeInfo,
974     Dispatch_GetIDsOfNames,
975     WebBrowserEvents2_Invoke
976 };
977
978 static IDispatch WebBrowserEvents2 = { &WebBrowserEvents2Vtbl };
979
980 static HRESULT WINAPI ClientSite_QueryInterface(IOleClientSite *iface, REFIID riid, void **ppv)
981 {
982     return QueryInterface(riid, ppv);
983 }
984
985 static ULONG WINAPI ClientSite_AddRef(IOleClientSite *iface)
986 {
987     return 2;
988 }
989
990 static ULONG WINAPI ClientSite_Release(IOleClientSite *iface)
991 {
992     return 1;
993 }
994
995 static HRESULT WINAPI ClientSite_SaveObject(IOleClientSite *iface)
996 {
997     ok(0, "unexpected call\n");
998     return E_NOTIMPL;
999 }
1000
1001 static HRESULT WINAPI ClientSite_GetMoniker(IOleClientSite *iface, DWORD dwAssign, DWORD dwWhichMoniker,
1002         IMoniker **ppmon)
1003 {
1004     ok(0, "unexpected call\n");
1005     return E_NOTIMPL;
1006 }
1007
1008 static HRESULT WINAPI ClientSite_GetContainer(IOleClientSite *iface, IOleContainer **ppContainer)
1009 {
1010     CHECK_EXPECT(GetContainer);
1011
1012     ok(ppContainer != NULL, "ppContainer == NULL\n");
1013     if(ppContainer)
1014         *ppContainer = &OleContainer;
1015
1016     return S_OK;
1017 }
1018
1019 static HRESULT WINAPI ClientSite_ShowObject(IOleClientSite *iface)
1020 {
1021     CHECK_EXPECT(ShowObject);
1022     return S_OK;
1023 }
1024
1025 static HRESULT WINAPI ClientSite_OnShowWindow(IOleClientSite *iface, BOOL fShow)
1026 {
1027     ok(0, "unexpected call\n");
1028     return E_NOTIMPL;
1029 }
1030
1031 static HRESULT WINAPI ClientSite_RequestNewObjectLayout(IOleClientSite *iface)
1032 {
1033     ok(0, "unexpected call\n");
1034     return E_NOTIMPL;
1035 }
1036
1037 static const IOleClientSiteVtbl ClientSiteVtbl = {
1038     ClientSite_QueryInterface,
1039     ClientSite_AddRef,
1040     ClientSite_Release,
1041     ClientSite_SaveObject,
1042     ClientSite_GetMoniker,
1043     ClientSite_GetContainer,
1044     ClientSite_ShowObject,
1045     ClientSite_OnShowWindow,
1046     ClientSite_RequestNewObjectLayout
1047 };
1048
1049 static IOleClientSite ClientSite = { &ClientSiteVtbl };
1050
1051 static HRESULT WINAPI IOleControlSite_fnQueryInterface(IOleControlSite *iface, REFIID riid, void **ppv)
1052 {
1053     *ppv = NULL;
1054     return E_NOINTERFACE;
1055 }
1056
1057 static ULONG WINAPI IOleControlSite_fnAddRef(IOleControlSite *iface)
1058 {
1059     return 2;
1060 }
1061
1062 static ULONG WINAPI IOleControlSite_fnRelease(IOleControlSite *iface)
1063 {
1064     return 1;
1065 }
1066
1067 static HRESULT WINAPI IOleControlSite_fnOnControlInfoChanged(IOleControlSite* This)
1068 {
1069     ok(0, "unexpected call\n");
1070     return E_NOTIMPL;
1071 }
1072
1073 static HRESULT WINAPI IOleControlSite_fnLockInPlaceActive(IOleControlSite* This,
1074                                                           BOOL fLock)
1075 {
1076     ok(0, "unexpected call\n");
1077     return E_NOTIMPL;
1078 }
1079
1080 static HRESULT WINAPI IOleControlSite_fnGetExtendedControl(IOleControlSite* This,
1081                                                            IDispatch **ppDisp)
1082 {
1083     ok(0, "unexpected call\n");
1084     return E_NOTIMPL;
1085 }
1086
1087 static HRESULT WINAPI IOleControlSite_fnTransformCoords(IOleControlSite* This,
1088                                                         POINTL *pPtlHimetric,
1089                                                         POINTF *pPtfContainer,
1090                                                         DWORD dwFlags)
1091 {
1092     ok(0, "unexpected call\n");
1093     return E_NOTIMPL;
1094 }
1095
1096 static HRESULT WINAPI IOleControlSite_fnTranslateAccelerator(IOleControlSite* This, MSG *pMsg,
1097                                                              DWORD grfModifiers)
1098 {
1099     CHECK_EXPECT(ControlSite_TranslateAccelerator);
1100     return hr_site_TranslateAccelerator;
1101 }
1102
1103 static HRESULT WINAPI IOleControlSite_fnOnFocus(IOleControlSite* This, BOOL fGotFocus)
1104 {
1105     CHECK_EXPECT2(OnFocus);
1106     return E_NOTIMPL;
1107 }
1108
1109 static HRESULT WINAPI IOleControlSite_fnShowPropertyFrame(IOleControlSite* This)
1110 {
1111     ok(0, "unexpected call\n");
1112     return E_NOTIMPL;
1113 }
1114
1115 static IOleControlSiteVtbl ControlSiteVtbl = {
1116     IOleControlSite_fnQueryInterface,
1117     IOleControlSite_fnAddRef,
1118     IOleControlSite_fnRelease,
1119     IOleControlSite_fnOnControlInfoChanged,
1120     IOleControlSite_fnLockInPlaceActive,
1121     IOleControlSite_fnGetExtendedControl,
1122     IOleControlSite_fnTransformCoords,
1123     IOleControlSite_fnTranslateAccelerator,
1124     IOleControlSite_fnOnFocus,
1125     IOleControlSite_fnShowPropertyFrame
1126 };
1127
1128 static IOleControlSite ControlSite = { &ControlSiteVtbl };
1129
1130 static HRESULT WINAPI InPlaceUIWindow_QueryInterface(IOleInPlaceFrame *iface,
1131                                                      REFIID riid, void **ppv)
1132 {
1133     ok(0, "unexpected call\n");
1134     return E_NOINTERFACE;
1135 }
1136
1137 static ULONG WINAPI InPlaceUIWindow_AddRef(IOleInPlaceFrame *iface)
1138 {
1139     return 2;
1140 }
1141
1142 static ULONG WINAPI InPlaceUIWindow_Release(IOleInPlaceFrame *iface)
1143 {
1144     return 1;
1145 }
1146
1147 static HRESULT WINAPI InPlaceUIWindow_GetWindow(IOleInPlaceFrame *iface, HWND *phwnd)
1148 {
1149     ok(0, "unexpected call\n");
1150     return E_NOTIMPL;
1151 }
1152
1153 static HRESULT WINAPI InPlaceFrame_GetWindow(IOleInPlaceFrame *iface, HWND *phwnd)
1154 {
1155     CHECK_EXPECT(Frame_GetWindow);
1156     ok(phwnd != NULL, "phwnd == NULL\n");
1157     if(phwnd)
1158         *phwnd = container_hwnd;
1159     return S_OK;
1160 }
1161
1162 static HRESULT WINAPI InPlaceUIWindow_ContextSensitiveHelp(IOleInPlaceFrame *iface, BOOL fEnterMode)
1163 {
1164     ok(0, "unexpected call\n");
1165     return E_NOTIMPL;
1166 }
1167
1168 static HRESULT WINAPI InPlaceUIWindow_GetBorder(IOleInPlaceFrame *iface, LPRECT lprectBorder)
1169 {
1170     ok(0, "unexpected call\n");
1171     return E_NOTIMPL;
1172 }
1173
1174 static HRESULT WINAPI InPlaceUIWindow_RequestBorderSpace(IOleInPlaceFrame *iface,
1175         LPCBORDERWIDTHS pborderwidths)
1176 {
1177     ok(0, "unexpected call\n");
1178     return E_NOTIMPL;
1179 }
1180
1181 static HRESULT WINAPI InPlaceUIWindow_SetBorderSpace(IOleInPlaceFrame *iface,
1182         LPCBORDERWIDTHS pborderwidths)
1183 {
1184     ok(0, "unexpected call\n");
1185     return E_NOTIMPL;
1186 }
1187
1188 static HRESULT WINAPI InPlaceUIWindow_SetActiveObject(IOleInPlaceFrame *iface,
1189         IOleInPlaceActiveObject *pActiveObject, LPCOLESTR pszObjName)
1190 {
1191     CHECK_EXPECT(UIWindow_SetActiveObject);
1192     if(!test_close) {
1193         ok(pActiveObject != NULL, "pActiveObject = NULL\n");
1194         ok(!lstrcmpW(pszObjName, wszItem), "unexpected pszObjName\n");
1195     } else {
1196         ok(!pActiveObject, "pActiveObject != NULL\n");
1197         ok(!pszObjName, "pszObjName != NULL\n");
1198     }
1199     return S_OK;
1200 }
1201
1202 static HRESULT WINAPI InPlaceFrame_SetActiveObject(IOleInPlaceFrame *iface,
1203         IOleInPlaceActiveObject *pActiveObject, LPCOLESTR pszObjName)
1204 {
1205     CHECK_EXPECT(Frame_SetActiveObject);
1206     if(!test_close) {
1207         ok(pActiveObject != NULL, "pActiveObject = NULL\n");
1208         ok(!lstrcmpW(pszObjName, wszItem), "unexpected pszObjName\n");
1209     } else {
1210         ok(!pActiveObject, "pActiveObject != NULL\n");
1211         ok(!pszObjName, "pszObjName != NULL\n");
1212     }
1213     return S_OK;
1214 }
1215
1216 static HRESULT WINAPI InPlaceFrame_InsertMenus(IOleInPlaceFrame *iface, HMENU hmenuShared,
1217         LPOLEMENUGROUPWIDTHS lpMenuWidths)
1218 {
1219     ok(0, "unexpected call\n");
1220     return E_NOTIMPL;
1221 }
1222
1223 static HRESULT WINAPI InPlaceFrame_SetMenu(IOleInPlaceFrame *iface, HMENU hmenuShared,
1224         HOLEMENU holemenu, HWND hwndActiveObject)
1225 {
1226     CHECK_EXPECT(SetMenu);
1227     ok(hmenuShared == NULL, "hmenuShared=%p\n", hmenuShared);
1228     ok(holemenu == NULL, "holemenu=%p\n", holemenu);
1229     ok(hwndActiveObject == shell_embedding_hwnd, "hwndActiveObject=%p, expected %p\n",
1230        hwndActiveObject, shell_embedding_hwnd);
1231     return S_OK;
1232 }
1233
1234 static HRESULT WINAPI InPlaceFrame_RemoveMenus(IOleInPlaceFrame *iface, HMENU hmenuShared)
1235 {
1236     ok(0, "unexpected call\n");
1237     return E_NOTIMPL;
1238 }
1239
1240 static HRESULT WINAPI InPlaceFrame_SetStatusText(IOleInPlaceFrame *iface, LPCOLESTR pszStatusText)
1241 {
1242     CHECK_EXPECT2(SetStatusText);
1243     /* FIXME: Check pszStatusText */
1244     return S_OK;
1245 }
1246
1247 static HRESULT WINAPI InPlaceFrame_EnableModeless(IOleInPlaceFrame *iface, BOOL fEnable)
1248 {
1249     if(fEnable)
1250         CHECK_EXPECT2(EnableModeless_TRUE);
1251     else
1252         CHECK_EXPECT2(EnableModeless_FALSE);
1253     return S_OK;
1254 }
1255
1256 static HRESULT WINAPI InPlaceFrame_TranslateAccelerator(IOleInPlaceFrame *iface, LPMSG lpmsg, WORD wID)
1257 {
1258     ok(0, "unexpected call\n");
1259     return E_NOTIMPL;
1260 }
1261
1262 static const IOleInPlaceFrameVtbl InPlaceUIWindowVtbl = {
1263     InPlaceUIWindow_QueryInterface,
1264     InPlaceUIWindow_AddRef,
1265     InPlaceUIWindow_Release,
1266     InPlaceUIWindow_GetWindow,
1267     InPlaceUIWindow_ContextSensitiveHelp,
1268     InPlaceUIWindow_GetBorder,
1269     InPlaceUIWindow_RequestBorderSpace,
1270     InPlaceUIWindow_SetBorderSpace,
1271     InPlaceUIWindow_SetActiveObject,
1272 };
1273
1274 static IOleInPlaceUIWindow InPlaceUIWindow = { (IOleInPlaceUIWindowVtbl*)&InPlaceUIWindowVtbl };
1275
1276 static const IOleInPlaceFrameVtbl InPlaceFrameVtbl = {
1277     InPlaceUIWindow_QueryInterface,
1278     InPlaceUIWindow_AddRef,
1279     InPlaceUIWindow_Release,
1280     InPlaceFrame_GetWindow,
1281     InPlaceUIWindow_ContextSensitiveHelp,
1282     InPlaceUIWindow_GetBorder,
1283     InPlaceUIWindow_RequestBorderSpace,
1284     InPlaceUIWindow_SetBorderSpace,
1285     InPlaceFrame_SetActiveObject,
1286     InPlaceFrame_InsertMenus,
1287     InPlaceFrame_SetMenu,
1288     InPlaceFrame_RemoveMenus,
1289     InPlaceFrame_SetStatusText,
1290     InPlaceFrame_EnableModeless,
1291     InPlaceFrame_TranslateAccelerator
1292 };
1293
1294 static IOleInPlaceFrame InPlaceFrame = { &InPlaceFrameVtbl };
1295
1296 static HRESULT WINAPI InPlaceSite_QueryInterface(IOleInPlaceSiteEx *iface, REFIID riid, void **ppv)
1297 {
1298     return QueryInterface(riid, ppv);
1299 }
1300
1301 static ULONG WINAPI InPlaceSite_AddRef(IOleInPlaceSiteEx *iface)
1302 {
1303     return 2;
1304 }
1305
1306 static ULONG WINAPI InPlaceSite_Release(IOleInPlaceSiteEx *iface)
1307 {
1308     return 1;
1309 }
1310
1311 static HRESULT WINAPI InPlaceSite_GetWindow(IOleInPlaceSiteEx *iface, HWND *phwnd)
1312 {
1313     CHECK_EXPECT(Site_GetWindow);
1314     ok(phwnd != NULL, "phwnd == NULL\n");
1315     if(phwnd)
1316         *phwnd = container_hwnd;
1317     return S_OK;
1318 }
1319
1320 static HRESULT WINAPI InPlaceSite_ContextSensitiveHelp(IOleInPlaceSiteEx *iface, BOOL fEnterMode)
1321 {
1322     ok(0, "unexpected call\n");
1323     return E_NOTIMPL;
1324 }
1325
1326 static HRESULT WINAPI InPlaceSite_CanInPlaceActivate(IOleInPlaceSiteEx *iface)
1327 {
1328     CHECK_EXPECT(CanInPlaceActivate);
1329     return S_OK;
1330 }
1331
1332 static HRESULT WINAPI InPlaceSite_OnInPlaceActivate(IOleInPlaceSiteEx *iface)
1333 {
1334     CHECK_EXPECT(OnInPlaceActivate);
1335     return S_OK;
1336 }
1337
1338 static HRESULT WINAPI InPlaceSite_OnUIActivate(IOleInPlaceSiteEx *iface)
1339 {
1340     CHECK_EXPECT(OnUIActivate);
1341     return S_OK;
1342 }
1343
1344 static HRESULT WINAPI InPlaceSite_GetWindowContext(IOleInPlaceSiteEx *iface,
1345         IOleInPlaceFrame **ppFrame, IOleInPlaceUIWindow **ppDoc, LPRECT lprcPosRect,
1346         LPRECT lprcClipRect, LPOLEINPLACEFRAMEINFO lpFrameInfo)
1347 {
1348     static const RECT pos_rect = {2,1,1002,901};
1349     static const RECT clip_rect = {10,10,990,890};
1350
1351     CHECK_EXPECT(GetWindowContext);
1352
1353     ok(ppFrame != NULL, "ppFrame = NULL\n");
1354     if(ppFrame)
1355         *ppFrame = &InPlaceFrame;
1356
1357     ok(ppDoc != NULL, "ppDoc = NULL\n");
1358     if(ppDoc)
1359         *ppDoc = &InPlaceUIWindow;
1360
1361     ok(lprcPosRect != NULL, "lprcPosRect = NULL\n");
1362     if(lprcPosRect)
1363         memcpy(lprcPosRect, &pos_rect, sizeof(RECT));
1364
1365     ok(lprcClipRect != NULL, "lprcClipRect = NULL\n");
1366     if(lprcClipRect)
1367         memcpy(lprcClipRect, &clip_rect, sizeof(RECT));
1368
1369     ok(lpFrameInfo != NULL, "lpFrameInfo = NULL\n");
1370     if(lpFrameInfo) {
1371         ok(lpFrameInfo->cb == sizeof(*lpFrameInfo), "lpFrameInfo->cb = %u, expected %u\n", lpFrameInfo->cb, (unsigned)sizeof(*lpFrameInfo));
1372         lpFrameInfo->fMDIApp = FALSE;
1373         lpFrameInfo->hwndFrame = container_hwnd;
1374         lpFrameInfo->haccel = NULL;
1375         lpFrameInfo->cAccelEntries = 0;
1376     }
1377
1378     return S_OK;
1379 }
1380
1381 static HRESULT WINAPI InPlaceSite_Scroll(IOleInPlaceSiteEx *iface, SIZE scrollExtant)
1382 {
1383     ok(0, "unexpected call\n");
1384     return E_NOTIMPL;
1385 }
1386
1387 static HRESULT WINAPI InPlaceSite_OnUIDeactivate(IOleInPlaceSiteEx *iface, BOOL fUndoable)
1388 {
1389     CHECK_EXPECT(OnUIDeactivate);
1390     ok(!fUndoable, "fUndoable should be FALSE\n");
1391     return S_OK;
1392 }
1393
1394 static HRESULT WINAPI InPlaceSite_OnInPlaceDeactivate(IOleInPlaceSiteEx *iface)
1395 {
1396     CHECK_EXPECT(OnInPlaceDeactivate);
1397     return S_OK;
1398 }
1399
1400 static HRESULT WINAPI InPlaceSite_DiscardUndoState(IOleInPlaceSiteEx *iface)
1401 {
1402     ok(0, "unexpected call\n");
1403     return E_NOTIMPL;
1404 }
1405
1406 static HRESULT WINAPI InPlaceSite_DeactivateAndUndo(IOleInPlaceSiteEx *iface)
1407 {
1408     ok(0, "unexpected call\n");
1409     return E_NOTIMPL;
1410 }
1411
1412 static HRESULT WINAPI InPlaceSite_OnPosRectChange(IOleInPlaceSiteEx *iface, LPCRECT lprcPosRect)
1413 {
1414     ok(0, "unexpected call\n");
1415     return E_NOTIMPL;
1416 }
1417
1418 static HRESULT WINAPI InPlaceSite_OnInPlaceActivateEx(IOleInPlaceSiteEx *iface,
1419                                                       BOOL *pNoRedraw, DWORD dwFlags)
1420 {
1421     ok(0, "unexpected call\n");
1422     return E_NOTIMPL;
1423 }
1424
1425 static HRESULT WINAPI InPlaceSite_OnInPlaceDeactivateEx(IOleInPlaceSiteEx *iface,
1426                                                         BOOL fNoRedraw)
1427 {
1428     ok(0, "unexpected call\n");
1429     return E_NOTIMPL;
1430 }
1431
1432 static HRESULT WINAPI InPlaceSite_RequestUIActivate(IOleInPlaceSiteEx *iface)
1433 {
1434     CHECK_EXPECT2(RequestUIActivate);
1435     return S_OK;
1436 }
1437
1438 static const IOleInPlaceSiteExVtbl InPlaceSiteExVtbl = {
1439     InPlaceSite_QueryInterface,
1440     InPlaceSite_AddRef,
1441     InPlaceSite_Release,
1442     InPlaceSite_GetWindow,
1443     InPlaceSite_ContextSensitiveHelp,
1444     InPlaceSite_CanInPlaceActivate,
1445     InPlaceSite_OnInPlaceActivate,
1446     InPlaceSite_OnUIActivate,
1447     InPlaceSite_GetWindowContext,
1448     InPlaceSite_Scroll,
1449     InPlaceSite_OnUIDeactivate,
1450     InPlaceSite_OnInPlaceDeactivate,
1451     InPlaceSite_DiscardUndoState,
1452     InPlaceSite_DeactivateAndUndo,
1453     InPlaceSite_OnPosRectChange,
1454     InPlaceSite_OnInPlaceActivateEx,
1455     InPlaceSite_OnInPlaceDeactivateEx,
1456     InPlaceSite_RequestUIActivate
1457 };
1458
1459 static IOleInPlaceSiteEx InPlaceSite = { &InPlaceSiteExVtbl };
1460
1461 static HRESULT WINAPI DocHostUIHandler_QueryInterface(IDocHostUIHandler2 *iface, REFIID riid, void **ppv)
1462 {
1463     return QueryInterface(riid, ppv);
1464 }
1465
1466 static ULONG WINAPI DocHostUIHandler_AddRef(IDocHostUIHandler2 *iface)
1467 {
1468     return 2;
1469 }
1470
1471 static ULONG WINAPI DocHostUIHandler_Release(IDocHostUIHandler2 *iface)
1472 {
1473     return 1;
1474 }
1475
1476 static HRESULT WINAPI DocHostUIHandler_ShowContextMenu(IDocHostUIHandler2 *iface, DWORD dwID, POINT *ppt,
1477         IUnknown *pcmdtReserved, IDispatch *pdicpReserved)
1478 {
1479     ok(0, "unexpected call %d %p %p %p\n", dwID, ppt, pcmdtReserved, pdicpReserved);
1480     return S_FALSE;
1481 }
1482
1483 static HRESULT WINAPI DocHostUIHandler_GetHostInfo(IDocHostUIHandler2 *iface, DOCHOSTUIINFO *pInfo)
1484 {
1485     CHECK_EXPECT2(GetHostInfo);
1486     ok(pInfo != NULL, "pInfo=NULL\n");
1487     if(pInfo) {
1488         ok(pInfo->cbSize == sizeof(DOCHOSTUIINFO) || broken(!pInfo->cbSize), "pInfo->cbSize=%u\n", pInfo->cbSize);
1489         ok(!pInfo->dwFlags, "pInfo->dwFlags=%08x, expected 0\n", pInfo->dwFlags);
1490         ok(!pInfo->dwDoubleClick, "pInfo->dwDoubleClick=%08x, expected 0\n", pInfo->dwDoubleClick);
1491         ok(!pInfo->pchHostCss, "pInfo->pchHostCss=%p, expected NULL\n", pInfo->pchHostCss);
1492         ok(!pInfo->pchHostNS, "pInfo->pchhostNS=%p, expected NULL\n", pInfo->pchHostNS);
1493     }
1494     return E_FAIL;
1495 }
1496
1497 static HRESULT WINAPI DocHostUIHandler_ShowUI(IDocHostUIHandler2 *iface, DWORD dwID,
1498         IOleInPlaceActiveObject *pActiveObject, IOleCommandTarget *pCommandTarget,
1499         IOleInPlaceFrame *pFrame, IOleInPlaceUIWindow *pDoc)
1500 {
1501     CHECK_EXPECT(ShowUI);
1502     return E_NOTIMPL;
1503 }
1504
1505 static HRESULT WINAPI DocHostUIHandler_HideUI(IDocHostUIHandler2 *iface)
1506 {
1507     CHECK_EXPECT(HideUI);
1508     return E_NOTIMPL;
1509 }
1510
1511 static HRESULT WINAPI DocHostUIHandler_UpdateUI(IDocHostUIHandler2 *iface)
1512 {
1513     CHECK_EXPECT2(UpdateUI);
1514     return E_NOTIMPL;
1515 }
1516
1517 static HRESULT WINAPI DocHostUIHandler_EnableModeless(IDocHostUIHandler2 *iface, BOOL fEnable)
1518 {
1519     if(fEnable)
1520         CHECK_EXPECT(DocHost_EnableModeless_TRUE);
1521     else
1522         CHECK_EXPECT(DocHost_EnableModeless_FALSE);
1523
1524     return S_OK;
1525 }
1526
1527 static HRESULT WINAPI DocHostUIHandler_OnDocWindowActivate(IDocHostUIHandler2 *iface, BOOL fActivate)
1528 {
1529     ok(0, "unexpected call\n");
1530     return E_NOTIMPL;
1531 }
1532
1533 static HRESULT WINAPI DocHostUIHandler_OnFrameWindowActivate(IDocHostUIHandler2 *iface, BOOL fActivate)
1534 {
1535     ok(0, "unexpected call\n");
1536     return E_NOTIMPL;
1537 }
1538
1539 static HRESULT WINAPI DocHostUIHandler_ResizeBorder(IDocHostUIHandler2 *iface, LPCRECT prcBorder,
1540         IOleInPlaceUIWindow *pUIWindow, BOOL fRameWindow)
1541 {
1542     ok(0, "unexpected call\n");
1543     return E_NOTIMPL;
1544 }
1545
1546 static HRESULT WINAPI DocHostUIHandler_TranslateAccelerator(IDocHostUIHandler2 *iface, LPMSG lpMsg,
1547         const GUID *pguidCmdGroup, DWORD nCmdID)
1548 {
1549     CHECK_EXPECT(DocHost_TranslateAccelerator);
1550     ok(pguidCmdGroup != NULL, "Got NULL pguidCmdGroup.\n");
1551     if(pguidCmdGroup)
1552         ok(IsEqualGUID(pguidCmdGroup, &CGID_MSHTML), "Unexpected pguidCmdGroup\n");
1553     ok(lpMsg != NULL, "Got NULL lpMsg.\n");
1554     return hr_dochost_TranslateAccelerator;
1555 }
1556
1557 static HRESULT WINAPI DocHostUIHandler_GetOptionKeyPath(IDocHostUIHandler2 *iface,
1558         LPOLESTR *pchKey, DWORD dw)
1559 {
1560     CHECK_EXPECT(GetOptionKeyPath);
1561     ok(pchKey != NULL, "pchKey==NULL\n");
1562     if(pchKey)
1563         ok(*pchKey == NULL, "*pchKey=%p\n", *pchKey);
1564     ok(!dw, "dw=%x\n", dw);
1565     return E_NOTIMPL;
1566 }
1567
1568 static HRESULT WINAPI DocHostUIHandler_GetDropTarget(IDocHostUIHandler2 *iface,
1569         IDropTarget *pDropTarget, IDropTarget **ppDropTarget)
1570 {
1571     CHECK_EXPECT(GetDropTarget);
1572     return E_NOTIMPL;
1573 }
1574
1575 static HRESULT WINAPI DocHostUIHandler_GetExternal(IDocHostUIHandler2 *iface, IDispatch **ppDispatch)
1576 {
1577     CHECK_EXPECT(GetExternal);
1578     *ppDispatch = NULL;
1579     return S_FALSE;
1580 }
1581
1582 static HRESULT WINAPI DocHostUIHandler_TranslateUrl(IDocHostUIHandler2 *iface, DWORD dwTranslate,
1583         OLECHAR *pchURLIn, OLECHAR **ppchURLOut)
1584 {
1585     if(is_downloading && !(dwl_flags & DWL_EXPECT_BEFORE_NAVIGATE))
1586         todo_wine CHECK_EXPECT(TranslateUrl);
1587     else
1588         CHECK_EXPECT(TranslateUrl);
1589     return E_NOTIMPL;
1590 }
1591
1592 static HRESULT WINAPI DocHostUIHandler_FilterDataObject(IDocHostUIHandler2 *iface, IDataObject *pDO,
1593         IDataObject **ppPORet)
1594 {
1595     ok(0, "unexpected call\n");
1596     return E_NOTIMPL;
1597 }
1598
1599 static HRESULT WINAPI DocHostUIHandler_GetOverrideKeyPath(IDocHostUIHandler2 *iface,
1600         LPOLESTR *pchKey, DWORD dw)
1601 {
1602     CHECK_EXPECT(GetOverridesKeyPath);
1603     ok(pchKey != NULL, "pchKey==NULL\n");
1604     if(pchKey)
1605         ok(*pchKey == NULL, "*pchKey=%p\n", *pchKey);
1606     ok(!dw, "dw=%x\n", dw);
1607     return E_NOTIMPL;
1608 }
1609
1610 static const IDocHostUIHandler2Vtbl DocHostUIHandlerVtbl = {
1611     DocHostUIHandler_QueryInterface,
1612     DocHostUIHandler_AddRef,
1613     DocHostUIHandler_Release,
1614     DocHostUIHandler_ShowContextMenu,
1615     DocHostUIHandler_GetHostInfo,
1616     DocHostUIHandler_ShowUI,
1617     DocHostUIHandler_HideUI,
1618     DocHostUIHandler_UpdateUI,
1619     DocHostUIHandler_EnableModeless,
1620     DocHostUIHandler_OnDocWindowActivate,
1621     DocHostUIHandler_OnFrameWindowActivate,
1622     DocHostUIHandler_ResizeBorder,
1623     DocHostUIHandler_TranslateAccelerator,
1624     DocHostUIHandler_GetOptionKeyPath,
1625     DocHostUIHandler_GetDropTarget,
1626     DocHostUIHandler_GetExternal,
1627     DocHostUIHandler_TranslateUrl,
1628     DocHostUIHandler_FilterDataObject,
1629     DocHostUIHandler_GetOverrideKeyPath
1630 };
1631
1632 static IDocHostUIHandler2 DocHostUIHandler = { &DocHostUIHandlerVtbl };
1633
1634
1635 static HRESULT WINAPI ServiceProvider_QueryInterface(IServiceProvider *iface, REFIID riid, void **ppv)
1636 {
1637     return QueryInterface(riid, ppv);
1638 }
1639
1640 static ULONG WINAPI ServiceProvider_AddRef(IServiceProvider *iface)
1641 {
1642     return 2;
1643 }
1644
1645 static ULONG WINAPI ServiceProvider_Release(IServiceProvider *iface)
1646 {
1647     return 1;
1648 }
1649
1650 static HRESULT WINAPI ServiceProvider_QueryService(IServiceProvider *iface,
1651                                     REFGUID guidService, REFIID riid, void **ppv)
1652 {
1653     *ppv = NULL;
1654
1655     if(!winetest_interactive)
1656         return E_NOINTERFACE;
1657
1658     if (IsEqualGUID(&SID_STopLevelBrowser, guidService))
1659         trace("Service SID_STopLevelBrowser\n");
1660     else if (IsEqualGUID(&SID_SEditCommandTarget, guidService))
1661         trace("Service SID_SEditCommandTarget\n");
1662     else if (IsEqualGUID(&IID_ITargetFrame2, guidService))
1663         trace("Service IID_ITargetFrame2\n");
1664     else if (IsEqualGUID(&SID_SInternetSecurityManager, guidService))
1665         trace("Service SID_SInternetSecurityManager\n");
1666     else if (IsEqualGUID(&SID_SOleUndoManager, guidService))
1667         trace("Service SID_SOleUndoManager\n");
1668     else if (IsEqualGUID(&SID_IMimeInfo, guidService))
1669         trace("Service SID_IMimeInfo\n");
1670     else if (IsEqualGUID(&SID_STopWindow, guidService))
1671         trace("Service SID_STopWindow\n");
1672
1673     /* 30D02401-6A81-11D0-8274-00C04FD5AE38 Explorer Bar: Search */
1674     /* D1E7AFEC-6A2E-11D0-8C78-00C04FD918B4 no info */
1675     /* A9227C3C-7F8E-11D0-8CB0-00A0C92DBFE8 no info */
1676     /* 371EA634-DC5C-11D1-BA57-00C04FC2040E one reference to IVersionHost */
1677     /* 3050F429-98B5-11CF-BB82-00AA00BDCE0B IID_IElementBehaviorFactory */
1678     /* 6D12FE80-7911-11CF-9534-0000C05BAE0B SID_DefView */
1679     /* AD7F6C62-F6BD-11D2-959B-006097C553C8 no info */
1680     /* 53A2D5B1-D2FC-11D0-84E0-006097C9987D no info */
1681     /* 3050F312-98B5-11CF-BB82-00AA00BDCE0B HTMLFrameBaseClass */
1682     /* 639447BD-B2D3-44B9-9FB0-510F23CB45E4 no info */
1683     /* 20C46561-8491-11CF-960C-0080C7F4EE85 no info */
1684
1685     else
1686         trace("Service %s not supported\n", debugstr_guid(guidService));
1687
1688     return E_NOINTERFACE;
1689 }
1690
1691
1692 static const IServiceProviderVtbl ServiceProviderVtbl = {
1693     ServiceProvider_QueryInterface,
1694     ServiceProvider_AddRef,
1695     ServiceProvider_Release,
1696     ServiceProvider_QueryService
1697 };
1698
1699 static IServiceProvider ServiceProvider = { &ServiceProviderVtbl };
1700
1701
1702 static HRESULT QueryInterface(REFIID riid, void **ppv)
1703 {
1704     *ppv = NULL;
1705
1706     if(IsEqualGUID(&IID_IUnknown, riid)
1707             || IsEqualGUID(&IID_IOleClientSite, riid))
1708         *ppv = &ClientSite;
1709     else if(IsEqualGUID(&IID_IOleWindow, riid)
1710             || IsEqualGUID(&IID_IOleInPlaceSite, riid)
1711             || IsEqualGUID(&IID_IOleInPlaceSiteEx, riid))
1712         *ppv = &InPlaceSite;
1713     else if(IsEqualGUID(&IID_IDocHostUIHandler, riid)
1714             || IsEqualGUID(&IID_IDocHostUIHandler2, riid))
1715         *ppv = use_container_dochostui ? &DocHostUIHandler : NULL;
1716     else if(IsEqualGUID(&IID_IDispatch, riid))
1717         *ppv = &Dispatch;
1718     else if(IsEqualGUID(&IID_IServiceProvider, riid))
1719         *ppv = &ServiceProvider;
1720     else if(IsEqualGUID(&IID_IDocHostShowUI, riid))
1721         trace("interface IID_IDocHostShowUI\n");
1722     else if(IsEqualGUID(&IID_IOleControlSite, riid))
1723         *ppv = &ControlSite;
1724     else if(IsEqualGUID(&IID_IOleCommandTarget, riid))
1725         trace("interface IID_IOleCommandTarget\n");
1726
1727     /* B6EA2050-048A-11D1-82B9-00C04FB9942E IAxWinHostWindow */
1728
1729     else
1730     {
1731         /* are there more interfaces, that a host can support? */
1732         trace("%s: interface not supported\n", debugstr_guid(riid));
1733     }
1734
1735     return (*ppv) ? S_OK : E_NOINTERFACE;
1736 }
1737
1738 static LRESULT WINAPI wnd_proc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
1739 {
1740     return DefWindowProcW(hwnd, msg, wParam, lParam);
1741 }
1742
1743 static HWND create_container_window(void)
1744 {
1745     static const WCHAR wszWebBrowserContainer[] =
1746         {'W','e','b','B','r','o','w','s','e','r','C','o','n','t','a','i','n','e','r',0};
1747     static WNDCLASSEXW wndclass = {
1748         sizeof(WNDCLASSEXW),
1749         0,
1750         wnd_proc,
1751         0, 0, NULL, NULL, NULL, NULL, NULL,
1752         wszWebBrowserContainer,
1753         NULL
1754     };
1755
1756     RegisterClassExW(&wndclass);
1757     return CreateWindowW(wszWebBrowserContainer, wszWebBrowserContainer,
1758             WS_OVERLAPPEDWINDOW, 10, 10, 600, 600, NULL, NULL, NULL, NULL);
1759 }
1760
1761 static void test_DoVerb(IWebBrowser2 *unk)
1762 {
1763     IOleObject *oleobj;
1764     RECT rect = {0,0,1000,1000};
1765     HRESULT hres;
1766
1767     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleObject, (void**)&oleobj);
1768     ok(hres == S_OK, "QueryInterface(IID_OleObject) failed: %08x\n", hres);
1769     if(FAILED(hres))
1770         return;
1771
1772     SET_EXPECT(CanInPlaceActivate);
1773     SET_EXPECT(Site_GetWindow);
1774     SET_EXPECT(OnInPlaceActivate);
1775     SET_EXPECT(GetWindowContext);
1776     SET_EXPECT(ShowObject);
1777     SET_EXPECT(GetContainer);
1778     SET_EXPECT(Frame_GetWindow);
1779     SET_EXPECT(OnUIActivate);
1780     SET_EXPECT(Frame_SetActiveObject);
1781     SET_EXPECT(UIWindow_SetActiveObject);
1782     SET_EXPECT(SetMenu);
1783     SET_EXPECT(OnFocus);
1784
1785     hres = IOleObject_DoVerb(oleobj, OLEIVERB_SHOW, NULL, &ClientSite,
1786                              0, (HWND)0xdeadbeef, &rect);
1787     ok(hres == S_OK, "DoVerb failed: %08x\n", hres);
1788
1789     CHECK_CALLED(CanInPlaceActivate);
1790     CHECK_CALLED(Site_GetWindow);
1791     CHECK_CALLED(OnInPlaceActivate);
1792     CHECK_CALLED(GetWindowContext);
1793     CHECK_CALLED(ShowObject);
1794     CHECK_CALLED(GetContainer);
1795     CHECK_CALLED(Frame_GetWindow);
1796     CHECK_CALLED(OnUIActivate);
1797     CHECK_CALLED(Frame_SetActiveObject);
1798     CHECK_CALLED(UIWindow_SetActiveObject);
1799     CHECK_CALLED(SetMenu);
1800     todo_wine CHECK_CALLED(OnFocus);
1801
1802     hres = IOleObject_DoVerb(oleobj, OLEIVERB_SHOW, NULL, &ClientSite,
1803                            0, (HWND)0xdeadbeef, &rect);
1804     ok(hres == S_OK, "DoVerb failed: %08x\n", hres);
1805
1806     IOleObject_Release(oleobj);
1807 }
1808
1809 static void call_DoVerb(IWebBrowser2 *unk, LONG verb)
1810 {
1811     IOleObject *oleobj;
1812     RECT rect = {60,60,600,600};
1813     HRESULT hres;
1814
1815     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleObject, (void**)&oleobj);
1816     ok(hres == S_OK, "QueryInterface(IID_OleObject) failed: %08x\n", hres);
1817     if(FAILED(hres))
1818         return;
1819
1820     hres = IOleObject_DoVerb(oleobj, verb, NULL, &ClientSite,
1821                              -1, container_hwnd, &rect);
1822     ok(hres == S_OK, "DoVerb failed: %08x\n", hres);
1823
1824     IOleObject_Release(oleobj);
1825 }
1826
1827 static HWND get_hwnd(IWebBrowser2 *unk)
1828 {
1829     IOleInPlaceObject *inplace;
1830     HWND hwnd;
1831     HRESULT hres;
1832
1833     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleInPlaceObject, (void**)&inplace);
1834     ok(hres == S_OK, "QueryInterface(IID_OleInPlaceObject) failed: %08x\n", hres);
1835
1836     hres = IOleInPlaceObject_GetWindow(inplace, &hwnd);
1837     ok(hres == S_OK, "GetWindow failed: %08x\n", hres);
1838
1839     IOleInPlaceObject_Release(inplace);
1840     return hwnd;
1841 }
1842
1843 static void test_GetMiscStatus(IOleObject *oleobj)
1844 {
1845     DWORD st, i;
1846     HRESULT hres;
1847
1848     for(i=0; i<10; i++) {
1849         st = 0xdeadbeef;
1850         hres = IOleObject_GetMiscStatus(oleobj, i, &st);
1851         ok(hres == S_OK, "GetMiscStatus failed: %08x\n", hres);
1852         ok(st == (OLEMISC_SETCLIENTSITEFIRST|OLEMISC_ACTIVATEWHENVISIBLE|OLEMISC_INSIDEOUT
1853                   |OLEMISC_CANTLINKINSIDE|OLEMISC_RECOMPOSEONRESIZE),
1854            "st=%08x, expected OLEMISC_SETCLIENTSITEFIRST|OLEMISC_ACTIVATEWHENVISIBLE|"
1855            "OLEMISC_INSIDEOUT|OLEMISC_CANTLINKINSIDE|OLEMISC_RECOMPOSEONRESIZE)\n", st);
1856     }
1857 }
1858
1859 static void test_SetHostNames(IOleObject *oleobj)
1860 {
1861     HRESULT hres;
1862
1863     static const WCHAR test_appW[] =  {'t','e','s','t',' ','a','p','p',0};
1864
1865     hres = IOleObject_SetHostNames(oleobj, test_appW, (void*)0xdeadbeef);
1866     ok(hres == S_OK, "SetHostNames failed: %08x\n", hres);
1867 }
1868
1869 static void test_ClientSite(IWebBrowser2 *unk, IOleClientSite *client, BOOL stop_download)
1870 {
1871     IOleObject *oleobj;
1872     IOleInPlaceObject *inplace;
1873     HWND hwnd;
1874     HRESULT hres;
1875
1876     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleObject, (void**)&oleobj);
1877     ok(hres == S_OK, "QueryInterface(IID_OleObject) failed: %08x\n", hres);
1878     if(FAILED(hres))
1879         return;
1880
1881     test_GetMiscStatus(oleobj);
1882     test_SetHostNames(oleobj);
1883
1884     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleInPlaceObject, (void**)&inplace);
1885     ok(hres == S_OK, "QueryInterface(IID_OleInPlaceObject) failed: %08x\n", hres);
1886     if(FAILED(hres)) {
1887         IOleObject_Release(oleobj);
1888         return;
1889     }
1890
1891     hres = IOleInPlaceObject_GetWindow(inplace, &hwnd);
1892     ok(hres == S_OK, "GetWindow failed: %08x\n", hres);
1893     ok((hwnd == NULL) ^ (client == NULL), "unexpected hwnd %p\n", hwnd);
1894
1895     if(client) {
1896         SET_EXPECT(GetContainer);
1897         SET_EXPECT(Site_GetWindow);
1898         SET_EXPECT(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
1899         SET_EXPECT(Invoke_AMBIENT_SILENT);
1900     }else if(stop_download) {
1901         SET_EXPECT(Invoke_DOWNLOADCOMPLETE);
1902         if (use_container_olecmd) SET_EXPECT(Exec_SETDOWNLOADSTATE_0);
1903         SET_EXPECT(Invoke_COMMANDSTATECHANGE);
1904     }else {
1905         SET_EXPECT(Invoke_STATUSTEXTCHANGE);
1906         SET_EXPECT(Invoke_PROGRESSCHANGE);
1907     }
1908
1909     hres = IOleObject_SetClientSite(oleobj, client);
1910     ok(hres == S_OK, "SetClientSite failed: %08x\n", hres);
1911
1912     if(client) {
1913         CHECK_CALLED(GetContainer);
1914         CHECK_CALLED(Site_GetWindow);
1915         CHECK_CALLED(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
1916         CHECK_CALLED(Invoke_AMBIENT_SILENT);
1917     }else if(stop_download) {
1918         todo_wine CHECK_CALLED(Invoke_DOWNLOADCOMPLETE);
1919         if (use_container_olecmd) todo_wine CHECK_CALLED(Exec_SETDOWNLOADSTATE_0);
1920         todo_wine CHECK_CALLED(Invoke_COMMANDSTATECHANGE);
1921     }else {
1922         CLEAR_CALLED(Invoke_STATUSTEXTCHANGE); /* Called by IE9 */
1923         CLEAR_CALLED(Invoke_PROGRESSCHANGE);
1924     }
1925
1926     hres = IOleInPlaceObject_GetWindow(inplace, &hwnd);
1927     ok(hres == S_OK, "GetWindow failed: %08x\n", hres);
1928     ok((hwnd == NULL) == (client == NULL), "unexpected hwnd %p\n", hwnd);
1929
1930     shell_embedding_hwnd = hwnd;
1931
1932     test_SetHostNames(oleobj);
1933
1934     IOleInPlaceObject_Release(inplace);
1935     IOleObject_Release(oleobj);
1936 }
1937
1938 static void test_ClassInfo(IWebBrowser2 *unk)
1939 {
1940     IProvideClassInfo2 *class_info;
1941     TYPEATTR *type_attr;
1942     ITypeInfo *typeinfo;
1943     GUID guid;
1944     HRESULT hres;
1945
1946     hres = IWebBrowser2_QueryInterface(unk, &IID_IProvideClassInfo2, (void**)&class_info);
1947     ok(hres == S_OK, "QueryInterface(IID_IProvideClassInfo)  failed: %08x\n", hres);
1948     if(FAILED(hres))
1949         return;
1950
1951     hres = IProvideClassInfo2_GetGUID(class_info, GUIDKIND_DEFAULT_SOURCE_DISP_IID, &guid);
1952     ok(hres == S_OK, "GetGUID failed: %08x\n", hres);
1953     ok(IsEqualGUID(wb_version > 1 ? &DIID_DWebBrowserEvents2 : &DIID_DWebBrowserEvents, &guid), "wrong guid\n");
1954
1955     hres = IProvideClassInfo2_GetGUID(class_info, 0, &guid);
1956     ok(hres == E_FAIL, "GetGUID failed: %08x, expected E_FAIL\n", hres);
1957     ok(IsEqualGUID(&IID_NULL, &guid), "wrong guid\n");
1958
1959     hres = IProvideClassInfo2_GetGUID(class_info, 2, &guid);
1960     ok(hres == E_FAIL, "GetGUID failed: %08x, expected E_FAIL\n", hres);
1961     ok(IsEqualGUID(&IID_NULL, &guid), "wrong guid\n");
1962
1963     hres = IProvideClassInfo2_GetGUID(class_info, GUIDKIND_DEFAULT_SOURCE_DISP_IID, NULL);
1964     ok(hres == E_POINTER, "GetGUID failed: %08x, expected E_POINTER\n", hres);
1965
1966     hres = IProvideClassInfo2_GetGUID(class_info, 0, NULL);
1967     ok(hres == E_POINTER, "GetGUID failed: %08x, expected E_POINTER\n", hres);
1968
1969     typeinfo = NULL;
1970     hres = IProvideClassInfo2_GetClassInfo(class_info, &typeinfo);
1971     ok(hres == S_OK, "GetClassInfo failed: %08x\n", hres);
1972     ok(typeinfo != NULL, "typeinfo == NULL\n");
1973
1974     hres = ITypeInfo_GetTypeAttr(typeinfo, &type_attr);
1975     ok(hres == S_OK, "GetTypeAtr failed: %08x\n", hres);
1976
1977     ok(IsEqualGUID(&type_attr->guid, wb_version > 1 ? &CLSID_WebBrowser : &CLSID_WebBrowser_V1),
1978        "guid = %s\n", debugstr_guid(&type_attr->guid));
1979
1980     ITypeInfo_ReleaseTypeAttr(typeinfo, type_attr);
1981     ITypeInfo_Release(typeinfo);
1982
1983     IProvideClassInfo2_Release(class_info);
1984 }
1985
1986 static void test_EnumVerbs(IWebBrowser2 *wb)
1987 {
1988     IEnumOLEVERB *enum_verbs;
1989     IOleObject *oleobj;
1990     OLEVERB verbs[20];
1991     ULONG fetched;
1992     HRESULT hres;
1993
1994     hres = IWebBrowser2_QueryInterface(wb, &IID_IOleObject, (void**)&oleobj);
1995     ok(hres == S_OK, "QueryInterface(IID_IOleObject) failed: %08x\n", hres);
1996
1997     hres = IOleObject_EnumVerbs(oleobj, &enum_verbs);
1998     IOleObject_Release(oleobj);
1999     ok(hres == S_OK, "EnumVerbs failed: %08x\n", hres);
2000     ok(enum_verbs != NULL, "enum_verbs == NULL\n");
2001
2002     fetched = 0xdeadbeef;
2003     hres = IEnumOLEVERB_Next(enum_verbs, sizeof(verbs)/sizeof(*verbs), verbs, &fetched);
2004     ok(hres == S_OK, "Next failed: %08x\n", hres);
2005     ok(!fetched, "fetched = %d\n", fetched);
2006
2007     fetched = 0xdeadbeef;
2008     hres = IEnumOLEVERB_Next(enum_verbs, 1, verbs, &fetched);
2009     ok(hres == S_OK, "Next failed: %08x\n", hres);
2010     ok(!fetched, "fetched = %d\n", fetched);
2011
2012     hres = IEnumOLEVERB_Reset(enum_verbs);
2013     ok(hres == S_OK, "Reset failed: %08x\n", hres);
2014
2015     fetched = 0xdeadbeef;
2016     hres = IEnumOLEVERB_Next(enum_verbs, 1, verbs, &fetched);
2017     ok(hres == S_OK, "Next failed: %08x\n", hres);
2018     ok(!fetched, "fetched = %d\n", fetched);
2019
2020     hres = IEnumOLEVERB_Next(enum_verbs, 1, verbs, NULL);
2021     ok(hres == S_OK, "Next failed: %08x\n", hres);
2022
2023     hres = IEnumOLEVERB_Skip(enum_verbs, 20);
2024     ok(hres == S_OK, "Reset failed: %08x\n", hres);
2025
2026     fetched = 0xdeadbeef;
2027     hres = IEnumOLEVERB_Next(enum_verbs, 1, verbs, &fetched);
2028     ok(hres == S_OK, "Next failed: %08x\n", hres);
2029     ok(!fetched, "fetched = %d\n", fetched);
2030
2031     IEnumOLEVERB_Release(enum_verbs);
2032 }
2033
2034 static void test_ie_funcs(IWebBrowser2 *wb)
2035 {
2036     IDispatch *disp;
2037     VARIANT_BOOL b;
2038     int i;
2039     LONG hwnd;
2040     HRESULT hres;
2041     BSTR sName;
2042
2043     /* HWND */
2044
2045     hwnd = 0xdeadbeef;
2046     hres = IWebBrowser2_get_HWND(wb, &hwnd);
2047     ok(hres == E_FAIL, "get_HWND failed: %08x, expected E_FAIL\n", hres);
2048     ok(hwnd == 0, "unexpected hwnd %x\n", hwnd);
2049
2050     /* MenuBar */
2051
2052     hres = IWebBrowser2_get_MenuBar(wb, &b);
2053     ok(hres == S_OK, "get_MenuBar failed: %08x\n", hres);
2054     ok(b == VARIANT_TRUE, "b=%x\n", b);
2055
2056     SET_EXPECT(Invoke_ONMENUBAR);
2057     hres = IWebBrowser2_put_MenuBar(wb, (exvb = VARIANT_FALSE));
2058     ok(hres == S_OK, "put_MenuBar failed: %08x\n", hres);
2059     CHECK_CALLED(Invoke_ONMENUBAR);
2060
2061     hres = IWebBrowser2_get_MenuBar(wb, &b);
2062     ok(hres == S_OK, "get_MenuBar failed: %08x\n", hres);
2063     ok(b == VARIANT_FALSE, "b=%x\n", b);
2064
2065     SET_EXPECT(Invoke_ONMENUBAR);
2066     hres = IWebBrowser2_put_MenuBar(wb, (exvb = 100));
2067     ok(hres == S_OK, "put_MenuBar failed: %08x\n", hres);
2068     CHECK_CALLED(Invoke_ONMENUBAR);
2069
2070     hres = IWebBrowser2_get_MenuBar(wb, &b);
2071     ok(hres == S_OK, "get_MenuBar failed: %08x\n", hres);
2072     ok(b == VARIANT_TRUE, "b=%x\n", b);
2073
2074     /* AddressBar */
2075
2076     hres = IWebBrowser2_get_AddressBar(wb, &b);
2077     ok(hres == S_OK, "get_AddressBar failed: %08x\n", hres);
2078     ok(b == VARIANT_TRUE, "b=%x\n", b);
2079
2080     SET_EXPECT(Invoke_ONADDRESSBAR);
2081     hres = IWebBrowser2_put_AddressBar(wb, (exvb = VARIANT_FALSE));
2082     ok(hres == S_OK, "put_AddressBar failed: %08x\n", hres);
2083     CHECK_CALLED(Invoke_ONADDRESSBAR);
2084
2085     hres = IWebBrowser2_get_AddressBar(wb, &b);
2086     ok(hres == S_OK, "get_MenuBar failed: %08x\n", hres);
2087     ok(b == VARIANT_FALSE, "b=%x\n", b);
2088
2089     SET_EXPECT(Invoke_ONADDRESSBAR);
2090     hres = IWebBrowser2_put_AddressBar(wb, (exvb = 100));
2091     ok(hres == S_OK, "put_AddressBar failed: %08x\n", hres);
2092     CHECK_CALLED(Invoke_ONADDRESSBAR);
2093
2094     hres = IWebBrowser2_get_AddressBar(wb, &b);
2095     ok(hres == S_OK, "get_AddressBar failed: %08x\n", hres);
2096     ok(b == VARIANT_TRUE, "b=%x\n", b);
2097
2098     SET_EXPECT(Invoke_ONADDRESSBAR);
2099     hres = IWebBrowser2_put_AddressBar(wb, (exvb = VARIANT_TRUE));
2100     ok(hres == S_OK, "put_MenuBar failed: %08x\n", hres);
2101     CHECK_CALLED(Invoke_ONADDRESSBAR);
2102
2103     /* StatusBar */
2104
2105     hres = IWebBrowser2_get_StatusBar(wb, &b);
2106     ok(hres == S_OK, "get_StatusBar failed: %08x\n", hres);
2107     ok(b == VARIANT_TRUE, "b=%x\n", b);
2108
2109     SET_EXPECT(Invoke_ONSTATUSBAR);
2110     hres = IWebBrowser2_put_StatusBar(wb, (exvb = VARIANT_TRUE));
2111     ok(hres == S_OK, "put_StatusBar failed: %08x\n", hres);
2112     CHECK_CALLED(Invoke_ONSTATUSBAR);
2113
2114     hres = IWebBrowser2_get_StatusBar(wb, &b);
2115     ok(hres == S_OK, "get_StatusBar failed: %08x\n", hres);
2116     ok(b == VARIANT_TRUE, "b=%x\n", b);
2117
2118     SET_EXPECT(Invoke_ONSTATUSBAR);
2119     hres = IWebBrowser2_put_StatusBar(wb, (exvb = VARIANT_FALSE));
2120     ok(hres == S_OK, "put_StatusBar failed: %08x\n", hres);
2121     CHECK_CALLED(Invoke_ONSTATUSBAR);
2122
2123     hres = IWebBrowser2_get_StatusBar(wb, &b);
2124     ok(hres == S_OK, "get_StatusBar failed: %08x\n", hres);
2125     ok(b == VARIANT_FALSE, "b=%x\n", b);
2126
2127     SET_EXPECT(Invoke_ONSTATUSBAR);
2128     hres = IWebBrowser2_put_StatusBar(wb, (exvb = 100));
2129     ok(hres == S_OK, "put_StatusBar failed: %08x\n", hres);
2130     CHECK_CALLED(Invoke_ONSTATUSBAR);
2131
2132     hres = IWebBrowser2_get_StatusBar(wb, &b);
2133     ok(hres == S_OK, "get_StatusBar failed: %08x\n", hres);
2134     ok(b == VARIANT_TRUE, "b=%x\n", b);
2135
2136     /* ToolBar */
2137
2138     hres = IWebBrowser2_get_ToolBar(wb, &i);
2139     ok(hres == S_OK, "get_ToolBar failed: %08x\n", hres);
2140     ok(i, "i=%x\n", i);
2141
2142     SET_EXPECT(Invoke_ONTOOLBAR);
2143     hres = IWebBrowser2_put_ToolBar(wb, (exvb = VARIANT_FALSE));
2144     ok(hres == S_OK, "put_ToolBar failed: %08x\n", hres);
2145     CHECK_CALLED(Invoke_ONTOOLBAR);
2146
2147     hres = IWebBrowser2_get_ToolBar(wb, &i);
2148     ok(hres == S_OK, "get_ToolBar failed: %08x\n", hres);
2149     ok(i == VARIANT_FALSE, "b=%x\n", i);
2150
2151     SET_EXPECT(Invoke_ONTOOLBAR);
2152     hres = IWebBrowser2_put_ToolBar(wb, (exvb = 100));
2153     ok(hres == S_OK, "put_ToolBar failed: %08x\n", hres);
2154     CHECK_CALLED(Invoke_ONTOOLBAR);
2155
2156     hres = IWebBrowser2_get_ToolBar(wb, &i);
2157     ok(hres == S_OK, "get_ToolBar failed: %08x\n", hres);
2158     ok(i, "i=%x\n", i);
2159
2160     SET_EXPECT(Invoke_ONTOOLBAR);
2161     hres = IWebBrowser2_put_ToolBar(wb, (exvb = VARIANT_TRUE));
2162     ok(hres == S_OK, "put_ToolBar failed: %08x\n", hres);
2163     CHECK_CALLED(Invoke_ONTOOLBAR);
2164
2165     /* FullScreen */
2166
2167     hres = IWebBrowser2_get_FullScreen(wb, &b);
2168     ok(hres == S_OK, "get_FullScreen failed: %08x\n", hres);
2169     ok(b == VARIANT_FALSE, "b=%x\n", b);
2170
2171     SET_EXPECT(Invoke_ONFULLSCREEN);
2172     hres = IWebBrowser2_put_FullScreen(wb, (exvb = VARIANT_TRUE));
2173     ok(hres == S_OK, "put_FullScreen failed: %08x\n", hres);
2174     CHECK_CALLED(Invoke_ONFULLSCREEN);
2175
2176     hres = IWebBrowser2_get_FullScreen(wb, &b);
2177     ok(hres == S_OK, "get_FullScreen failed: %08x\n", hres);
2178     ok(b == VARIANT_TRUE, "b=%x\n", b);
2179
2180     SET_EXPECT(Invoke_ONFULLSCREEN);
2181     hres = IWebBrowser2_put_FullScreen(wb, (exvb = 100));
2182     ok(hres == S_OK, "put_FullScreen failed: %08x\n", hres);
2183     CHECK_CALLED(Invoke_ONFULLSCREEN);
2184
2185     hres = IWebBrowser2_get_FullScreen(wb, &b);
2186     ok(hres == S_OK, "get_FullScreen failed: %08x\n", hres);
2187     ok(b == VARIANT_TRUE, "b=%x\n", b);
2188
2189     SET_EXPECT(Invoke_ONFULLSCREEN);
2190     hres = IWebBrowser2_put_FullScreen(wb, (exvb = VARIANT_FALSE));
2191     ok(hres == S_OK, "put_FullScreen failed: %08x\n", hres);
2192     CHECK_CALLED(Invoke_ONFULLSCREEN);
2193
2194     /* TheaterMode */
2195
2196     hres = IWebBrowser2_get_TheaterMode(wb, &b);
2197     ok(hres == S_OK, "get_TheaterMode failed: %08x\n", hres);
2198     ok(b == VARIANT_FALSE, "b=%x\n", b);
2199
2200     SET_EXPECT(Invoke_ONTHEATERMODE);
2201     hres = IWebBrowser2_put_TheaterMode(wb, (exvb = VARIANT_TRUE));
2202     ok(hres == S_OK, "put_TheaterMode failed: %08x\n", hres);
2203     CHECK_CALLED(Invoke_ONTHEATERMODE);
2204
2205     hres = IWebBrowser2_get_TheaterMode(wb, &b);
2206     ok(hres == S_OK, "get_TheaterMode failed: %08x\n", hres);
2207     ok(b == VARIANT_TRUE, "b=%x\n", b);
2208
2209     SET_EXPECT(Invoke_ONTHEATERMODE);
2210     hres = IWebBrowser2_put_TheaterMode(wb, (exvb = 100));
2211     ok(hres == S_OK, "put_TheaterMode failed: %08x\n", hres);
2212     CHECK_CALLED(Invoke_ONTHEATERMODE);
2213
2214     hres = IWebBrowser2_get_TheaterMode(wb, &b);
2215     ok(hres == S_OK, "get_TheaterMode failed: %08x\n", hres);
2216     ok(b == VARIANT_TRUE, "b=%x\n", b);
2217
2218     SET_EXPECT(Invoke_ONTHEATERMODE);
2219     hres = IWebBrowser2_put_TheaterMode(wb, (exvb = VARIANT_FALSE));
2220     ok(hres == S_OK, "put_TheaterMode failed: %08x\n", hres);
2221     CHECK_CALLED(Invoke_ONTHEATERMODE);
2222
2223     /* Resizable */
2224
2225     b = 0x100;
2226     hres = IWebBrowser2_get_Resizable(wb, &b);
2227     ok(hres == E_NOTIMPL, "get_Resizable failed: %08x\n", hres);
2228     ok(b == 0x100, "b=%x\n", b);
2229
2230     SET_EXPECT(Invoke_WINDOWSETRESIZABLE);
2231     hres = IWebBrowser2_put_Resizable(wb, (exvb = VARIANT_TRUE));
2232     ok(hres == S_OK, "put_Resizable failed: %08x\n", hres);
2233     CHECK_CALLED(Invoke_WINDOWSETRESIZABLE);
2234
2235     SET_EXPECT(Invoke_WINDOWSETRESIZABLE);
2236     hres = IWebBrowser2_put_Resizable(wb, (exvb = VARIANT_FALSE));
2237     ok(hres == S_OK, "put_Resizable failed: %08x\n", hres);
2238     CHECK_CALLED(Invoke_WINDOWSETRESIZABLE);
2239
2240     hres = IWebBrowser2_get_Resizable(wb, &b);
2241     ok(hres == E_NOTIMPL, "get_Resizable failed: %08x\n", hres);
2242     ok(b == 0x100, "b=%x\n", b);
2243
2244     /* Application */
2245
2246     disp = NULL;
2247     hres = IWebBrowser2_get_Application(wb, &disp);
2248     ok(hres == S_OK, "get_Application failed: %08x\n", hres);
2249     ok(disp == (void*)wb, "disp=%p, expected %p\n", disp, wb);
2250     if(disp)
2251         IDispatch_Release(disp);
2252
2253     hres = IWebBrowser2_get_Application(wb, NULL);
2254     ok(hres == E_POINTER, "get_Application failed: %08x, expected E_POINTER\n", hres);
2255
2256     /* Name */
2257     hres = IWebBrowser2_get_Name(wb, &sName);
2258     ok(hres == S_OK, "getName failed: %08x, expected S_OK\n", hres);
2259     if (is_lang_english())
2260         ok(!strcmp_wa(sName, "Microsoft Web Browser Control"), "got '%s', expected 'Microsoft Web Browser Control'\n", wine_dbgstr_w(sName));
2261     else /* Non-English cannot be blank. */
2262         ok(sName!=NULL, "get_Name return a NULL string.\n");
2263     SysFreeString(sName);
2264
2265     /* Quit */
2266
2267     hres = IWebBrowser2_Quit(wb);
2268     ok(hres == E_FAIL, "Quit failed: %08x, expected E_FAIL\n", hres);
2269 }
2270
2271 static void test_Silent(IWebBrowser2 *wb, IOleControl *control, BOOL is_clientsite)
2272 {
2273     VARIANT_BOOL b;
2274     HRESULT hres;
2275
2276     b = 100;
2277     hres = IWebBrowser2_get_Silent(wb, &b);
2278     ok(hres == S_OK, "get_Silent failed: %08x\n", hres);
2279     ok(b == VARIANT_FALSE, "b=%x\n", b);
2280
2281     hres = IWebBrowser2_put_Silent(wb, VARIANT_TRUE);
2282     ok(hres == S_OK, "set_Silent failed: %08x\n", hres);
2283
2284     b = 100;
2285     hres = IWebBrowser2_get_Silent(wb, &b);
2286     ok(hres == S_OK, "get_Silent failed: %08x\n", hres);
2287     ok(b == VARIANT_TRUE, "b=%x\n", b);
2288
2289     hres = IWebBrowser2_put_Silent(wb, 100);
2290     ok(hres == S_OK, "set_Silent failed: %08x\n", hres);
2291
2292     b = 100;
2293     hres = IWebBrowser2_get_Silent(wb, &b);
2294     ok(hres == S_OK, "get_Silent failed: %08x\n", hres);
2295     ok(b == VARIANT_TRUE, "b=%x\n", b);
2296
2297     hres = IWebBrowser2_put_Silent(wb, VARIANT_FALSE);
2298     ok(hres == S_OK, "set_Silent failed: %08x\n", hres);
2299
2300     b = 100;
2301     hres = IWebBrowser2_get_Silent(wb, &b);
2302     ok(hres == S_OK, "get_Silent failed: %08x\n", hres);
2303     ok(b == VARIANT_FALSE, "b=%x\n", b);
2304
2305     if(is_clientsite) {
2306         hres = IWebBrowser2_put_Silent(wb, VARIANT_TRUE);
2307         ok(hres == S_OK, "set_Silent failed: %08x\n", hres);
2308
2309         SET_EXPECT(Invoke_AMBIENT_SILENT);
2310     }
2311
2312     hres = IOleControl_OnAmbientPropertyChange(control, DISPID_AMBIENT_SILENT);
2313     ok(hres == S_OK, "OnAmbientPropertyChange failed %08x\n", hres);
2314
2315     if(is_clientsite)
2316         CHECK_CALLED(Invoke_AMBIENT_SILENT);
2317
2318     b = 100;
2319     hres = IWebBrowser2_get_Silent(wb, &b);
2320     ok(hres == S_OK, "get_Silent failed: %08x\n", hres);
2321     ok(b == VARIANT_FALSE, "b=%x\n", b);
2322 }
2323
2324 static void test_Offline(IWebBrowser2 *wb, IOleControl *control, BOOL is_clientsite)
2325 {
2326     VARIANT_BOOL b;
2327     HRESULT hres;
2328
2329     b = 100;
2330     hres = IWebBrowser2_get_Offline(wb, &b);
2331     ok(hres == S_OK, "get_Offline failed: %08x\n", hres);
2332     ok(b == VARIANT_FALSE, "b=%x\n", b);
2333
2334     hres = IWebBrowser2_put_Offline(wb, VARIANT_TRUE);
2335     ok(hres == S_OK, "set_Offline failed: %08x\n", hres);
2336
2337     b = 100;
2338     hres = IWebBrowser2_get_Offline(wb, &b);
2339     ok(hres == S_OK, "get_Offline failed: %08x\n", hres);
2340     ok(b == VARIANT_TRUE, "b=%x\n", b);
2341
2342     hres = IWebBrowser2_put_Offline(wb, 100);
2343     ok(hres == S_OK, "set_Offline failed: %08x\n", hres);
2344
2345     b = 100;
2346     hres = IWebBrowser2_get_Offline(wb, &b);
2347     ok(hres == S_OK, "get_Offline failed: %08x\n", hres);
2348     ok(b == VARIANT_TRUE, "b=%x\n", b);
2349
2350     hres = IWebBrowser2_put_Offline(wb, VARIANT_FALSE);
2351     ok(hres == S_OK, "set_Offline failed: %08x\n", hres);
2352
2353     b = 100;
2354     hres = IWebBrowser2_get_Offline(wb, &b);
2355     ok(hres == S_OK, "get_Offline failed: %08x\n", hres);
2356     ok(b == VARIANT_FALSE, "b=%x\n", b);
2357
2358     if(is_clientsite) {
2359         hres = IWebBrowser2_put_Offline(wb, VARIANT_TRUE);
2360         ok(hres == S_OK, "set_Offline failed: %08x\n", hres);
2361
2362         SET_EXPECT(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
2363     }
2364
2365     hres = IOleControl_OnAmbientPropertyChange(control, DISPID_AMBIENT_OFFLINEIFNOTCONNECTED);
2366     ok(hres == S_OK, "OnAmbientPropertyChange failed %08x\n", hres);
2367
2368     if(is_clientsite)
2369         CHECK_CALLED(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
2370
2371     b = 100;
2372     hres = IWebBrowser2_get_Offline(wb, &b);
2373     ok(hres == S_OK, "get_Offline failed: %08x\n", hres);
2374     ok(b == VARIANT_FALSE, "b=%x\n", b);
2375 }
2376
2377 static void test_ambient_unknown(IWebBrowser2 *wb, IOleControl *control, BOOL is_clientsite)
2378 {
2379     HRESULT hres;
2380
2381     SET_EXPECT(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
2382     SET_EXPECT(Invoke_AMBIENT_SILENT);
2383     SET_EXPECT(Invoke_AMBIENT_USERMODE);
2384     SET_EXPECT(Invoke_AMBIENT_DLCONTROL);
2385     SET_EXPECT(Invoke_AMBIENT_USERAGENT);
2386     SET_EXPECT(Invoke_AMBIENT_PALETTE);
2387
2388     hres = IOleControl_OnAmbientPropertyChange(control, DISPID_UNKNOWN);
2389     ok(hres == S_OK, "OnAmbientPropertyChange failed %08x\n", hres);
2390
2391     CHECK_EXPECT(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
2392     CHECK_EXPECT(Invoke_AMBIENT_SILENT);
2393     CHECK_EXPECT(Invoke_AMBIENT_USERMODE);
2394     CHECK_EXPECT(Invoke_AMBIENT_DLCONTROL);
2395     CHECK_EXPECT(Invoke_AMBIENT_USERAGENT);
2396     CHECK_EXPECT(Invoke_AMBIENT_PALETTE);
2397
2398     CLEAR_CALLED(Invoke_AMBIENT_OFFLINEIFNOTCONNECTED);
2399     CLEAR_CALLED(Invoke_AMBIENT_SILENT);
2400     CLEAR_CALLED(Invoke_AMBIENT_USERMODE);
2401     CLEAR_CALLED(Invoke_AMBIENT_DLCONTROL);
2402     CLEAR_CALLED(Invoke_AMBIENT_USERAGENT);
2403     CLEAR_CALLED(Invoke_AMBIENT_PALETTE);
2404 }
2405
2406 static void test_wb_funcs(IWebBrowser2 *wb, BOOL is_clientsite)
2407 {
2408     IOleControl *control;
2409     HRESULT hres;
2410
2411     hres = IWebBrowser2_QueryInterface(wb, &IID_IOleControl, (void**)&control);
2412     ok(hres == S_OK, "Could not get IOleControl interface: %08x\n", hres);
2413
2414     test_Silent(wb, control, is_clientsite);
2415     test_Offline(wb, control, is_clientsite);
2416     test_ambient_unknown(wb, control, is_clientsite);
2417
2418     IOleControl_Release(control);
2419 }
2420
2421 static void test_GetControlInfo(IWebBrowser2 *unk)
2422 {
2423     IOleControl *control;
2424     CONTROLINFO info;
2425     HRESULT hres;
2426
2427     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleControl, (void**)&control);
2428     ok(hres == S_OK, "Could not get IOleControl: %08x\n", hres);
2429     if(FAILED(hres))
2430         return;
2431
2432     hres = IOleControl_GetControlInfo(control, &info);
2433     ok(hres == E_NOTIMPL, "GetControlInfo failed: %08x, expected E_NOTIMPL\n", hres);
2434     hres = IOleControl_GetControlInfo(control, NULL);
2435     ok(hres == E_NOTIMPL, "GetControlInfo failed: %08x, expected E_NOTIMPL\n", hres);
2436
2437     IOleControl_Release(control);
2438 }
2439
2440 static void test_Extent(IWebBrowser2 *unk)
2441 {
2442     IOleObject *oleobj;
2443     SIZE size, expected;
2444     HRESULT hres;
2445     DWORD dpi_x;
2446     DWORD dpi_y;
2447     HDC hdc;
2448
2449     /* default aspect ratio is 96dpi / 96dpi */
2450     hdc = GetDC(0);
2451     dpi_x = GetDeviceCaps(hdc, LOGPIXELSX);
2452     dpi_y = GetDeviceCaps(hdc, LOGPIXELSY);
2453     ReleaseDC(0, hdc);
2454     if (dpi_x != 96 || dpi_y != 96)
2455         trace("dpi: %d / %d\n", dpi_y, dpi_y);
2456
2457     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleObject, (void**)&oleobj);
2458     ok(hres == S_OK, "Could not get IOleObkect: %08x\n", hres);
2459     if(FAILED(hres))
2460         return;
2461
2462     size.cx = size.cy = 0xdeadbeef;
2463     hres = IOleObject_GetExtent(oleobj, DVASPECT_CONTENT, &size);
2464     ok(hres == S_OK, "GetExtent failed: %08x\n", hres);
2465     /* Default size is 50x20 pixels, in himetric units */
2466     expected.cx = MulDiv( 50, 2540, dpi_x );
2467     expected.cy = MulDiv( 20, 2540, dpi_y );
2468     ok(size.cx == expected.cx && size.cy == expected.cy, "size = {%d %d} (expected %d %d)\n",
2469        size.cx, size.cy, expected.cx, expected.cy );
2470
2471     size.cx = 800;
2472     size.cy = 700;
2473     hres = IOleObject_SetExtent(oleobj, DVASPECT_CONTENT, &size);
2474     ok(hres == S_OK, "SetExtent failed: %08x\n", hres);
2475
2476     size.cx = size.cy = 0xdeadbeef;
2477     hres = IOleObject_GetExtent(oleobj, DVASPECT_CONTENT, &size);
2478     ok(hres == S_OK, "GetExtent failed: %08x\n", hres);
2479     ok(size.cx == 800 && size.cy == 700, "size = {%d %d}\n", size.cx, size.cy);
2480
2481     size.cx = size.cy = 0xdeadbeef;
2482     hres = IOleObject_GetExtent(oleobj, 0, &size);
2483     ok(hres == S_OK, "GetExtent failed: %08x\n", hres);
2484     ok(size.cx == 800 && size.cy == 700, "size = {%d %d}\n", size.cx, size.cy);
2485
2486     size.cx = 900;
2487     size.cy = 800;
2488     hres = IOleObject_SetExtent(oleobj, 0, &size);
2489     ok(hres == S_OK, "SetExtent failed: %08x\n", hres);
2490
2491     size.cx = size.cy = 0xdeadbeef;
2492     hres = IOleObject_GetExtent(oleobj, 0, &size);
2493     ok(hres == S_OK, "GetExtent failed: %08x\n", hres);
2494     ok(size.cx == 900 && size.cy == 800, "size = {%d %d}\n", size.cx, size.cy);
2495
2496     size.cx = size.cy = 0xdeadbeef;
2497     hres = IOleObject_GetExtent(oleobj, 0xdeadbeef, &size);
2498     ok(hres == S_OK, "GetExtent failed: %08x\n", hres);
2499     ok(size.cx == 900 && size.cy == 800, "size = {%d %d}\n", size.cx, size.cy);
2500
2501     size.cx = 1000;
2502     size.cy = 900;
2503     hres = IOleObject_SetExtent(oleobj, 0xdeadbeef, &size);
2504     ok(hres == S_OK, "SetExtent failed: %08x\n", hres);
2505
2506     size.cx = size.cy = 0xdeadbeef;
2507     hres = IOleObject_GetExtent(oleobj, 0xdeadbeef, &size);
2508     ok(hres == S_OK, "GetExtent failed: %08x\n", hres);
2509     ok(size.cx == 1000 && size.cy == 900, "size = {%d %d}\n", size.cx, size.cy);
2510
2511     size.cx = size.cy = 0xdeadbeef;
2512     hres = IOleObject_GetExtent(oleobj, DVASPECT_CONTENT, &size);
2513     ok(hres == S_OK, "GetExtent failed: %08x\n", hres);
2514     ok(size.cx == 1000 && size.cy == 900, "size = {%d %d}\n", size.cx, size.cy);
2515
2516     IOleObject_Release(oleobj);
2517 }
2518
2519 static void test_ConnectionPoint(IWebBrowser2 *unk, BOOL init)
2520 {
2521     IConnectionPointContainer *container;
2522     IConnectionPoint *point;
2523     HRESULT hres;
2524
2525     static DWORD dw = 100;
2526
2527     hres = IWebBrowser2_QueryInterface(unk, &IID_IConnectionPointContainer, (void**)&container);
2528     ok(hres == S_OK, "QueryInterface(IID_IConnectionPointContainer) failed: %08x\n", hres);
2529     if(FAILED(hres))
2530         return;
2531
2532     hres = IConnectionPointContainer_FindConnectionPoint(container, &DIID_DWebBrowserEvents2, &point);
2533     IConnectionPointContainer_Release(container);
2534     ok(hres == S_OK, "FindConnectionPoint failed: %08x\n", hres);
2535     if(FAILED(hres))
2536         return;
2537
2538     if(init) {
2539         hres = IConnectionPoint_Advise(point, (IUnknown*)&WebBrowserEvents2, &dw);
2540         ok(hres == S_OK, "Advise failed: %08x\n", hres);
2541         ok(dw == 1, "dw=%d, expected 1\n", dw);
2542     }else {
2543         hres = IConnectionPoint_Unadvise(point, dw);
2544         ok(hres == S_OK, "Unadvise failed: %08x\n", hres);
2545     }
2546
2547     IConnectionPoint_Release(point);
2548 }
2549
2550 static void test_Navigate2(IWebBrowser2 *webbrowser, const char *nav_url)
2551 {
2552     VARIANT url;
2553     BOOL is_file;
2554     HRESULT hres;
2555
2556     test_LocationURL(webbrowser, is_first_load ? "" : current_url);
2557     test_ready_state(is_first_load ? READYSTATE_UNINITIALIZED : READYSTATE_COMPLETE);
2558
2559     is_http = !memcmp(nav_url, "http:", 5);
2560     V_VT(&url) = VT_BSTR;
2561     V_BSTR(&url) = a2bstr(current_url = nav_url);
2562
2563     if((is_file = !strncasecmp(nav_url, "file://", 7)))
2564         current_url = nav_url + 7;
2565
2566     if(is_first_load) {
2567         SET_EXPECT(Invoke_AMBIENT_USERMODE);
2568         SET_EXPECT(Invoke_PROPERTYCHANGE);
2569         SET_EXPECT(Invoke_BEFORENAVIGATE2);
2570         SET_EXPECT(Invoke_DOWNLOADBEGIN);
2571         if (use_container_olecmd) SET_EXPECT(Exec_SETDOWNLOADSTATE_1);
2572         SET_EXPECT(EnableModeless_FALSE);
2573         SET_EXPECT(Invoke_STATUSTEXTCHANGE);
2574         SET_EXPECT(SetStatusText);
2575         if(use_container_dochostui)
2576             SET_EXPECT(GetHostInfo);
2577         SET_EXPECT(Invoke_AMBIENT_DLCONTROL);
2578         SET_EXPECT(Invoke_AMBIENT_USERAGENT);
2579         SET_EXPECT(Invoke_AMBIENT_PALETTE);
2580         if(use_container_dochostui) {
2581             SET_EXPECT(GetOptionKeyPath);
2582             SET_EXPECT(GetOverridesKeyPath);
2583         }
2584         if (use_container_olecmd) SET_EXPECT(QueryStatus_SETPROGRESSTEXT);
2585         if (use_container_olecmd) SET_EXPECT(Exec_SETPROGRESSMAX);
2586         if (use_container_olecmd) SET_EXPECT(Exec_SETPROGRESSPOS);
2587         SET_EXPECT(Invoke_SETSECURELOCKICON);
2588         SET_EXPECT(Invoke_FILEDOWNLOAD);
2589         if (use_container_olecmd) SET_EXPECT(Exec_SETDOWNLOADSTATE_0);
2590         SET_EXPECT(Invoke_COMMANDSTATECHANGE);
2591         SET_EXPECT(EnableModeless_TRUE);
2592         if (!use_container_olecmd) SET_EXPECT(Invoke_DOWNLOADCOMPLETE);
2593         if (is_file) SET_EXPECT(Invoke_PROGRESSCHANGE);
2594     }
2595
2596     hres = IWebBrowser2_Navigate2(webbrowser, &url, NULL, NULL, NULL, NULL);
2597     ok(hres == S_OK, "Navigate2 failed: %08x\n", hres);
2598
2599     if(is_first_load) {
2600         CHECK_CALLED(Invoke_AMBIENT_USERMODE);
2601         todo_wine CHECK_CALLED(Invoke_PROPERTYCHANGE);
2602         CHECK_CALLED(Invoke_BEFORENAVIGATE2);
2603         todo_wine CHECK_CALLED(Invoke_DOWNLOADBEGIN);
2604         if (use_container_olecmd) todo_wine CHECK_CALLED(Exec_SETDOWNLOADSTATE_1);
2605         CHECK_CALLED(EnableModeless_FALSE);
2606         CHECK_CALLED(Invoke_STATUSTEXTCHANGE);
2607         CHECK_CALLED(SetStatusText);
2608         if(use_container_dochostui)
2609             CHECK_CALLED(GetHostInfo);
2610         CHECK_CALLED(Invoke_AMBIENT_DLCONTROL);
2611         CHECK_CALLED(Invoke_AMBIENT_USERAGENT);
2612         CLEAR_CALLED(Invoke_AMBIENT_PALETTE); /* Not called by IE9 */
2613         if(use_container_dochostui) {
2614             CLEAR_CALLED(GetOptionKeyPath);
2615             CHECK_CALLED(GetOverridesKeyPath);
2616         }
2617         if (use_container_olecmd) todo_wine CHECK_CALLED(QueryStatus_SETPROGRESSTEXT);
2618         if (use_container_olecmd) todo_wine CHECK_CALLED(Exec_SETPROGRESSMAX);
2619         if (use_container_olecmd) todo_wine CHECK_CALLED(Exec_SETPROGRESSPOS);
2620         todo_wine CHECK_CALLED(Invoke_SETSECURELOCKICON);
2621         todo_wine CHECK_CALLED(Invoke_FILEDOWNLOAD);
2622         todo_wine CHECK_CALLED(Invoke_COMMANDSTATECHANGE);
2623         if (use_container_olecmd) todo_wine CHECK_CALLED(Exec_SETDOWNLOADSTATE_0);
2624         CHECK_CALLED(EnableModeless_TRUE);
2625         if (is_file) todo_wine CHECK_CALLED(Invoke_PROGRESSCHANGE);
2626     }
2627
2628     VariantClear(&url);
2629
2630     test_ready_state(READYSTATE_LOADING);
2631 }
2632
2633 static void test_QueryStatusWB(IWebBrowser2 *webbrowser, BOOL use_custom_target, BOOL has_document)
2634 {
2635     HRESULT hres, success_state;
2636     OLECMDF success_flags;
2637     enum OLECMDF status;
2638
2639     /*
2640      * We can tell the difference between the custom container target and the built-in target
2641      * since the custom target returns OLECMDF_SUPPORTED instead of OLECMDF_ENABLED.
2642      */
2643     if (use_custom_target)
2644         success_flags = OLECMDF_SUPPORTED;
2645     else
2646         success_flags = OLECMDF_ENABLED;
2647
2648     /* When no target is available (no document or custom target) an error is returned */
2649     if (has_document)
2650         success_state = S_OK;
2651     else
2652         success_state = E_UNEXPECTED;
2653
2654     /*
2655      * Test a safe operation that exists as both a high-numbered MSHTML id and an OLECMDID.
2656      * These tests show that QueryStatusWB uses a NULL pguidCmdGroup, since OLECMDID_STOP
2657      * is enabled and IDM_STOP is not.
2658      */
2659     status = 0xdeadbeef;
2660     if (use_custom_target) SET_EXPECT(QueryStatus_STOP);
2661     hres = IWebBrowser2_QueryStatusWB(webbrowser, OLECMDID_STOP, &status);
2662     ok(hres == success_state, "QueryStatusWB failed: %08x %08x\n", hres, success_state);
2663     if (!use_custom_target && has_document)
2664         todo_wine ok((has_document && status == success_flags) || (!has_document && status == 0xdeadbeef),
2665                      "OLECMDID_STOP not enabled/supported: %08x %08x\n", status, success_flags);
2666     else
2667         ok((has_document && status == success_flags) || (!has_document && status == 0xdeadbeef),
2668            "OLECMDID_STOP not enabled/supported: %08x %08x\n", status, success_flags);
2669     status = 0xdeadbeef;
2670     if (use_custom_target) SET_EXPECT(QueryStatus_IDM_STOP);
2671     hres = IWebBrowser2_QueryStatusWB(webbrowser, IDM_STOP, &status);
2672     ok(hres == success_state, "QueryStatusWB failed: %08x %08x\n", hres, success_state);
2673     ok((has_document && status == 0) || (!has_document && status == 0xdeadbeef),
2674        "IDM_STOP is enabled/supported: %08x %d\n", status, has_document);
2675 }
2676
2677 static void test_ExecWB(IWebBrowser2 *webbrowser, BOOL use_custom_target, BOOL has_document)
2678 {
2679     HRESULT hres, olecmdid_state, idm_state;
2680
2681     /* When no target is available (no document or custom target) an error is returned */
2682     if (has_document)
2683     {
2684         olecmdid_state = S_OK;
2685         idm_state = OLECMDERR_E_NOTSUPPORTED;
2686     }
2687     else
2688     {
2689         olecmdid_state = E_UNEXPECTED;
2690         idm_state = E_UNEXPECTED;
2691     }
2692
2693     /*
2694      * Test a safe operation that exists as both a high-numbered MSHTML id and an OLECMDID.
2695      * These tests show that QueryStatusWB uses a NULL pguidCmdGroup, since OLECMDID_STOP
2696      * succeeds (S_OK) and IDM_STOP does not (OLECMDERR_E_NOTSUPPORTED).
2697      */
2698     if(use_custom_target) {
2699         SET_EXPECT(Exec_STOP);
2700     }else if(has_document) {
2701         SET_EXPECT(Invoke_STATUSTEXTCHANGE);
2702         SET_EXPECT(SetStatusText);
2703     }
2704     hres = IWebBrowser2_ExecWB(webbrowser, OLECMDID_STOP, OLECMDEXECOPT_DONTPROMPTUSER, 0, 0);
2705     if(!use_custom_target && has_document) {
2706         todo_wine ok(hres == olecmdid_state, "ExecWB failed: %08x %08x\n", hres, olecmdid_state);
2707         CLEAR_CALLED(Invoke_STATUSTEXTCHANGE); /* Called by IE9 */
2708         CLEAR_CALLED(SetStatusText); /* Called by IE9 */
2709     }else {
2710         ok(hres == olecmdid_state, "ExecWB failed: %08x %08x\n", hres, olecmdid_state);
2711     }
2712     if (use_custom_target)
2713         SET_EXPECT(Exec_IDM_STOP);
2714     hres = IWebBrowser2_ExecWB(webbrowser, IDM_STOP, OLECMDEXECOPT_DONTPROMPTUSER, 0, 0);
2715     ok(hres == idm_state, "ExecWB failed: %08x %08x\n", hres, idm_state);
2716 }
2717
2718 static void test_download(DWORD flags)
2719 {
2720     BOOL *b = (flags & DWL_REFRESH) ? &called_Exec_SETDOWNLOADSTATE_0 : &called_Invoke_DOCUMENTCOMPLETE;
2721     MSG msg;
2722
2723     is_downloading = TRUE;
2724     dwl_flags = flags;
2725
2726     test_ready_state((flags & (DWL_FROM_PUT_HREF|DWL_FROM_GOBACK|DWL_FROM_GOFORWARD|DWL_REFRESH))
2727                      ? READYSTATE_COMPLETE : READYSTATE_LOADING);
2728
2729     if((is_http && !(flags & (DWL_FROM_GOBACK|DWL_FROM_GOFORWARD|DWL_REFRESH))) || (flags & DWL_EXPECT_BEFORE_NAVIGATE))
2730         SET_EXPECT(Invoke_PROPERTYCHANGE);
2731
2732     if(flags & DWL_EXPECT_BEFORE_NAVIGATE) {
2733         SET_EXPECT(Invoke_BEFORENAVIGATE2);
2734         SET_EXPECT(TranslateUrl);
2735     }
2736     SET_EXPECT(Exec_SETPROGRESSMAX);
2737     SET_EXPECT(Exec_SETPROGRESSPOS);
2738     SET_EXPECT(Exec_SETDOWNLOADSTATE_1);
2739     SET_EXPECT(DocHost_EnableModeless_FALSE);
2740     SET_EXPECT(DocHost_EnableModeless_TRUE);
2741     SET_EXPECT(Invoke_SETSECURELOCKICON);
2742     SET_EXPECT(Invoke_282);
2743     SET_EXPECT(EnableModeless_FALSE);
2744     SET_EXPECT(Invoke_COMMANDSTATECHANGE);
2745     SET_EXPECT(Invoke_STATUSTEXTCHANGE);
2746     SET_EXPECT(SetStatusText);
2747     SET_EXPECT(EnableModeless_TRUE);
2748     if(!is_first_load)
2749         SET_EXPECT(GetHostInfo);
2750     SET_EXPECT(Exec_SETDOWNLOADSTATE_0);
2751     SET_EXPECT(Invoke_TITLECHANGE);
2752     if(!(flags & DWL_REFRESH))
2753         SET_EXPECT(Invoke_NAVIGATECOMPLETE2);
2754     if(is_first_load)
2755         SET_EXPECT(GetDropTarget);
2756     SET_EXPECT(Invoke_PROGRESSCHANGE);
2757     if(!(flags & DWL_REFRESH))
2758         SET_EXPECT(Invoke_DOCUMENTCOMPLETE);
2759
2760     if(flags & DWL_HTTP)
2761         SET_EXPECT(Exec_SETTITLE);
2762     SET_EXPECT(UpdateUI);
2763     SET_EXPECT(Exec_UPDATECOMMANDS);
2764     SET_EXPECT(QueryStatus_STOP);
2765
2766     while(!*b && GetMessage(&msg, NULL, 0, 0)) {
2767         TranslateMessage(&msg);
2768         DispatchMessage(&msg);
2769     }
2770
2771     if((is_http && !(flags & (DWL_FROM_GOBACK|DWL_FROM_GOFORWARD|DWL_REFRESH))) || (flags & DWL_EXPECT_BEFORE_NAVIGATE))
2772         todo_wine CHECK_CALLED(Invoke_PROPERTYCHANGE);
2773
2774     if(flags & DWL_EXPECT_BEFORE_NAVIGATE) {
2775         CHECK_CALLED(Invoke_BEFORENAVIGATE2);
2776         CHECK_CALLED(TranslateUrl);
2777     }
2778     todo_wine CHECK_CALLED(Exec_SETPROGRESSMAX);
2779     todo_wine CHECK_CALLED(Exec_SETPROGRESSPOS);
2780     CHECK_CALLED(Exec_SETDOWNLOADSTATE_1);
2781     CLEAR_CALLED(DocHost_EnableModeless_FALSE); /* IE 7 */
2782     CLEAR_CALLED(DocHost_EnableModeless_TRUE); /* IE 7 */
2783     todo_wine CHECK_CALLED(Invoke_SETSECURELOCKICON);
2784     CLEAR_CALLED(Invoke_282); /* IE 7 */
2785     if(is_first_load)
2786         todo_wine CHECK_CALLED(EnableModeless_FALSE);
2787     else
2788         CLEAR_CALLED(EnableModeless_FALSE); /* IE 8 */
2789     CLEAR_CALLED(Invoke_COMMANDSTATECHANGE);
2790     todo_wine CHECK_CALLED(Invoke_STATUSTEXTCHANGE);
2791     todo_wine CHECK_CALLED(SetStatusText);
2792     if(is_first_load)
2793         todo_wine CHECK_CALLED(EnableModeless_TRUE);
2794     else
2795         CLEAR_CALLED(EnableModeless_FALSE); /* IE 8 */
2796     if(!is_first_load)
2797         todo_wine CHECK_CALLED(GetHostInfo);
2798     CHECK_CALLED(Exec_SETDOWNLOADSTATE_0);
2799     todo_wine CHECK_CALLED(Invoke_TITLECHANGE);
2800     if(!(flags & DWL_REFRESH))
2801         CHECK_CALLED(Invoke_NAVIGATECOMPLETE2);
2802     if(is_first_load)
2803         todo_wine CHECK_CALLED(GetDropTarget);
2804     if(!(flags & DWL_REFRESH))
2805         CHECK_CALLED(Invoke_DOCUMENTCOMPLETE);
2806
2807     is_downloading = FALSE;
2808
2809     test_ready_state(READYSTATE_COMPLETE);
2810
2811     while(!called_Exec_UPDATECOMMANDS && GetMessage(&msg, NULL, 0, 0)) {
2812         TranslateMessage(&msg);
2813         DispatchMessage(&msg);
2814     }
2815
2816     todo_wine CHECK_CALLED(Invoke_PROGRESSCHANGE);
2817     if(flags & DWL_HTTP)
2818         CLEAR_CALLED(Exec_SETTITLE); /* FIXME: make it more strict */
2819     CHECK_CALLED(UpdateUI);
2820     CHECK_CALLED(Exec_UPDATECOMMANDS);
2821     CLEAR_CALLED(QueryStatus_STOP);
2822 }
2823
2824 static void test_Refresh(IWebBrowser2 *webbrowser)
2825 {
2826     HRESULT hres;
2827
2828     trace("Refresh...\n");
2829
2830     SET_EXPECT(Exec_DocHostCommandHandler_2300);
2831     hres = IWebBrowser2_Refresh(webbrowser);
2832     ok(hres == S_OK, "Refresh failed: %08x\n", hres);
2833     CHECK_CALLED(Exec_DocHostCommandHandler_2300);
2834
2835     test_download(DWL_REFRESH);
2836 }
2837
2838 static void test_olecmd(IWebBrowser2 *unk, BOOL loaded)
2839 {
2840     IOleCommandTarget *cmdtrg;
2841     OLECMD cmds[3];
2842     HRESULT hres;
2843
2844     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleCommandTarget, (void**)&cmdtrg);
2845     ok(hres == S_OK, "Could not get IOleCommandTarget iface: %08x\n", hres);
2846     if(FAILED(hres))
2847         return;
2848
2849     cmds[0].cmdID = OLECMDID_SPELL;
2850     cmds[0].cmdf = 0xdeadbeef;
2851     cmds[1].cmdID = OLECMDID_REFRESH;
2852     cmds[1].cmdf = 0xdeadbeef;
2853     hres = IOleCommandTarget_QueryStatus(cmdtrg, NULL, 2, cmds, NULL);
2854     if(loaded) {
2855         ok(hres == S_OK, "QueryStatus failed: %08x\n", hres);
2856         ok(cmds[0].cmdf == OLECMDF_SUPPORTED, "OLECMDID_SPELL cmdf = %x\n", cmds[0].cmdf);
2857         ok(cmds[1].cmdf == (OLECMDF_ENABLED|OLECMDF_SUPPORTED),
2858            "OLECMDID_REFRESH cmdf = %x\n", cmds[1].cmdf);
2859     }else {
2860         ok(hres == 0x80040104, "QueryStatus failed: %08x\n", hres);
2861         ok(cmds[0].cmdf == 0xdeadbeef, "OLECMDID_SPELL cmdf = %x\n", cmds[0].cmdf);
2862         ok(cmds[1].cmdf == 0xdeadbeef, "OLECMDID_REFRESH cmdf = %x\n", cmds[0].cmdf);
2863     }
2864
2865     IOleCommandTarget_Release(cmdtrg);
2866 }
2867
2868 static void test_IServiceProvider(IWebBrowser2 *unk)
2869 {
2870     IServiceProvider *servprov = (void*)0xdeadbeef;
2871     IUnknown *iface;
2872     HRESULT hres;
2873
2874     hres = IWebBrowser2_QueryInterface(unk, &IID_IServiceProvider, (void**)&servprov);
2875     ok(hres == S_OK, "QueryInterface returned %08x, expected S_OK\n", hres);
2876     if(FAILED(hres))
2877         return;
2878
2879     hres = IServiceProvider_QueryService(servprov, &SID_STopLevelBrowser, &IID_IBrowserService2, (LPVOID*)&iface);
2880     ok(hres == E_FAIL, "QueryService returned %08x, expected E_FAIL\n", hres);
2881     ok(!iface, "QueryService returned %p, expected NULL\n", iface);
2882     if(hres == S_OK)
2883         IUnknown_Release(iface);
2884
2885     hres = IServiceProvider_QueryService(servprov, &SID_SHTMLWindow, &IID_IHTMLWindow2, (LPVOID*)&iface);
2886     ok(hres == S_OK, "QueryService returned %08x, expected S_OK\n", hres);
2887     ok(iface != NULL, "QueryService returned NULL\n");
2888     if(hres == S_OK)
2889         IUnknown_Release(iface);
2890
2891     IServiceProvider_Release(servprov);
2892 }
2893
2894 static void test_put_href(IWebBrowser2 *unk, const char *url)
2895 {
2896     IHTMLLocation *location;
2897     IHTMLDocument2 *doc;
2898     IDispatch *doc_disp;
2899     BSTR str;
2900     HRESULT hres;
2901
2902     doc_disp = get_document(unk);
2903
2904     hres = IDispatch_QueryInterface(doc_disp, &IID_IHTMLDocument2, (void**)&doc);
2905     IDispatch_Release(doc_disp);
2906     ok(hres == S_OK, "QueryInterface(IID_IHTMLDocument2 failed: %08x\n", hres);
2907
2908     location = NULL;
2909     hres = IHTMLDocument2_get_location(doc, &location);
2910     IHTMLDocument2_Release(doc);
2911     ok(hres == S_OK, "get_location failed: %08x\n", hres);
2912     ok(location != NULL, "location == NULL\n");
2913
2914     SET_EXPECT(TranslateUrl);
2915     SET_EXPECT(Invoke_BEFORENAVIGATE2);
2916     if(!is_http)
2917         SET_EXPECT(Invoke_PROPERTYCHANGE);
2918
2919     dwl_flags = DWL_FROM_PUT_HREF;
2920
2921     is_http = !memcmp(url, "http:", 5);
2922     str = a2bstr(current_url = url);
2923     is_first_load = FALSE;
2924     hres = IHTMLLocation_put_href(location, str);
2925
2926     CHECK_CALLED(TranslateUrl);
2927     CHECK_CALLED(Invoke_BEFORENAVIGATE2);
2928     if(!is_http)
2929         todo_wine CHECK_CALLED(Invoke_PROPERTYCHANGE);
2930
2931     IHTMLLocation_Release(location);
2932     SysFreeString(str);
2933     ok(hres == S_OK, "put_href failed: %08x\n", hres);
2934
2935     test_ready_state(READYSTATE_COMPLETE);
2936 }
2937
2938 static void test_go_back(IWebBrowser2 *wb, const char *back_url)
2939 {
2940     HRESULT hres;
2941
2942     current_url = back_url;
2943
2944     SET_EXPECT(Invoke_BEFORENAVIGATE2);
2945     SET_EXPECT(Invoke_COMMANDSTATECHANGE);
2946     hres = IWebBrowser2_GoBack(wb);
2947     ok(hres == S_OK, "GoBack failed: %08x\n", hres);
2948     CHECK_CALLED(Invoke_BEFORENAVIGATE2);
2949     todo_wine CHECK_CALLED(Invoke_COMMANDSTATECHANGE);
2950 }
2951
2952 static void test_go_forward(IWebBrowser2 *wb, const char *forward_url)
2953 {
2954     HRESULT hres;
2955
2956     current_url = forward_url;
2957     dwl_flags |= DWL_FROM_GOFORWARD;
2958
2959     SET_EXPECT(Invoke_BEFORENAVIGATE2);
2960     SET_EXPECT(Invoke_COMMANDSTATECHANGE);
2961     hres = IWebBrowser2_GoForward(wb);
2962     ok(hres == S_OK, "GoForward failed: %08x\n", hres);
2963     CHECK_CALLED(Invoke_BEFORENAVIGATE2);
2964     todo_wine CHECK_CALLED(Invoke_COMMANDSTATECHANGE);
2965 }
2966
2967 static void test_QueryInterface(IWebBrowser2 *wb)
2968 {
2969     IQuickActivate *qa = (IQuickActivate*)0xdeadbeef;
2970     IRunnableObject *runnable = (IRunnableObject*)0xdeadbeef;
2971     IPerPropertyBrowsing *propbrowse = (void*)0xdeadbeef;
2972     IOleInPlaceSite *inplace = (void*)0xdeadbeef;
2973     IOleCache *cache = (void*)0xdeadbeef;
2974     IObjectWithSite *site = (void*)0xdeadbeef;
2975     IViewObjectEx *viewex = (void*)0xdeadbeef;
2976     IOleLink *link = (void*)0xdeadbeef;
2977     IMarshal *marshal = (void*)0xdeadbeef;
2978     IUnknown *unk = (IUnknown*)wb;
2979     HRESULT hres;
2980
2981     hres = IUnknown_QueryInterface(unk, &IID_IQuickActivate, (void**)&qa);
2982     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
2983     ok(qa == NULL, "qa=%p, expected NULL\n", qa);
2984
2985     hres = IUnknown_QueryInterface(unk, &IID_IRunnableObject, (void**)&runnable);
2986     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
2987     ok(runnable == NULL, "runnable=%p, expected NULL\n", runnable);
2988
2989     hres = IUnknown_QueryInterface(unk, &IID_IPerPropertyBrowsing, (void**)&propbrowse);
2990     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
2991     ok(propbrowse == NULL, "propbrowse=%p, expected NULL\n", propbrowse);
2992
2993     hres = IUnknown_QueryInterface(unk, &IID_IOleCache, (void**)&cache);
2994     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
2995     ok(cache == NULL, "cache=%p, expected NULL\n", cache);
2996
2997     hres = IUnknown_QueryInterface(unk, &IID_IOleInPlaceSite, (void**)&inplace);
2998     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
2999     ok(inplace == NULL, "inplace=%p, expected NULL\n", inplace);
3000
3001     hres = IUnknown_QueryInterface(unk, &IID_IObjectWithSite, (void**)&site);
3002     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
3003     ok(site == NULL, "site=%p, expected NULL\n", site);
3004
3005     hres = IUnknown_QueryInterface(unk, &IID_IViewObjectEx, (void**)&viewex);
3006     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
3007     ok(viewex == NULL, "viewex=%p, expected NULL\n", viewex);
3008
3009     hres = IUnknown_QueryInterface(unk, &IID_IOleLink, (void**)&link);
3010     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
3011     ok(link == NULL, "link=%p, expected NULL\n", link);
3012
3013     hres = IUnknown_QueryInterface(unk, &IID_IMarshal, (void**)&marshal);
3014     ok(hres == E_NOINTERFACE, "QueryInterface returned %08x, expected E_NOINTERFACE\n", hres);
3015     ok(marshal == NULL, "marshal=%p, expected NULL\n", marshal);
3016
3017 }
3018
3019 static void test_UIActivate(IWebBrowser2 *unk, BOOL activate)
3020 {
3021     IOleDocumentView *docview;
3022     IDispatch *disp;
3023     HRESULT hres;
3024
3025     disp = get_document(unk);
3026
3027     hres = IDispatch_QueryInterface(disp, &IID_IOleDocumentView, (void**)&docview);
3028     ok(hres == S_OK, "Got 0x%08x\n", hres);
3029     if(SUCCEEDED(hres)) {
3030         if(activate) {
3031             SET_EXPECT(RequestUIActivate);
3032             SET_EXPECT(ShowUI);
3033             SET_EXPECT(HideUI);
3034             SET_EXPECT(OnFocus);
3035         }
3036
3037         hres = IOleDocumentView_UIActivate(docview, activate);
3038         if(activate)
3039             todo_wine ok(hres == S_OK, "Got 0x%08x\n", hres);
3040         else
3041             ok(hres == S_OK, "Got 0x%08x\n", hres);
3042
3043         if(activate) {
3044             todo_wine {
3045                 CHECK_CALLED(RequestUIActivate);
3046                 CHECK_CALLED(ShowUI);
3047                 CHECK_CALLED(HideUI);
3048                 CHECK_CALLED(OnFocus);
3049             }
3050         }
3051
3052         IOleDocumentView_Release(docview);
3053     }
3054
3055     IDispatch_Release(disp);
3056 }
3057
3058 static void test_external(IWebBrowser2 *unk)
3059 {
3060     IDocHostUIHandler2 *dochost;
3061     IOleClientSite *client;
3062     IDispatch *disp;
3063     HRESULT hres;
3064
3065     client = get_dochost(unk);
3066
3067     hres = IOleClientSite_QueryInterface(client, &IID_IDocHostUIHandler2, (void**)&dochost);
3068     ok(hres == S_OK, "Could not get IDocHostUIHandler2 iface: %08x\n", hres);
3069     IOleClientSite_Release(client);
3070
3071     if(use_container_dochostui)
3072         SET_EXPECT(GetExternal);
3073     disp = (void*)0xdeadbeef;
3074     hres = IDocHostUIHandler2_GetExternal(dochost, &disp);
3075     if(use_container_dochostui) {
3076         CHECK_CALLED(GetExternal);
3077         ok(hres == S_FALSE, "GetExternal failed: %08x\n", hres);
3078         ok(!disp, "disp = %p\n", disp);
3079     }else {
3080         IShellUIHelper *uihelper;
3081
3082         ok(hres == S_OK, "GetExternal failed: %08x\n", hres);
3083         ok(disp != NULL, "disp == NULL\n");
3084
3085         hres = IDispatch_QueryInterface(disp, &IID_IShellUIHelper, (void**)&uihelper);
3086         ok(hres == S_OK, "Could not get IShellUIHelper iface: %08x\n", hres);
3087         IShellUIHelper_Release(uihelper);
3088     }
3089
3090     IDocHostUIHandler2_Release(dochost);
3091 }
3092
3093 static void test_TranslateAccelerator(IWebBrowser2 *unk)
3094 {
3095     IOleClientSite *doc_clientsite;
3096     IOleInPlaceActiveObject *pao;
3097     HRESULT hres;
3098     DWORD keycode;
3099     MSG msg_a = {
3100         container_hwnd,
3101         0, 0, 0,
3102         GetTickCount(),
3103         {5, 5}
3104     };
3105
3106     test_Navigate2(unk, "about:blank");
3107
3108     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleInPlaceActiveObject, (void**)&pao);
3109     ok(hres == S_OK, "Got 0x%08x\n", hres);
3110     if(SUCCEEDED(hres)) {
3111         /* One accelerator that should be handled by mshtml */
3112         msg_a.message = WM_KEYDOWN;
3113         msg_a.wParam = VK_F1;
3114         hres = IOleInPlaceActiveObject_TranslateAccelerator(pao, &msg_a);
3115         ok(hres == S_FALSE, "Got 0x%08x (%04x::%02lx)\n", hres, msg_a.message, msg_a.wParam);
3116
3117         /* And one that should not */
3118         msg_a.message = WM_KEYDOWN;
3119         msg_a.wParam = VK_F5;
3120         hres = IOleInPlaceActiveObject_TranslateAccelerator(pao, &msg_a);
3121         ok(hres == S_FALSE, "Got 0x%08x (%04x::%02lx)\n", hres, msg_a.message, msg_a.wParam);
3122
3123         IOleInPlaceActiveObject_Release(pao);
3124     }
3125
3126     test_UIActivate(unk, TRUE);
3127
3128     /* Test again after UIActivate */
3129     hres = IWebBrowser2_QueryInterface(unk, &IID_IOleInPlaceActiveObject, (void**)&pao);
3130     ok(hres == S_OK, "Got 0x%08x\n", hres);
3131     if(SUCCEEDED(hres)) {
3132         /* One accelerator that should be handled by mshtml */
3133         msg_a.message = WM_KEYDOWN;
3134         msg_a.wParam = VK_F1;
3135         SET_EXPECT(DocHost_TranslateAccelerator);
3136         SET_EXPECT(ControlSite_TranslateAccelerator);
3137         hres = IOleInPlaceActiveObject_TranslateAccelerator(pao, &msg_a);
3138         ok(hres == S_FALSE, "Got 0x%08x (%04x::%02lx)\n", hres, msg_a.message, msg_a.wParam);
3139         todo_wine CHECK_CALLED(DocHost_TranslateAccelerator);
3140         todo_wine CHECK_CALLED(ControlSite_TranslateAccelerator);
3141
3142         /* And one that should not */
3143         msg_a.message = WM_KEYDOWN;
3144         msg_a.wParam = VK_F5;
3145         SET_EXPECT(DocHost_TranslateAccelerator);
3146         hres = IOleInPlaceActiveObject_TranslateAccelerator(pao, &msg_a);
3147         todo_wine ok(hres == S_OK, "Got 0x%08x (%04x::%02lx)\n", hres, msg_a.message, msg_a.wParam);
3148         todo_wine CHECK_CALLED(DocHost_TranslateAccelerator);
3149
3150         IOleInPlaceActiveObject_Release(pao);
3151     }
3152
3153     doc_clientsite = get_dochost(unk);
3154     if(doc_clientsite) {
3155         IDocHostUIHandler2 *dochost;
3156         IOleControlSite *doc_controlsite;
3157         IUnknown *unk_test;
3158
3159         hres = IOleClientSite_QueryInterface(doc_clientsite, &IID_IOleInPlaceFrame, (void**)&unk_test);
3160         ok(hres == E_NOINTERFACE, "Got 0x%08x\n", hres);
3161         if(SUCCEEDED(hres)) IUnknown_Release(unk_test);
3162
3163         hres = IOleClientSite_QueryInterface(doc_clientsite, &IID_IDocHostShowUI, (void**)&unk_test);
3164         todo_wine ok(hres == S_OK, "Got 0x%08x\n", hres);
3165         if(SUCCEEDED(hres)) IUnknown_Release(unk_test);
3166
3167         hres = IOleClientSite_QueryInterface(doc_clientsite, &IID_IDocHostUIHandler, (void**)&unk_test);
3168         ok(hres == S_OK, "Got 0x%08x\n", hres);
3169         if(SUCCEEDED(hres)) IUnknown_Release(unk_test);
3170
3171         hres = IOleClientSite_QueryInterface(doc_clientsite, &IID_IDocHostUIHandler2, (void**)&dochost);
3172         ok(hres == S_OK, "Got 0x%08x\n", hres);
3173         if(SUCCEEDED(hres)) {
3174             msg_a.message = WM_KEYDOWN;
3175             hr_dochost_TranslateAccelerator = 0xdeadbeef;
3176             for(keycode = 0; keycode <= 0x100; keycode++) {
3177                 msg_a.wParam = keycode;
3178                 SET_EXPECT(DocHost_TranslateAccelerator);
3179                 hres = IDocHostUIHandler2_TranslateAccelerator(dochost, &msg_a, &CGID_MSHTML, 1234);
3180                 ok(hres == 0xdeadbeef, "Got 0x%08x\n", hres);
3181                 CHECK_CALLED(DocHost_TranslateAccelerator);
3182             }
3183             hr_dochost_TranslateAccelerator = E_NOTIMPL;
3184
3185             SET_EXPECT(DocHost_TranslateAccelerator);
3186             hres = IDocHostUIHandler2_TranslateAccelerator(dochost, &msg_a, &CGID_MSHTML, 1234);
3187             ok(hres == E_NOTIMPL, "Got 0x%08x\n", hres);
3188             CHECK_CALLED(DocHost_TranslateAccelerator);
3189
3190             IDocHostUIHandler2_Release(dochost);
3191         }
3192
3193         hres = IOleClientSite_QueryInterface(doc_clientsite, &IID_IOleControlSite, (void**)&doc_controlsite);
3194         ok(hres == S_OK, "Got 0x%08x\n", hres);
3195         if(SUCCEEDED(hres)) {
3196             msg_a.message = WM_KEYDOWN;
3197             hr_site_TranslateAccelerator = 0xdeadbeef;
3198             for(keycode = 0; keycode < 0x100; keycode++) {
3199                 msg_a.wParam = keycode;
3200                 SET_EXPECT(ControlSite_TranslateAccelerator);
3201                 hres = IOleControlSite_TranslateAccelerator(doc_controlsite, &msg_a, 0);
3202                 if(keycode == 0x9 || keycode == 0x75)
3203                     todo_wine ok(hres == S_OK, "Got 0x%08x (keycode: %04x)\n", hres, keycode);
3204                 else
3205                     ok(hres == S_FALSE, "Got 0x%08x (keycode: %04x)\n", hres, keycode);
3206
3207                 CHECK_CALLED(ControlSite_TranslateAccelerator);
3208             }
3209             msg_a.wParam = VK_LEFT;
3210             SET_EXPECT(ControlSite_TranslateAccelerator);
3211             hres = IOleControlSite_TranslateAccelerator(doc_controlsite, &msg_a, 0);
3212             ok(hres == S_FALSE, "Got 0x%08x (keycode: %04x)\n", hres, keycode);
3213             CHECK_CALLED(ControlSite_TranslateAccelerator);
3214
3215             hr_site_TranslateAccelerator = S_OK;
3216             SET_EXPECT(ControlSite_TranslateAccelerator);
3217             hres = IOleControlSite_TranslateAccelerator(doc_controlsite, &msg_a, 0);
3218             ok(hres == S_OK, "Got 0x%08x (keycode: %04x)\n", hres, keycode);
3219             CHECK_CALLED(ControlSite_TranslateAccelerator);
3220
3221             hr_site_TranslateAccelerator = E_NOTIMPL;
3222             SET_EXPECT(ControlSite_TranslateAccelerator);
3223             hres = IOleControlSite_TranslateAccelerator(doc_controlsite, &msg_a, 0);
3224             ok(hres == S_FALSE, "Got 0x%08x (keycode: %04x)\n", hres, keycode);
3225             CHECK_CALLED(ControlSite_TranslateAccelerator);
3226
3227             IOleControlSite_Release(doc_controlsite);
3228         }
3229
3230         IOleClientSite_Release(doc_clientsite);
3231     }
3232
3233     test_UIActivate(unk, FALSE);
3234 }
3235
3236 static void test_dochost_qs(IWebBrowser2 *webbrowser)
3237 {
3238     IOleClientSite *client_site;
3239     IServiceProvider *serv_prov;
3240     IUnknown *service;
3241     HRESULT hres;
3242
3243     client_site = get_dochost(webbrowser);
3244     hres = IOleClientSite_QueryInterface(client_site, &IID_IServiceProvider, (void**)&serv_prov);
3245     IOleClientSite_Release(client_site);
3246     ok(hres == S_OK, "Could not get IServiceProvider iface: %08x\n", hres);
3247
3248     hres = IServiceProvider_QueryService(serv_prov, &IID_IHlinkFrame, &IID_IHlinkFrame, (void**)&service);
3249     ok(hres == S_OK, "QueryService failed: %08x\n", hres);
3250     ok(iface_cmp(service, (IUnknown*)webbrowser), "service != unk\n");
3251     IUnknown_Release(service);
3252
3253     hres = IServiceProvider_QueryService(serv_prov, &IID_IWebBrowserApp, &IID_IHlinkFrame, (void**)&service);
3254     ok(hres == S_OK, "QueryService failed: %08x\n", hres);
3255     ok(iface_cmp(service, (IUnknown*)webbrowser), "service != unk\n");
3256     IUnknown_Release(service);
3257
3258     hres = IServiceProvider_QueryService(serv_prov, &IID_IShellBrowser, &IID_IShellBrowser, (void**)&service);
3259     ok(hres == S_OK, "QueryService failed: %08x\n", hres);
3260     IUnknown_Release(service);
3261
3262     hres = IServiceProvider_QueryService(serv_prov, &IID_IShellBrowser, &IID_IBrowserService, (void**)&service);
3263     ok(hres == S_OK, "QueryService failed: %08x\n", hres);
3264     IUnknown_Release(service);
3265
3266     hres = IServiceProvider_QueryService(serv_prov, &IID_IShellBrowser, &IID_IDocObjectService, (void**)&service);
3267     ok(hres == S_OK, "QueryService failed: %08x\n", hres);
3268     IUnknown_Release(service);
3269
3270     IServiceProvider_Release(serv_prov);
3271 }
3272
3273 static void test_Close(IWebBrowser2 *wb, BOOL do_download)
3274 {
3275     IOleObject *oo;
3276     IOleClientSite *ocs;
3277     HRESULT hres;
3278
3279     hres = IWebBrowser2_QueryInterface(wb, &IID_IOleObject, (void**)&oo);
3280     ok(hres == S_OK, "QueryInterface failed: %08x\n", hres);
3281     if(hres != S_OK)
3282         return;
3283
3284     test_close = TRUE;
3285
3286     SET_EXPECT(Frame_SetActiveObject);
3287     SET_EXPECT(UIWindow_SetActiveObject);
3288     SET_EXPECT(OnUIDeactivate);
3289     SET_EXPECT(OnFocus);
3290     SET_EXPECT(OnInPlaceDeactivate);
3291     SET_EXPECT(Invoke_STATUSTEXTCHANGE);
3292     if(!do_download) {
3293         SET_EXPECT(Invoke_COMMANDSTATECHANGE);
3294         SET_EXPECT(Invoke_DOWNLOADCOMPLETE);
3295     }
3296     hres = IOleObject_Close(oo, OLECLOSE_NOSAVE);
3297     ok(hres == S_OK, "OleObject_Close failed: %x\n", hres);
3298     CHECK_CALLED(Frame_SetActiveObject);
3299     CHECK_CALLED(UIWindow_SetActiveObject);
3300     CHECK_CALLED(OnUIDeactivate);
3301     todo_wine CHECK_CALLED(OnFocus);
3302     CHECK_CALLED(OnInPlaceDeactivate);
3303     CLEAR_CALLED(Invoke_STATUSTEXTCHANGE); /* Called by IE9 */
3304     if(!do_download) {
3305         todo_wine CHECK_CALLED(Invoke_COMMANDSTATECHANGE);
3306         todo_wine CHECK_CALLED(Invoke_DOWNLOADCOMPLETE);
3307     }
3308
3309     hres = IOleObject_GetClientSite(oo, &ocs);
3310     ok(hres == S_OK, "hres = %x\n", hres);
3311     ok(!ocs, "ocs != NULL\n");
3312
3313     hres = IOleObject_Close(oo, OLECLOSE_NOSAVE);
3314     ok(hres == S_OK, "OleObject_Close failed: %x\n", hres);
3315
3316     test_close = FALSE;
3317     IOleObject_Release(oo);
3318 }
3319
3320 #define TEST_DOWNLOAD    0x0001
3321 #define TEST_NOOLECMD    0x0002
3322 #define TEST_NODOCHOST   0x0004
3323
3324 static void init_test(IWebBrowser2 *webbrowser, DWORD flags)
3325 {
3326     wb = webbrowser;
3327
3328     is_downloading = (flags & TEST_DOWNLOAD) != 0;
3329     is_first_load = TRUE;
3330     dwl_flags = 0;
3331     use_container_olecmd = !(flags & TEST_NOOLECMD);
3332     use_container_dochostui = !(flags & TEST_NODOCHOST);
3333 }
3334
3335 static void test_WebBrowser(BOOL do_download, BOOL do_close)
3336 {
3337     IWebBrowser2 *webbrowser;
3338     ULONG ref;
3339
3340     webbrowser = create_webbrowser();
3341     if(!webbrowser)
3342         return;
3343
3344     init_test(webbrowser, do_download ? TEST_DOWNLOAD : 0);
3345
3346     test_QueryStatusWB(webbrowser, FALSE, FALSE);
3347     test_ExecWB(webbrowser, FALSE, FALSE);
3348     test_QueryInterface(webbrowser);
3349     test_ready_state(READYSTATE_UNINITIALIZED);
3350     test_ClassInfo(webbrowser);
3351     test_EnumVerbs(webbrowser);
3352     test_LocationURL(webbrowser, "");
3353     test_ConnectionPoint(webbrowser, TRUE);
3354     test_ClientSite(webbrowser, &ClientSite, !do_download);
3355     test_Extent(webbrowser);
3356     test_wb_funcs(webbrowser, TRUE);
3357     test_DoVerb(webbrowser);
3358     test_olecmd(webbrowser, FALSE);
3359     test_Navigate2(webbrowser, "about:blank");
3360     test_QueryStatusWB(webbrowser, TRUE, TRUE);
3361     test_ExecWB(webbrowser, TRUE, TRUE);
3362
3363     if(do_download) {
3364         IDispatch *doc, *doc2;
3365
3366         test_download(0);
3367         test_olecmd(webbrowser, TRUE);
3368         doc = get_document(webbrowser);
3369
3370         test_put_href(webbrowser, "about:test");
3371         test_download(DWL_FROM_PUT_HREF);
3372         doc2 = get_document(webbrowser);
3373         ok(doc == doc2, "doc != doc2\n");
3374         IDispatch_Release(doc2);
3375
3376         trace("Navigate2 repeated...\n");
3377         test_Navigate2(webbrowser, "about:blank");
3378         test_download(DWL_EXPECT_BEFORE_NAVIGATE);
3379         doc2 = get_document(webbrowser);
3380         ok(doc == doc2, "doc != doc2\n");
3381         IDispatch_Release(doc2);
3382         IDispatch_Release(doc);
3383
3384         if(!do_close) {
3385             trace("Navigate2 http URL...\n");
3386             test_ready_state(READYSTATE_COMPLETE);
3387             test_Navigate2(webbrowser, "http://test.winehq.org/tests/hello.html");
3388             test_download(DWL_EXPECT_BEFORE_NAVIGATE|DWL_HTTP);
3389
3390             test_Refresh(webbrowser);
3391
3392             trace("put_href http URL...\n");
3393             test_put_href(webbrowser, "http://www.winehq.org/");
3394             test_download(DWL_FROM_PUT_HREF|DWL_HTTP);
3395
3396             trace("GoBack...\n");
3397             test_go_back(webbrowser, "http://test.winehq.org/tests/hello.html");
3398             test_download(DWL_FROM_GOBACK|DWL_HTTP);
3399
3400             trace("GoForward...\n");
3401             test_go_forward(webbrowser, "http://www.winehq.org/");
3402             test_download(DWL_FROM_GOFORWARD|DWL_HTTP);
3403         }
3404
3405         test_EnumVerbs(webbrowser);
3406         test_TranslateAccelerator(webbrowser);
3407
3408         test_dochost_qs(webbrowser);
3409     }
3410
3411     test_external(webbrowser);
3412
3413     if(do_close)
3414         test_Close(webbrowser, do_download);
3415     else
3416         test_ClientSite(webbrowser, NULL, !do_download);
3417     test_ie_funcs(webbrowser);
3418     test_GetControlInfo(webbrowser);
3419     test_wb_funcs(webbrowser, FALSE);
3420     test_ConnectionPoint(webbrowser, FALSE);
3421     test_IServiceProvider(webbrowser);
3422
3423     ref = IWebBrowser2_Release(webbrowser);
3424     ok(ref == 0 || broken(do_download && !do_close), "ref=%d, expected 0\n", ref);
3425 }
3426
3427 static void test_WebBrowserV1(void)
3428 {
3429     IWebBrowser2 *wb;
3430     ULONG ref;
3431     HRESULT hres;
3432
3433     hres = CoCreateInstance(&CLSID_WebBrowser_V1, NULL, CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER,
3434             &IID_IWebBrowser2, (void**)&wb);
3435     ok(hres == S_OK, "Could not get WebBrowserV1 instance: %08x\n", hres);
3436
3437     init_test(wb, 0);
3438     wb_version = 1;
3439
3440     test_QueryStatusWB(wb, FALSE, FALSE);
3441     test_ExecWB(wb, FALSE, FALSE);
3442     test_QueryInterface(wb);
3443     test_ready_state(READYSTATE_UNINITIALIZED);
3444     test_ClassInfo(wb);
3445     test_EnumVerbs(wb);
3446
3447     ref = IWebBrowser2_Release(wb);
3448     ok(ref == 0, "ref=%d, expected 0\n", ref);
3449 }
3450
3451 static void test_WebBrowser_slim_container(void)
3452 {
3453     IWebBrowser2 *webbrowser;
3454     ULONG ref;
3455
3456     webbrowser = create_webbrowser();
3457     init_test(webbrowser, TEST_NOOLECMD|TEST_NODOCHOST);
3458
3459     test_ConnectionPoint(webbrowser, TRUE);
3460     test_ClientSite(webbrowser, &ClientSite, TRUE);
3461     test_DoVerb(webbrowser);
3462     test_Navigate2(webbrowser, "about:blank");
3463
3464     /* Tests of interest */
3465     test_QueryStatusWB(webbrowser, FALSE, TRUE);
3466     test_ExecWB(webbrowser, FALSE, TRUE);
3467     test_external(webbrowser);
3468
3469     /* Cleanup stage */
3470     test_ClientSite(webbrowser, NULL, TRUE);
3471     test_ConnectionPoint(webbrowser, FALSE);
3472
3473     ref = IWebBrowser2_Release(webbrowser);
3474     ok(ref == 0, "ref=%d, expected 0\n", ref);
3475 }
3476
3477 static void test_WebBrowser_DoVerb(void)
3478 {
3479     IWebBrowser2 *webbrowser;
3480     RECT rect;
3481     HWND hwnd;
3482     ULONG ref;
3483     BOOL res;
3484
3485     webbrowser = create_webbrowser();
3486     init_test(webbrowser, 0);
3487
3488     test_ClientSite(webbrowser, &ClientSite, FALSE);
3489
3490     SET_EXPECT(CanInPlaceActivate);
3491     SET_EXPECT(Site_GetWindow);
3492     SET_EXPECT(OnInPlaceActivate);
3493     SET_EXPECT(GetWindowContext);
3494     SET_EXPECT(ShowObject);
3495     SET_EXPECT(GetContainer);
3496     SET_EXPECT(Frame_GetWindow);
3497     call_DoVerb(webbrowser, OLEIVERB_INPLACEACTIVATE);
3498     CHECK_CALLED(CanInPlaceActivate);
3499     CHECK_CALLED(Site_GetWindow);
3500     CHECK_CALLED(OnInPlaceActivate);
3501     CHECK_CALLED(GetWindowContext);
3502     CHECK_CALLED(ShowObject);
3503     CHECK_CALLED(GetContainer);
3504     CHECK_CALLED(Frame_GetWindow);
3505
3506     hwnd = get_hwnd(webbrowser);
3507
3508     memset(&rect, 0xa, sizeof(rect));
3509     res = GetWindowRect(hwnd, &rect);
3510     ok(res, "GetWindowRect failed: %u\n", GetLastError());
3511
3512     SET_EXPECT(OnInPlaceDeactivate);
3513     call_DoVerb(webbrowser, OLEIVERB_HIDE);
3514     CHECK_CALLED(OnInPlaceDeactivate);
3515
3516     test_ClientSite(webbrowser, NULL, FALSE);
3517
3518     ref = IWebBrowser2_Release(webbrowser);
3519     ok(ref == 0, "ref=%d, expected 0\n", ref);
3520 }
3521
3522
3523 /* Check if Internet Explorer is configured to run in "Enhanced Security Configuration" (aka hardened mode) */
3524 /* Note: this code is duplicated in dlls/mshtml/tests/mshtml_test.h and dlls/urlmon/tests/sec_mgr.c */
3525 static BOOL is_ie_hardened(void)
3526 {
3527     HKEY zone_map;
3528     DWORD ie_harden, type, size;
3529
3530     ie_harden = 0;
3531     if(RegOpenKeyEx(HKEY_CURRENT_USER, "Software\\Microsoft\\Windows\\CurrentVersion\\Internet Settings\\ZoneMap",
3532                     0, KEY_QUERY_VALUE, &zone_map) == ERROR_SUCCESS) {
3533         size = sizeof(DWORD);
3534         if (RegQueryValueEx(zone_map, "IEHarden", NULL, &type, (LPBYTE) &ie_harden, &size) != ERROR_SUCCESS ||
3535             type != REG_DWORD) {
3536             ie_harden = 0;
3537         }
3538         RegCloseKey(zone_map);
3539     }
3540
3541     return ie_harden != 0;
3542 }
3543
3544 static void test_FileProtocol(void)
3545 {
3546     IWebBrowser2 *webbrowser;
3547     HANDLE file;
3548     ULONG ref;
3549     char file_path[MAX_PATH];
3550     char file_url[MAX_PATH] = "File://";
3551
3552     static const char test_file[] = "wine_test.html";
3553
3554     GetTempPathA(MAX_PATH, file_path);
3555     strcat(file_path, test_file);
3556
3557     webbrowser = create_webbrowser();
3558     if(!webbrowser)
3559         return;
3560
3561     init_test(webbrowser, 0);
3562
3563     file = CreateFileA(file_path, GENERIC_WRITE, 0, NULL,
3564             CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
3565     if(file == INVALID_HANDLE_VALUE && GetLastError() != ERROR_FILE_EXISTS){
3566         ok(0, "CreateFile failed\n");
3567         return;
3568     }
3569     CloseHandle(file);
3570
3571     GetLongPathNameA(file_path, file_path, sizeof(file_path));
3572     strcat(file_url, file_path);
3573
3574     test_ConnectionPoint(webbrowser, TRUE);
3575     test_ClientSite(webbrowser, &ClientSite, TRUE);
3576     test_DoVerb(webbrowser);
3577     test_Navigate2(webbrowser, file_url);
3578     test_ClientSite(webbrowser, NULL, TRUE);
3579
3580     ref = IWebBrowser2_Release(webbrowser);
3581     ok(ref == 0, "ref=%u, expected 0\n", ref);
3582
3583     if(file != INVALID_HANDLE_VALUE)
3584         DeleteFileA(file_path);
3585 }
3586
3587 START_TEST(webbrowser)
3588 {
3589     OleInitialize(NULL);
3590
3591     container_hwnd = create_container_window();
3592
3593     trace("Testing WebBrowser (no download)...\n");
3594     test_WebBrowser(FALSE, FALSE);
3595     test_WebBrowser(FALSE, TRUE);
3596
3597     if(!is_ie_hardened()) {
3598         trace("Testing WebBrowser...\n");
3599         test_WebBrowser(TRUE, FALSE);
3600     }else {
3601         win_skip("Skipping http tests in hardened mode\n");
3602     }
3603
3604     trace("Testing WebBrowser DoVerb\n");
3605     test_WebBrowser_DoVerb();
3606     trace("Testing WebBrowser (with close)...\n");
3607     test_WebBrowser(TRUE, TRUE);
3608     trace("Testing WebBrowser w/o container-based olecmd...\n");
3609     test_WebBrowser_slim_container();
3610     trace("Testing WebBrowserV1...\n");
3611     test_WebBrowserV1();
3612     test_FileProtocol();
3613
3614     OleUninitialize();
3615 }