mshtml: Use inner window directly in HTMLImageElementFactory implementation.
[wine] / dlls / jscript / tests / activex.c
1 /*
2  * Copyright 2009 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 #include <stdio.h>
20
21 #define COBJMACROS
22 #define CONST_VTABLE
23
24 #include <ole2.h>
25 #include <dispex.h>
26 #include <activscp.h>
27 #include <objsafe.h>
28 #include <urlmon.h>
29 #include <mshtmhst.h>
30
31 #include "wine/test.h"
32
33 #ifdef _WIN64
34
35 #define IActiveScriptParse_QueryInterface IActiveScriptParse64_QueryInterface
36 #define IActiveScriptParse_Release IActiveScriptParse64_Release
37 #define IActiveScriptParse_InitNew IActiveScriptParse64_InitNew
38 #define IActiveScriptParse_ParseScriptText IActiveScriptParse64_ParseScriptText
39 #define IActiveScriptParseProcedure2_Release \
40     IActiveScriptParseProcedure2_64_Release
41 #define IActiveScriptParseProcedure2_ParseProcedureText \
42     IActiveScriptParseProcedure2_64_ParseProcedureText
43
44 #else
45
46 #define IActiveScriptParse_QueryInterface IActiveScriptParse32_QueryInterface
47 #define IActiveScriptParse_Release IActiveScriptParse32_Release
48 #define IActiveScriptParse_InitNew IActiveScriptParse32_InitNew
49 #define IActiveScriptParse_ParseScriptText IActiveScriptParse32_ParseScriptText
50 #define IActiveScriptParseProcedure2_Release \
51     IActiveScriptParseProcedure2_32_Release
52 #define IActiveScriptParseProcedure2_ParseProcedureText \
53     IActiveScriptParseProcedure2_32_ParseProcedureText
54
55 #endif
56
57 static const CLSID CLSID_JScript =
58     {0xf414c260,0x6ac0,0x11cf,{0xb6,0xd1,0x00,0xaa,0x00,0xbb,0xbb,0x58}};
59
60 #define DEFINE_EXPECT(func) \
61     static BOOL expect_ ## func = FALSE, called_ ## func = FALSE
62
63 #define SET_EXPECT(func) \
64     expect_ ## func = TRUE
65
66 #define CHECK_EXPECT2(func) \
67     do { \
68         ok(expect_ ##func, "unexpected call " #func "\n"); \
69         called_ ## func = TRUE; \
70     }while(0)
71
72 #define CHECK_EXPECT(func) \
73     do { \
74         CHECK_EXPECT2(func); \
75         expect_ ## func = FALSE; \
76     }while(0)
77
78 #define CHECK_CALLED(func) \
79     do { \
80         ok(called_ ## func, "expected " #func "\n"); \
81         expect_ ## func = called_ ## func = FALSE; \
82     }while(0)
83
84 DEFINE_EXPECT(CreateInstance);
85 DEFINE_EXPECT(ProcessUrlAction);
86 DEFINE_EXPECT(QueryCustomPolicy);
87 DEFINE_EXPECT(reportSuccess);
88 DEFINE_EXPECT(Host_QS_SecMgr);
89 DEFINE_EXPECT(Caller_QS_SecMgr);
90 DEFINE_EXPECT(QI_IObjectWithSite);
91 DEFINE_EXPECT(SetSite);
92
93 static const WCHAR testW[] = {'t','e','s','t',0};
94
95 static HRESULT QS_SecMgr_hres;
96 static HRESULT ProcessUrlAction_hres;
97 static DWORD ProcessUrlAction_policy;
98 static HRESULT CreateInstance_hres;
99 static HRESULT QueryCustomPolicy_hres;
100 static DWORD QueryCustomPolicy_psize;
101 static DWORD QueryCustomPolicy_policy;
102 static HRESULT QI_IDispatch_hres;
103 static HRESULT SetSite_hres;
104 static BOOL AllowIServiceProvider;
105
106 #define TESTOBJ_CLSID "{178fc163-f585-4e24-9c13-4bb7faf80646}"
107
108 static const GUID CLSID_TestObj =
109     {0x178fc163,0xf585,0x4e24,{0x9c,0x13,0x4b,0xb7,0xfa,0xf8,0x06,0x46}};
110
111 /* Defined as extern in urlmon.idl, but not exported by uuid.lib */
112 const GUID GUID_CUSTOM_CONFIRMOBJECTSAFETY =
113     {0x10200490,0xfa38,0x11d0,{0xac,0x0e,0x00,0xa0,0xc9,0xf,0xff,0xc0}};
114
115 #define DISPID_TEST_REPORTSUCCESS    0x1000
116
117 #define DISPID_GLOBAL_OK             0x2000
118
119 static const char *debugstr_guid(REFIID riid)
120 {
121     static char buf[50];
122
123     sprintf(buf, "{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}",
124             riid->Data1, riid->Data2, riid->Data3, riid->Data4[0],
125             riid->Data4[1], riid->Data4[2], riid->Data4[3], riid->Data4[4],
126             riid->Data4[5], riid->Data4[6], riid->Data4[7]);
127
128     return buf;
129 }
130
131 static BSTR a2bstr(const char *str)
132 {
133     BSTR ret;
134     int len;
135
136     len = MultiByteToWideChar(CP_ACP, 0, str, -1, NULL, 0);
137     ret = SysAllocStringLen(NULL, len-1);
138     MultiByteToWideChar(CP_ACP, 0, str, -1, ret, len);
139
140     return ret;
141 }
142
143 static int strcmp_wa(LPCWSTR strw, const char *stra)
144 {
145     CHAR buf[512];
146     WideCharToMultiByte(CP_ACP, 0, strw, -1, buf, sizeof(buf), 0, 0);
147     return lstrcmpA(buf, stra);
148 }
149
150 static HRESULT WINAPI ObjectWithSite_QueryInterface(IObjectWithSite *iface, REFIID riid, void **ppv)
151 {
152     ok(0, "unexpected call\n");
153     return E_NOTIMPL;
154 }
155
156 static ULONG WINAPI ObjectWithSite_AddRef(IObjectWithSite *iface)
157 {
158     return 2;
159 }
160
161 static ULONG WINAPI ObjectWithSite_Release(IObjectWithSite *iface)
162 {
163     return 1;
164 }
165
166 static HRESULT WINAPI ObjectWithSite_SetSite(IObjectWithSite *iface, IUnknown *pUnkSite)
167 {
168     IServiceProvider *sp;
169     HRESULT hres;
170
171
172     CHECK_EXPECT(SetSite);
173     ok(pUnkSite != NULL, "pUnkSite == NULL\n");
174
175     hres = IUnknown_QueryInterface(pUnkSite, &IID_IServiceProvider, (void**)&sp);
176     ok(hres == S_OK, "Could not get IServiceProvider iface: %08x\n", hres);
177     IServiceProvider_Release(sp);
178
179     return SetSite_hres;
180 }
181
182 static HRESULT WINAPI ObjectWithSite_GetSite(IObjectWithSite *iface, REFIID riid, void **ppvSite)
183 {
184     ok(0, "unexpected call\n");
185     return E_NOTIMPL;
186 }
187
188 static const IObjectWithSiteVtbl ObjectWithSiteVtbl = {
189     ObjectWithSite_QueryInterface,
190     ObjectWithSite_AddRef,
191     ObjectWithSite_Release,
192     ObjectWithSite_SetSite,
193     ObjectWithSite_GetSite
194 };
195
196 static IObjectWithSite ObjectWithSite = { &ObjectWithSiteVtbl };
197
198 static IObjectWithSite *object_with_site;
199
200 static HRESULT WINAPI DispatchEx_QueryInterface(IDispatchEx *iface, REFIID riid, void **ppv)
201 {
202     *ppv = NULL;
203
204     if(IsEqualGUID(riid, &IID_IUnknown)) {
205        *ppv = iface;
206     }else if(IsEqualGUID(riid, &IID_IDispatch) || IsEqualGUID(riid, &IID_IDispatchEx)) {
207         if(FAILED(QI_IDispatch_hres))
208             return QI_IDispatch_hres;
209         *ppv = iface;
210     }else if(IsEqualGUID(&IID_IObjectWithSite, riid)) {
211         CHECK_EXPECT(QI_IObjectWithSite);
212         *ppv = object_with_site;
213     }else if(IsEqualGUID(&IID_IObjectSafety, riid)) {
214         ok(0, "Unexpected IID_IObjectSafety query\n");
215     }
216
217     return *ppv ? S_OK : E_NOINTERFACE;
218 }
219
220 static ULONG WINAPI DispatchEx_AddRef(IDispatchEx *iface)
221 {
222     return 2;
223 }
224
225 static ULONG WINAPI DispatchEx_Release(IDispatchEx *iface)
226 {
227     return 1;
228 }
229
230 static HRESULT WINAPI DispatchEx_GetTypeInfoCount(IDispatchEx *iface, UINT *pctinfo)
231 {
232     ok(0, "unexpected call\n");
233     return E_NOTIMPL;
234 }
235
236 static HRESULT WINAPI DispatchEx_GetTypeInfo(IDispatchEx *iface, UINT iTInfo,
237                                               LCID lcid, ITypeInfo **ppTInfo)
238 {
239     ok(0, "unexpected call\n");
240     return E_NOTIMPL;
241 }
242
243 static HRESULT WINAPI DispatchEx_GetIDsOfNames(IDispatchEx *iface, REFIID riid,
244                                                 LPOLESTR *rgszNames, UINT cNames,
245                                                 LCID lcid, DISPID *rgDispId)
246 {
247     ok(0, "unexpected call\n");
248     return E_NOTIMPL;
249 }
250
251 static HRESULT WINAPI DispatchEx_Invoke(IDispatchEx *iface, DISPID dispIdMember,
252                             REFIID riid, LCID lcid, WORD wFlags, DISPPARAMS *pDispParams,
253                             VARIANT *pVarResult, EXCEPINFO *pExcepInfo, UINT *puArgErr)
254 {
255     ok(0, "unexpected call\n");
256     return E_NOTIMPL;
257 }
258
259 static HRESULT WINAPI DispatchEx_DeleteMemberByName(IDispatchEx *iface, BSTR bstrName, DWORD grfdex)
260 {
261     ok(0, "unexpected call %s %x\n", wine_dbgstr_w(bstrName), grfdex);
262     return E_NOTIMPL;
263 }
264
265 static HRESULT WINAPI DispatchEx_DeleteMemberByDispID(IDispatchEx *iface, DISPID id)
266 {
267     ok(0, "unexpected call\n");
268     return E_NOTIMPL;
269 }
270
271 static HRESULT WINAPI DispatchEx_GetMemberProperties(IDispatchEx *iface, DISPID id, DWORD grfdexFetch, DWORD *pgrfdex)
272 {
273     ok(0, "unexpected call\n");
274     return E_NOTIMPL;
275 }
276
277 static HRESULT WINAPI DispatchEx_GetMemberName(IDispatchEx *iface, DISPID id, BSTR *pbstrName)
278 {
279     ok(0, "unexpected call\n");
280     return E_NOTIMPL;
281 }
282
283 static HRESULT WINAPI DispatchEx_GetNextDispID(IDispatchEx *iface, DWORD grfdex, DISPID id, DISPID *pid)
284 {
285     ok(0, "unexpected call\n");
286     return E_NOTIMPL;
287 }
288
289 static HRESULT WINAPI DispatchEx_GetNameSpaceParent(IDispatchEx *iface, IUnknown **ppunk)
290 {
291     ok(0, "unexpected call\n");
292     return E_NOTIMPL;
293 }
294
295 static HRESULT WINAPI Test_GetDispID(IDispatchEx *iface, BSTR bstrName, DWORD grfdex, DISPID *pid)
296 {
297     if(!strcmp_wa(bstrName, "reportSuccess")) {
298         ok(grfdex == fdexNameCaseSensitive, "grfdex = %x\n", grfdex);
299         *pid = DISPID_TEST_REPORTSUCCESS;
300         return S_OK;
301     }
302
303     ok(0, "unexpected name %s\n", wine_dbgstr_w(bstrName));
304     return E_NOTIMPL;
305 }
306
307 static HRESULT WINAPI Test_InvokeEx(IDispatchEx *iface, DISPID id, LCID lcid, WORD wFlags, DISPPARAMS *pdp,
308         VARIANT *pvarRes, EXCEPINFO *pei, IServiceProvider *pspCaller)
309 {
310     switch(id) {
311     case DISPID_TEST_REPORTSUCCESS:
312         CHECK_EXPECT(reportSuccess);
313
314         ok(wFlags == INVOKE_FUNC, "wFlags = %x\n", wFlags);
315         ok(pdp != NULL, "pdp == NULL\n");
316         ok(!pdp->rgdispidNamedArgs, "rgdispidNamedArgs != NULL\n");
317         ok(pdp->cArgs == 0, "cArgs = %d\n", pdp->cArgs);
318         ok(!pdp->cNamedArgs, "cNamedArgs = %d\n", pdp->cNamedArgs);
319         ok(!pvarRes, "pvarRes != NULL\n");
320         ok(pei != NULL, "pei == NULL\n");
321         break;
322
323     default:
324         ok(0, "unexpected call\n");
325         return E_NOTIMPL;
326     }
327
328     return S_OK;
329 }
330
331 static IDispatchExVtbl testObjVtbl = {
332     DispatchEx_QueryInterface,
333     DispatchEx_AddRef,
334     DispatchEx_Release,
335     DispatchEx_GetTypeInfoCount,
336     DispatchEx_GetTypeInfo,
337     DispatchEx_GetIDsOfNames,
338     DispatchEx_Invoke,
339     Test_GetDispID,
340     Test_InvokeEx,
341     DispatchEx_DeleteMemberByName,
342     DispatchEx_DeleteMemberByDispID,
343     DispatchEx_GetMemberProperties,
344     DispatchEx_GetMemberName,
345     DispatchEx_GetNextDispID,
346     DispatchEx_GetNameSpaceParent
347 };
348
349 static IDispatchEx testObj = { &testObjVtbl };
350
351 static HRESULT WINAPI Global_GetDispID(IDispatchEx *iface, BSTR bstrName, DWORD grfdex, DISPID *pid)
352 {
353     if(!strcmp_wa(bstrName, "ok")) {
354         ok(grfdex == fdexNameCaseSensitive, "grfdex = %x\n", grfdex);
355         *pid = DISPID_GLOBAL_OK;
356         return S_OK;
357     }
358
359     ok(0, "unexpected name %s\n", wine_dbgstr_w(bstrName));
360     return E_NOTIMPL;
361 }
362
363 static HRESULT WINAPI Global_InvokeEx(IDispatchEx *iface, DISPID id, LCID lcid, WORD wFlags, DISPPARAMS *pdp,
364         VARIANT *pvarRes, EXCEPINFO *pei, IServiceProvider *pspCaller)
365 {
366     switch(id) {
367     case DISPID_GLOBAL_OK:
368         ok(wFlags == INVOKE_FUNC || wFlags == (INVOKE_FUNC|INVOKE_PROPERTYGET), "wFlags = %x\n", wFlags);
369         ok(pdp != NULL, "pdp == NULL\n");
370         ok(pdp->rgvarg != NULL, "rgvarg == NULL\n");
371         ok(!pdp->rgdispidNamedArgs, "rgdispidNamedArgs != NULL\n");
372         ok(pdp->cArgs == 2, "cArgs = %d\n", pdp->cArgs);
373         ok(!pdp->cNamedArgs, "cNamedArgs = %d\n", pdp->cNamedArgs);
374         ok(pei != NULL, "pei == NULL\n");
375
376         ok(V_VT(pdp->rgvarg) == VT_BSTR, "V_VT(psp->rgvargs) = %d\n", V_VT(pdp->rgvarg));
377         ok(V_VT(pdp->rgvarg+1) == VT_BOOL, "V_VT(psp->rgvargs+1) = %d\n", V_VT(pdp->rgvarg));
378         ok(V_BOOL(pdp->rgvarg+1), "%s\n", wine_dbgstr_w(V_BSTR(pdp->rgvarg)));
379         break;
380
381     default:
382         ok(0, "unexpected call\n");
383         return E_NOTIMPL;
384     }
385
386     return S_OK;
387 }
388
389 static IDispatchExVtbl globalObjVtbl = {
390     DispatchEx_QueryInterface,
391     DispatchEx_AddRef,
392     DispatchEx_Release,
393     DispatchEx_GetTypeInfoCount,
394     DispatchEx_GetTypeInfo,
395     DispatchEx_GetIDsOfNames,
396     DispatchEx_Invoke,
397     Global_GetDispID,
398     Global_InvokeEx,
399     DispatchEx_DeleteMemberByName,
400     DispatchEx_DeleteMemberByDispID,
401     DispatchEx_GetMemberProperties,
402     DispatchEx_GetMemberName,
403     DispatchEx_GetNextDispID,
404     DispatchEx_GetNameSpaceParent
405 };
406
407 static IDispatchEx globalObj = { &globalObjVtbl };
408
409 static HRESULT WINAPI ClassFactory_QueryInterface(IClassFactory *iface, REFIID riid, void **ppv)
410 {
411     if(IsEqualGUID(&IID_IUnknown, riid) || IsEqualGUID(&IID_IClassFactory, riid)) {
412         *ppv = iface;
413         return S_OK;
414     }
415
416     /* TODO: IClassFactoryEx */
417     *ppv = NULL;
418     return E_NOINTERFACE;
419 }
420
421 static ULONG WINAPI ClassFactory_AddRef(IClassFactory *iface)
422 {
423     return 2;
424 }
425
426 static ULONG WINAPI ClassFactory_Release(IClassFactory *iface)
427 {
428     return 1;
429 }
430
431 static HRESULT WINAPI ClassFactory_CreateInstance(IClassFactory *iface, IUnknown *outer, REFIID riid, void **ppv)
432 {
433     CHECK_EXPECT(CreateInstance);
434
435     ok(!outer, "outer = %p\n", outer);
436     ok(IsEqualGUID(&IID_IUnknown, riid), "unexpected riid %s\n", debugstr_guid(riid));
437
438     if(SUCCEEDED(CreateInstance_hres))
439         *ppv = &testObj;
440     return CreateInstance_hres;
441 }
442
443 static HRESULT WINAPI ClassFactory_LockServer(IClassFactory *iface, BOOL dolock)
444 {
445     ok(0, "unexpected call\n");
446     return S_OK;
447 }
448
449 static const IClassFactoryVtbl ClassFactoryVtbl = {
450     ClassFactory_QueryInterface,
451     ClassFactory_AddRef,
452     ClassFactory_Release,
453     ClassFactory_CreateInstance,
454     ClassFactory_LockServer
455 };
456
457 static IClassFactory activex_cf = { &ClassFactoryVtbl };
458
459 static HRESULT WINAPI InternetHostSecurityManager_QueryInterface(IInternetHostSecurityManager *iface, REFIID riid, void **ppv)
460 {
461     ok(0, "unexpected call\n");
462     return E_NOINTERFACE;
463 }
464
465 static ULONG WINAPI InternetHostSecurityManager_AddRef(IInternetHostSecurityManager *iface)
466 {
467     return 2;
468 }
469
470 static ULONG WINAPI InternetHostSecurityManager_Release(IInternetHostSecurityManager *iface)
471 {
472     return 1;
473 }
474
475 static HRESULT WINAPI InternetHostSecurityManager_GetSecurityId(IInternetHostSecurityManager *iface,  BYTE *pbSecurityId,
476         DWORD *pcbSecurityId, DWORD_PTR dwReserved)
477 {
478     ok(0, "unexpected call\n");
479     return E_NOTIMPL;
480 }
481
482 static HRESULT WINAPI InternetHostSecurityManager_ProcessUrlAction(IInternetHostSecurityManager *iface, DWORD dwAction,
483         BYTE *pPolicy, DWORD cbPolicy, BYTE *pContext, DWORD cbContext, DWORD dwFlags, DWORD dwReserved)
484 {
485     CHECK_EXPECT(ProcessUrlAction);
486
487     ok(dwAction == URLACTION_ACTIVEX_RUN, "dwAction = %x\n", dwAction);
488     ok(pPolicy != NULL, "pPolicy == NULL\n");
489     ok(cbPolicy == sizeof(DWORD), "cbPolicy = %d\n", cbPolicy);
490     ok(pContext != NULL, "pContext == NULL\n");
491     ok(cbContext == sizeof(GUID), "cbContext = %d\n", cbContext);
492     ok(IsEqualGUID(pContext, &CLSID_TestObj), "pContext = %s\n", debugstr_guid((const IID*)pContext));
493     ok(!dwFlags, "dwFlags = %x\n", dwFlags);
494     ok(!dwReserved, "dwReserved = %x\n", dwReserved);
495
496     if(SUCCEEDED(ProcessUrlAction_hres))
497         *(DWORD*)pPolicy = ProcessUrlAction_policy;
498     return ProcessUrlAction_hres;
499 }
500
501 static HRESULT WINAPI InternetHostSecurityManager_QueryCustomPolicy(IInternetHostSecurityManager *iface, REFGUID guidKey,
502         BYTE **ppPolicy, DWORD *pcbPolicy, BYTE *pContext, DWORD cbContext, DWORD dwReserved)
503 {
504     const struct CONFIRMSAFETY *cs = (const struct CONFIRMSAFETY*)pContext;
505     DWORD *ret;
506
507     CHECK_EXPECT(QueryCustomPolicy);
508
509     ok(IsEqualGUID(&GUID_CUSTOM_CONFIRMOBJECTSAFETY, guidKey), "guidKey = %s\n", debugstr_guid(guidKey));
510
511     ok(ppPolicy != NULL, "ppPolicy == NULL\n");
512     ok(pcbPolicy != NULL, "pcbPolicy == NULL\n");
513     ok(pContext != NULL, "pContext == NULL\n");
514     ok(cbContext == sizeof(struct CONFIRMSAFETY), "cbContext = %d\n", cbContext);
515     ok(!dwReserved, "dwReserved = %x\n", dwReserved);
516
517     /* TODO: CLSID */
518     ok(cs->pUnk != NULL, "cs->pUnk == NULL\n");
519     ok(!cs->dwFlags, "dwFlags = %x\n", cs->dwFlags);
520
521     if(FAILED(QueryCustomPolicy_hres))
522         return QueryCustomPolicy_hres;
523
524     ret = CoTaskMemAlloc(QueryCustomPolicy_psize);
525     *ppPolicy = (BYTE*)ret;
526     *pcbPolicy = QueryCustomPolicy_psize;
527     memset(ret, 0, QueryCustomPolicy_psize);
528     if(QueryCustomPolicy_psize >= sizeof(DWORD))
529         *ret = QueryCustomPolicy_policy;
530
531     return QueryCustomPolicy_hres;
532 }
533
534 static const IInternetHostSecurityManagerVtbl InternetHostSecurityManagerVtbl = {
535     InternetHostSecurityManager_QueryInterface,
536     InternetHostSecurityManager_AddRef,
537     InternetHostSecurityManager_Release,
538     InternetHostSecurityManager_GetSecurityId,
539     InternetHostSecurityManager_ProcessUrlAction,
540     InternetHostSecurityManager_QueryCustomPolicy
541 };
542
543 static IInternetHostSecurityManager InternetHostSecurityManager = { &InternetHostSecurityManagerVtbl };
544
545 static IServiceProvider ServiceProvider;
546
547 static HRESULT WINAPI ServiceProvider_QueryInterface(IServiceProvider *iface, REFIID riid, void **ppv)
548 {
549     ok(0, "unexpected call\n");
550     return E_NOINTERFACE;
551 }
552
553 static ULONG WINAPI ServiceProvider_AddRef(IServiceProvider *iface)
554 {
555     return 2;
556 }
557
558 static ULONG WINAPI ServiceProvider_Release(IServiceProvider *iface)
559 {
560     return 1;
561 }
562
563 static HRESULT WINAPI ServiceProvider_QueryService(IServiceProvider *iface,
564         REFGUID guidService, REFIID riid, void **ppv)
565 {
566     if(IsEqualGUID(&SID_GetCaller, guidService))
567         return E_NOINTERFACE;
568
569     if(IsEqualGUID(&SID_SInternetHostSecurityManager, guidService)) {
570         if(iface == &ServiceProvider)
571             CHECK_EXPECT(Host_QS_SecMgr);
572         else
573             CHECK_EXPECT(Caller_QS_SecMgr);
574         ok(IsEqualGUID(&IID_IInternetHostSecurityManager, riid), "unexpected riid %s\n", debugstr_guid(riid));
575         if(SUCCEEDED(QS_SecMgr_hres))
576             *ppv = &InternetHostSecurityManager;
577         return QS_SecMgr_hres;
578     }
579
580     ok(0, "unexpected service %s\n", debugstr_guid(guidService));
581     return E_NOINTERFACE;
582 }
583
584 static IServiceProviderVtbl ServiceProviderVtbl = {
585     ServiceProvider_QueryInterface,
586     ServiceProvider_AddRef,
587     ServiceProvider_Release,
588     ServiceProvider_QueryService
589 };
590
591 static IServiceProvider ServiceProvider = { &ServiceProviderVtbl };
592 static IServiceProvider caller_sp = { &ServiceProviderVtbl };
593
594 static HRESULT WINAPI ActiveScriptSite_QueryInterface(IActiveScriptSite *iface, REFIID riid, void **ppv)
595 {
596     if(IsEqualGUID(&IID_IUnknown, riid)) {
597         *ppv = iface;
598     }else if(IsEqualGUID(&IID_IActiveScriptSite, riid)) {
599         *ppv = iface;
600     }else if(IsEqualGUID(&IID_IServiceProvider, riid) && AllowIServiceProvider) {
601         *ppv = &ServiceProvider;
602     }else {
603         *ppv = NULL;
604         return E_NOINTERFACE;
605     }
606
607     IUnknown_AddRef((IUnknown*)*ppv);
608     return S_OK;
609 }
610
611 static ULONG WINAPI ActiveScriptSite_AddRef(IActiveScriptSite *iface)
612 {
613     return 2;
614 }
615
616 static ULONG WINAPI ActiveScriptSite_Release(IActiveScriptSite *iface)
617 {
618     return 1;
619 }
620
621 static HRESULT WINAPI ActiveScriptSite_GetLCID(IActiveScriptSite *iface, LCID *plcid)
622 {
623     *plcid = GetUserDefaultLCID();
624     return S_OK;
625 }
626
627 static HRESULT WINAPI ActiveScriptSite_GetItemInfo(IActiveScriptSite *iface, LPCOLESTR pstrName,
628         DWORD dwReturnMask, IUnknown **ppiunkItem, ITypeInfo **ppti)
629 {
630     ok(dwReturnMask == SCRIPTINFO_IUNKNOWN, "unexpected dwReturnMask %x\n", dwReturnMask);
631     ok(!ppti, "ppti != NULL\n");
632     ok(!strcmp_wa(pstrName, "test"), "pstrName = %s\n", wine_dbgstr_w(pstrName));
633
634     *ppiunkItem = (IUnknown*)&globalObj;
635     return S_OK;
636 }
637
638 static HRESULT WINAPI ActiveScriptSite_GetDocVersionString(IActiveScriptSite *iface, BSTR *pbstrVersion)
639 {
640     return E_NOTIMPL;
641 }
642
643 static HRESULT WINAPI ActiveScriptSite_OnScriptTerminate(IActiveScriptSite *iface,
644         const VARIANT *pvarResult, const EXCEPINFO *pexcepinfo)
645 {
646     return E_NOTIMPL;
647 }
648
649 static HRESULT WINAPI ActiveScriptSite_OnStateChange(IActiveScriptSite *iface, SCRIPTSTATE ssScriptState)
650 {
651     return E_NOTIMPL;
652 }
653
654 static HRESULT WINAPI ActiveScriptSite_OnScriptError(IActiveScriptSite *iface, IActiveScriptError *pscripterror)
655 {
656     return E_NOTIMPL;
657 }
658
659 static HRESULT WINAPI ActiveScriptSite_OnEnterScript(IActiveScriptSite *iface)
660 {
661     return E_NOTIMPL;
662 }
663
664 static HRESULT WINAPI ActiveScriptSite_OnLeaveScript(IActiveScriptSite *iface)
665 {
666     return E_NOTIMPL;
667 }
668
669 #undef ACTSCPSITE_THIS
670
671 static const IActiveScriptSiteVtbl ActiveScriptSiteVtbl = {
672     ActiveScriptSite_QueryInterface,
673     ActiveScriptSite_AddRef,
674     ActiveScriptSite_Release,
675     ActiveScriptSite_GetLCID,
676     ActiveScriptSite_GetItemInfo,
677     ActiveScriptSite_GetDocVersionString,
678     ActiveScriptSite_OnScriptTerminate,
679     ActiveScriptSite_OnStateChange,
680     ActiveScriptSite_OnScriptError,
681     ActiveScriptSite_OnEnterScript,
682     ActiveScriptSite_OnLeaveScript
683 };
684
685 static IActiveScriptSite ActiveScriptSite = { &ActiveScriptSiteVtbl };
686
687 static void set_safety_options(IUnknown *unk, BOOL use_sec_mgr)
688 {
689     IObjectSafety *safety;
690     DWORD supported, enabled, options_all, options_set;
691     HRESULT hres;
692
693     hres = IUnknown_QueryInterface(unk, &IID_IObjectSafety, (void**)&safety);
694     ok(hres == S_OK, "Could not get IObjectSafety: %08x\n", hres);
695     if(FAILED(hres))
696         return;
697
698     options_all = INTERFACESAFE_FOR_UNTRUSTED_DATA|INTERFACE_USES_DISPEX|INTERFACE_USES_SECURITY_MANAGER;
699     if(use_sec_mgr)
700         options_set = options_all;
701     else
702         options_set = INTERFACE_USES_DISPEX;
703
704     hres = IObjectSafety_SetInterfaceSafetyOptions(safety, &IID_IActiveScriptParse, options_all, options_set);
705     ok(hres == S_OK, "SetInterfaceSafetyOptions failed: %08x\n", hres);
706
707     supported = enabled = 0xdeadbeef;
708     hres = IObjectSafety_GetInterfaceSafetyOptions(safety, &IID_IActiveScriptParse, &supported, &enabled);
709     ok(hres == S_OK, "GetInterfaceSafetyOptions failed: %08x\n", hres);
710     ok(supported == options_all, "supported=%x, expected %x\n", supported, options_all);
711     ok(enabled == options_set, "enabled=%x, expected %x\n", enabled, options_set);
712
713     IObjectSafety_Release(safety);
714 }
715
716 #define parse_script_a(p,s) _parse_script_a(__LINE__,p,s)
717 static void _parse_script_a(unsigned line, IActiveScriptParse *parser, const char *script)
718 {
719     BSTR str;
720     HRESULT hres;
721
722     str = a2bstr(script);
723     hres = IActiveScriptParse_ParseScriptText(parser, str, NULL, NULL, NULL, 0, 0, 0, NULL, NULL);
724     SysFreeString(str);
725     ok_(__FILE__,line)(hres == S_OK, "ParseScriptText failed: %08x\n", hres);
726 }
727
728 static IActiveScriptParse *create_script(BOOL skip_tests, BOOL use_sec_mgr)
729 {
730     IActiveScriptParse *parser;
731     IActiveScript *script;
732     HRESULT hres;
733
734     QS_SecMgr_hres = S_OK;
735     ProcessUrlAction_hres = S_OK;
736     ProcessUrlAction_policy = URLPOLICY_ALLOW;
737     CreateInstance_hres = S_OK;
738     QueryCustomPolicy_hres = S_OK;
739     QueryCustomPolicy_psize = sizeof(DWORD);
740     QueryCustomPolicy_policy = URLPOLICY_ALLOW;
741     QI_IDispatch_hres = S_OK;
742     SetSite_hres = S_OK;
743     AllowIServiceProvider = TRUE;
744
745     hres = CoCreateInstance(&CLSID_JScript, NULL, CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER,
746             &IID_IActiveScript, (void**)&script);
747     if(!skip_tests)
748         ok(hres == S_OK, "CoCreateInstance failed: %08x\n", hres);
749     if(FAILED(hres))
750         return NULL;
751
752     if(!skip_tests)
753         set_safety_options((IUnknown*)script, use_sec_mgr);
754
755     hres = IActiveScript_QueryInterface(script, &IID_IActiveScriptParse, (void**)&parser);
756     ok(hres == S_OK, "Could not get IActiveScriptParse: %08x\n", hres);
757
758     hres = IActiveScriptParse_InitNew(parser);
759     ok(hres == S_OK, "InitNew failed: %08x\n", hres);
760
761     hres = IActiveScript_SetScriptSite(script, &ActiveScriptSite);
762     ok(hres == S_OK, "SetScriptSite failed: %08x\n", hres);
763
764     hres = IActiveScript_AddNamedItem(script, testW,
765             SCRIPTITEM_ISVISIBLE|SCRIPTITEM_ISSOURCE|SCRIPTITEM_GLOBALMEMBERS);
766     ok(hres == S_OK, "AddNamedItem failed: %08x\n", hres);
767
768     hres = IActiveScript_SetScriptState(script, SCRIPTSTATE_STARTED);
769     ok(hres == S_OK, "SetScriptState(SCRIPTSTATE_STARTED) failed: %08x\n", hres);
770
771     IActiveScript_Release(script);
772
773     if(!skip_tests) {
774         parse_script_a(parser,
775                 "function testException(func, type, number) {\n"
776                 "    try {\n"
777                 "        func();\n"
778                 "    }catch(e) {\n"
779                 "        ok(e.name === type, 'e.name = ' + e.name + ', expected ' + type)\n"
780                 "        ok(e.number === number, 'e.number = ' + e.number + ', expected ' + number);\n"
781                 "        return;\n"
782                 "    }\n"
783                 "    ok(false, 'exception expected');\n"
784                 "}");
785     }
786
787     return parser;
788 }
789
790 static IDispatchEx *parse_procedure_a(IActiveScriptParse *parser, const char *src)
791 {
792     IActiveScriptParseProcedure2 *parse_proc;
793     IDispatchEx *dispex;
794     IDispatch *disp;
795     BSTR str;
796     HRESULT hres;
797
798     hres = IActiveScriptParse_QueryInterface(parser, &IID_IActiveScriptParseProcedure2, (void**)&parse_proc);
799     ok(hres == S_OK, "Could not get IActiveScriptParseProcedure2: %08x\n", hres);
800
801     str = a2bstr(src);
802     hres = IActiveScriptParseProcedure2_ParseProcedureText(parse_proc, str, NULL, NULL, NULL, NULL, NULL, 0, 0, 0, &disp);
803     SysFreeString(str);
804     IActiveScriptParseProcedure2_Release(parse_proc);
805     ok(hres == S_OK, "ParseProcedureText failed: %08x\n", hres);
806     ok(disp != NULL, "disp == NULL\n");
807
808     hres = IDispatch_QueryInterface(disp, &IID_IDispatchEx, (void**)&dispex);
809     IDispatch_Release(disp);
810     ok(hres == S_OK, "Could not get IDispatchEx iface: %08x\n", hres);
811
812     return dispex;
813 }
814
815 #define call_procedure(p,c) _call_procedure(__LINE__,p,c)
816 static void _call_procedure(unsigned line, IDispatchEx *proc, IServiceProvider *caller)
817 {
818     DISPPARAMS dp = {NULL,NULL,0,0};
819     EXCEPINFO ei = {0};
820     HRESULT hres;
821
822     hres = IDispatchEx_InvokeEx(proc, DISPID_VALUE, 0, DISPATCH_METHOD, &dp, NULL, &ei, caller);
823     ok_(__FILE__,line)(hres == S_OK, "InvokeEx failed: %08x\n", hres);
824
825 }
826
827 static void test_ActiveXObject(void)
828 {
829     IActiveScriptParse *parser;
830     IDispatchEx *proc;
831
832     parser = create_script(FALSE, TRUE);
833
834     SET_EXPECT(Host_QS_SecMgr);
835     SET_EXPECT(ProcessUrlAction);
836     SET_EXPECT(CreateInstance);
837     SET_EXPECT(QueryCustomPolicy);
838     SET_EXPECT(QI_IObjectWithSite);
839     SET_EXPECT(reportSuccess);
840     parse_script_a(parser, "(new ActiveXObject('Wine.Test')).reportSuccess();");
841     CHECK_CALLED(Host_QS_SecMgr);
842     CHECK_CALLED(ProcessUrlAction);
843     CHECK_CALLED(CreateInstance);
844     CHECK_CALLED(QueryCustomPolicy);
845     CHECK_CALLED(QI_IObjectWithSite);
846     CHECK_CALLED(reportSuccess);
847
848     proc = parse_procedure_a(parser, "(new ActiveXObject('Wine.Test')).reportSuccess();");
849
850     SET_EXPECT(ProcessUrlAction);
851     SET_EXPECT(CreateInstance);
852     SET_EXPECT(QueryCustomPolicy);
853     SET_EXPECT(QI_IObjectWithSite);
854     SET_EXPECT(reportSuccess);
855     call_procedure(proc, NULL);
856     CHECK_CALLED(ProcessUrlAction);
857     CHECK_CALLED(CreateInstance);
858     CHECK_CALLED(QueryCustomPolicy);
859     CHECK_CALLED(QI_IObjectWithSite);
860     CHECK_CALLED(reportSuccess);
861
862     SET_EXPECT(ProcessUrlAction);
863     SET_EXPECT(CreateInstance);
864     SET_EXPECT(QueryCustomPolicy);
865     SET_EXPECT(QI_IObjectWithSite);
866     SET_EXPECT(reportSuccess);
867     call_procedure(proc, &caller_sp);
868     CHECK_CALLED(ProcessUrlAction);
869     CHECK_CALLED(CreateInstance);
870     CHECK_CALLED(QueryCustomPolicy);
871     CHECK_CALLED(QI_IObjectWithSite);
872     CHECK_CALLED(reportSuccess);
873
874     IDispatchEx_Release(proc);
875     IActiveScriptParse_Release(parser);
876
877     parser = create_script(FALSE, TRUE);
878     proc = parse_procedure_a(parser, "(new ActiveXObject('Wine.Test')).reportSuccess();");
879
880     SET_EXPECT(Host_QS_SecMgr);
881     SET_EXPECT(ProcessUrlAction);
882     SET_EXPECT(CreateInstance);
883     SET_EXPECT(QueryCustomPolicy);
884     SET_EXPECT(QI_IObjectWithSite);
885     SET_EXPECT(reportSuccess);
886     call_procedure(proc, &caller_sp);
887     CHECK_CALLED(Host_QS_SecMgr);
888     CHECK_CALLED(ProcessUrlAction);
889     CHECK_CALLED(CreateInstance);
890     CHECK_CALLED(QueryCustomPolicy);
891     CHECK_CALLED(QI_IObjectWithSite);
892     CHECK_CALLED(reportSuccess);
893
894     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.TestABC'); }, 'Error', -2146827859);");
895
896     IDispatchEx_Release(proc);
897     IActiveScriptParse_Release(parser);
898
899     parser = create_script(FALSE, TRUE);
900     QS_SecMgr_hres = E_NOINTERFACE;
901
902     SET_EXPECT(Host_QS_SecMgr);
903     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
904     CHECK_CALLED(Host_QS_SecMgr);
905
906     IActiveScriptParse_Release(parser);
907
908     parser = create_script(FALSE, TRUE);
909     ProcessUrlAction_hres = E_FAIL;
910
911     SET_EXPECT(Host_QS_SecMgr);
912     SET_EXPECT(ProcessUrlAction);
913     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
914     CHECK_CALLED(Host_QS_SecMgr);
915     CHECK_CALLED(ProcessUrlAction);
916
917     IActiveScriptParse_Release(parser);
918
919     parser = create_script(FALSE, TRUE);
920     ProcessUrlAction_policy = URLPOLICY_DISALLOW;
921
922     SET_EXPECT(Host_QS_SecMgr);
923     SET_EXPECT(ProcessUrlAction);
924     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
925     CHECK_CALLED(Host_QS_SecMgr);
926     CHECK_CALLED(ProcessUrlAction);
927
928     IActiveScriptParse_Release(parser);
929
930     parser = create_script(FALSE, TRUE);
931     CreateInstance_hres = E_FAIL;
932
933     SET_EXPECT(Host_QS_SecMgr);
934     SET_EXPECT(ProcessUrlAction);
935     SET_EXPECT(CreateInstance);
936     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
937     CHECK_CALLED(Host_QS_SecMgr);
938     CHECK_CALLED(ProcessUrlAction);
939     CHECK_CALLED(CreateInstance);
940
941     IActiveScriptParse_Release(parser);
942
943     parser = create_script(FALSE, TRUE);
944     QueryCustomPolicy_hres = E_FAIL;
945
946     SET_EXPECT(Host_QS_SecMgr);
947     SET_EXPECT(ProcessUrlAction);
948     SET_EXPECT(CreateInstance);
949     SET_EXPECT(QueryCustomPolicy);
950     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
951     CHECK_CALLED(Host_QS_SecMgr);
952     CHECK_CALLED(ProcessUrlAction);
953     CHECK_CALLED(CreateInstance);
954     CHECK_CALLED(QueryCustomPolicy);
955
956     IActiveScriptParse_Release(parser);
957
958     parser = create_script(FALSE, TRUE);
959     QueryCustomPolicy_psize = 6;
960
961     SET_EXPECT(Host_QS_SecMgr);
962     SET_EXPECT(ProcessUrlAction);
963     SET_EXPECT(CreateInstance);
964     SET_EXPECT(QueryCustomPolicy);
965     SET_EXPECT(QI_IObjectWithSite);
966     SET_EXPECT(reportSuccess);
967     parse_script_a(parser, "(new ActiveXObject('Wine.Test')).reportSuccess();");
968     CHECK_CALLED(Host_QS_SecMgr);
969     CHECK_CALLED(ProcessUrlAction);
970     CHECK_CALLED(CreateInstance);
971     CHECK_CALLED(QueryCustomPolicy);
972     CHECK_CALLED(QI_IObjectWithSite);
973     CHECK_CALLED(reportSuccess);
974
975     IActiveScriptParse_Release(parser);
976
977     parser = create_script(FALSE, TRUE);
978     QueryCustomPolicy_policy = URLPOLICY_DISALLOW;
979
980     SET_EXPECT(Host_QS_SecMgr);
981     SET_EXPECT(ProcessUrlAction);
982     SET_EXPECT(CreateInstance);
983     SET_EXPECT(QueryCustomPolicy);
984     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
985     CHECK_CALLED(Host_QS_SecMgr);
986     CHECK_CALLED(ProcessUrlAction);
987     CHECK_CALLED(CreateInstance);
988     CHECK_CALLED(QueryCustomPolicy);
989
990     QueryCustomPolicy_psize = 6;
991
992     SET_EXPECT(ProcessUrlAction);
993     SET_EXPECT(CreateInstance);
994     SET_EXPECT(QueryCustomPolicy);
995     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
996     CHECK_CALLED(ProcessUrlAction);
997     CHECK_CALLED(CreateInstance);
998     CHECK_CALLED(QueryCustomPolicy);
999
1000     QueryCustomPolicy_policy = URLPOLICY_ALLOW;
1001     QueryCustomPolicy_psize = 3;
1002
1003     SET_EXPECT(ProcessUrlAction);
1004     SET_EXPECT(CreateInstance);
1005     SET_EXPECT(QueryCustomPolicy);
1006     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
1007     CHECK_CALLED(ProcessUrlAction);
1008     CHECK_CALLED(CreateInstance);
1009     CHECK_CALLED(QueryCustomPolicy);
1010
1011     IActiveScriptParse_Release(parser);
1012
1013     parser = create_script(FALSE, FALSE);
1014
1015     SET_EXPECT(CreateInstance);
1016     SET_EXPECT(QI_IObjectWithSite);
1017     SET_EXPECT(reportSuccess);
1018     parse_script_a(parser, "(new ActiveXObject('Wine.Test')).reportSuccess();");
1019     CHECK_CALLED(CreateInstance);
1020     CHECK_CALLED(QI_IObjectWithSite);
1021     CHECK_CALLED(reportSuccess);
1022
1023     IActiveScriptParse_Release(parser);
1024
1025     parser = create_script(FALSE, TRUE);
1026     object_with_site = &ObjectWithSite;
1027
1028     SET_EXPECT(Host_QS_SecMgr);
1029     SET_EXPECT(ProcessUrlAction);
1030     SET_EXPECT(CreateInstance);
1031     SET_EXPECT(QueryCustomPolicy);
1032     SET_EXPECT(QI_IObjectWithSite);
1033     SET_EXPECT(SetSite);
1034     SET_EXPECT(reportSuccess);
1035     parse_script_a(parser, "(new ActiveXObject('Wine.Test')).reportSuccess();");
1036     CHECK_CALLED(Host_QS_SecMgr);
1037     CHECK_CALLED(ProcessUrlAction);
1038     CHECK_CALLED(CreateInstance);
1039     CHECK_CALLED(QueryCustomPolicy);
1040     CHECK_CALLED(QI_IObjectWithSite);
1041     CHECK_CALLED(SetSite);
1042     CHECK_CALLED(reportSuccess);
1043
1044     SetSite_hres = E_FAIL;
1045     SET_EXPECT(ProcessUrlAction);
1046     SET_EXPECT(CreateInstance);
1047     SET_EXPECT(QueryCustomPolicy);
1048     SET_EXPECT(QI_IObjectWithSite);
1049     SET_EXPECT(SetSite);
1050     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
1051     CHECK_CALLED(ProcessUrlAction);
1052     CHECK_CALLED(CreateInstance);
1053     CHECK_CALLED(QueryCustomPolicy);
1054     CHECK_CALLED(QI_IObjectWithSite);
1055     CHECK_CALLED(SetSite);
1056
1057     IActiveScriptParse_Release(parser);
1058
1059     /* No IServiceProvider Interface */
1060     parser = create_script(FALSE, FALSE);
1061     object_with_site = &ObjectWithSite;
1062     AllowIServiceProvider = FALSE;
1063
1064     SET_EXPECT(CreateInstance);
1065     SET_EXPECT(QI_IObjectWithSite);
1066     SET_EXPECT(reportSuccess);
1067     SET_EXPECT(SetSite);
1068     parse_script_a(parser, "(new ActiveXObject('Wine.Test')).reportSuccess();");
1069     CHECK_CALLED(CreateInstance);
1070     CHECK_CALLED(QI_IObjectWithSite);
1071     CHECK_CALLED(reportSuccess);
1072     CHECK_CALLED(SetSite);
1073
1074     IActiveScriptParse_Release(parser);
1075
1076     parser = create_script(FALSE, TRUE);
1077     object_with_site = &ObjectWithSite;
1078     AllowIServiceProvider = FALSE;
1079
1080     parse_script_a(parser, "testException(function() { new ActiveXObject('Wine.Test'); }, 'Error', -2146827859);");
1081
1082     IActiveScriptParse_Release(parser);
1083 }
1084
1085 static BOOL init_key(const char *key_name, const char *def_value, BOOL init)
1086 {
1087     HKEY hkey;
1088     DWORD res;
1089
1090     if(!init) {
1091         RegDeleteKey(HKEY_CLASSES_ROOT, key_name);
1092         return TRUE;
1093     }
1094
1095     res = RegCreateKeyA(HKEY_CLASSES_ROOT, key_name, &hkey);
1096     if(res != ERROR_SUCCESS)
1097         return FALSE;
1098
1099     if(def_value)
1100         res = RegSetValueA(hkey, NULL, REG_SZ, def_value, strlen(def_value));
1101
1102     RegCloseKey(hkey);
1103
1104     return res == ERROR_SUCCESS;
1105 }
1106
1107 static BOOL init_registry(BOOL init)
1108 {
1109     return init_key("Wine.Test\\CLSID", TESTOBJ_CLSID, init);
1110 }
1111
1112 static BOOL register_activex(void)
1113 {
1114     DWORD regid;
1115     HRESULT hres;
1116
1117     if(!init_registry(TRUE)) {
1118         init_registry(FALSE);
1119         return FALSE;
1120     }
1121
1122     hres = CoRegisterClassObject(&CLSID_TestObj, (IUnknown *)&activex_cf,
1123                                  CLSCTX_INPROC_SERVER, REGCLS_MULTIPLEUSE, &regid);
1124     ok(hres == S_OK, "Could not register script engine: %08x\n", hres);
1125
1126     return TRUE;
1127 }
1128
1129 static BOOL check_jscript(void)
1130 {
1131     IActiveScriptProperty *script_prop;
1132     IActiveScriptParse *parser;
1133     BSTR str;
1134     HRESULT hres;
1135
1136     parser = create_script(TRUE, TRUE);
1137     if(!parser)
1138         return FALSE;
1139
1140     str = a2bstr("if(!('localeCompare' in String.prototype)) throw 1;");
1141     hres = IActiveScriptParse_ParseScriptText(parser, str, NULL, NULL, NULL, 0, 0, 0, NULL, NULL);
1142     SysFreeString(str);
1143
1144     if(hres == S_OK)
1145         hres = IActiveScriptParse_QueryInterface(parser, &IID_IActiveScriptProperty, (void**)&script_prop);
1146     IActiveScriptParse_Release(parser);
1147     if(hres == S_OK)
1148         IActiveScriptProperty_Release(script_prop);
1149
1150     return hres == S_OK;
1151 }
1152
1153 START_TEST(activex)
1154 {
1155     CoInitialize(NULL);
1156
1157     if(check_jscript()) {
1158         register_activex();
1159
1160         test_ActiveXObject();
1161
1162         init_registry(FALSE);
1163     }else {
1164         win_skip("Broken engine, probably too old\n");
1165     }
1166
1167     CoUninitialize();
1168 }