2 * Copyright 2008 Jacek Caban for CodeWeavers
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
33 #include "wine/debug.h"
35 #include "mshtml_private.h"
37 WINE_DEFAULT_DEBUG_CHANNEL(mshtml
);
39 static const WCHAR windowW
[] = {'w','i','n','d','o','w',0};
40 static const WCHAR emptyW
[] = {0};
42 static const CLSID CLSID_JScript
=
43 {0xf414c260,0x6ac0,0x11cf,{0xb6,0xd1,0x00,0xaa,0x00,0xbb,0xbb,0x58}};
46 const IActiveScriptSiteVtbl
*lpIActiveScriptSiteVtbl
;
47 const IActiveScriptSiteInterruptPollVtbl
*lpIActiveScriptSiteInterruptPollVtbl
;
48 const IActiveScriptSiteWindowVtbl
*lpIActiveScriptSiteWindowVtbl
;
49 const IActiveScriptSiteDebug32Vtbl
*lpIActiveScriptSiteDebug32Vtbl
;
53 IActiveScript
*script
;
54 IActiveScriptParse
*parse
;
55 IActiveScriptParseProcedure
*parse_proc
;
57 SCRIPTSTATE script_state
;
65 #define ACTSCPSITE(x) ((IActiveScriptSite*) &(x)->lpIActiveScriptSiteVtbl)
66 #define ACTSCPPOLL(x) ((IActiveScriptSiteInterruptPoll*) &(x)->lpIActiveScriptSiteInterruptPollVtbl)
67 #define ACTSCPWIN(x) ((IActiveScriptSiteWindow*) &(x)->lpIActiveScriptSiteWindowVtbl)
68 #define ACTSCPDBG32(x) ((IActiveScriptSiteDebug32*) &(x)->lpIActiveScriptSiteDebug32Vtbl)
70 static BOOL
init_script_engine(ScriptHost
*script_host
)
72 IActiveScriptProperty
*property
;
73 IObjectSafety
*safety
;
75 DWORD supported_opts
=0, enabled_opts
=0;
78 hres
= IActiveScript_QueryInterface(script_host
->script
, &IID_IActiveScriptParse
, (void**)&script_host
->parse
);
80 WARN("Could not get IActiveScriptHost: %08x\n", hres
);
84 hres
= IActiveScript_QueryInterface(script_host
->script
, &IID_IObjectSafety
, (void**)&safety
);
86 FIXME("Could not get IObjectSafety: %08x\n", hres
);
90 hres
= IObjectSafety_GetInterfaceSafetyOptions(safety
, &IID_IActiveScriptParse
, &supported_opts
, &enabled_opts
);
92 FIXME("GetInterfaceSafetyOptions failed: %08x\n", hres
);
93 }else if(!(supported_opts
& INTERFACE_USES_DISPEX
)) {
94 FIXME("INTERFACE_USES_DISPEX is not supported\n");
96 hres
= IObjectSafety_SetInterfaceSafetyOptions(safety
, &IID_IActiveScriptParse
,
97 INTERFACESAFE_FOR_UNTRUSTED_DATA
|INTERFACE_USES_DISPEX
|INTERFACE_USES_SECURITY_MANAGER
,
98 INTERFACESAFE_FOR_UNTRUSTED_DATA
|INTERFACE_USES_DISPEX
|INTERFACE_USES_SECURITY_MANAGER
);
100 FIXME("SetInterfaceSafetyOptions failed: %08x\n", hres
);
103 IObjectSafety_Release(safety
);
107 hres
= IActiveScript_QueryInterface(script_host
->script
, &IID_IActiveScriptProperty
, (void**)&property
);
108 if(SUCCEEDED(hres
)) {
111 V_VT(&var
) = VT_BOOL
;
112 V_BOOL(&var
) = VARIANT_TRUE
;
113 hres
= IActiveScriptProperty_SetProperty(property
, SCRIPTPROP_HACK_TRIDENTEVENTSINK
, NULL
, &var
);
115 WARN("SetProperty failed: %08x\n", hres
);
117 IActiveScriptProperty_Release(property
);
119 WARN("Could not get IActiveScriptProperty: %08x\n", hres
);
122 hres
= IActiveScriptParse_InitNew(script_host
->parse
);
124 WARN("InitNew failed: %08x\n", hres
);
128 hres
= IActiveScript_SetScriptSite(script_host
->script
, ACTSCPSITE(script_host
));
130 WARN("SetScriptSite failed: %08x\n", hres
);
131 IActiveScript_Close(script_host
->script
);
135 hres
= IActiveScript_GetScriptState(script_host
->script
, &state
);
137 WARN("GetScriptState failed: %08x\n", hres
);
138 else if(state
!= SCRIPTSTATE_INITIALIZED
)
139 FIXME("state = %x\n", state
);
141 hres
= IActiveScript_SetScriptState(script_host
->script
, SCRIPTSTATE_STARTED
);
143 WARN("Starting script failed: %08x\n", hres
);
147 hres
= IActiveScript_AddNamedItem(script_host
->script
, windowW
,
148 SCRIPTITEM_ISVISIBLE
|SCRIPTITEM_ISSOURCE
|SCRIPTITEM_GLOBALMEMBERS
);
150 WARN("AddNamedItem failed: %08x\n", hres
);
152 hres
= IActiveScript_QueryInterface(script_host
->script
, &IID_IActiveScriptParseProcedure2
,
153 (void**)&script_host
->parse_proc
);
155 /* FIXME: QI for IActiveScriptParseProcedure */
156 WARN("Could not get IActiveScriptParseProcedure iface: %08x\n", hres
);
162 static void release_script_engine(ScriptHost
*This
)
167 switch(This
->script_state
) {
168 case SCRIPTSTATE_CONNECTED
:
169 IActiveScript_SetScriptState(This
->script
, SCRIPTSTATE_DISCONNECTED
);
171 case SCRIPTSTATE_STARTED
:
172 case SCRIPTSTATE_DISCONNECTED
:
173 case SCRIPTSTATE_INITIALIZED
:
174 IActiveScript_Close(This
->script
);
177 if(This
->parse_proc
) {
178 IActiveScriptParseProcedure_Release(This
->parse_proc
);
179 This
->parse_proc
= NULL
;
183 IActiveScriptParse_Release(This
->parse
);
188 IActiveScript_Release(This
->script
);
190 This
->script_state
= SCRIPTSTATE_UNINITIALIZED
;
193 void connect_scripts(HTMLDocument
*doc
)
197 LIST_FOR_EACH_ENTRY(iter
, &doc
->script_hosts
, ScriptHost
, entry
) {
198 if(iter
->script_state
== SCRIPTSTATE_STARTED
)
199 IActiveScript_SetScriptState(iter
->script
, SCRIPTSTATE_CONNECTED
);
203 #define ACTSCPSITE_THIS(iface) DEFINE_THIS(ScriptHost, IActiveScriptSite, iface)
205 static HRESULT WINAPI
ActiveScriptSite_QueryInterface(IActiveScriptSite
*iface
, REFIID riid
, void **ppv
)
207 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
211 if(IsEqualGUID(&IID_IUnknown
, riid
)) {
212 TRACE("(%p)->(IID_IUnknown %p)\n", This
, ppv
);
213 *ppv
= ACTSCPSITE(This
);
214 }else if(IsEqualGUID(&IID_IActiveScriptSite
, riid
)) {
215 TRACE("(%p)->(IID_IActiveScriptSite %p)\n", This
, ppv
);
216 *ppv
= ACTSCPSITE(This
);
217 }else if(IsEqualGUID(&IID_IActiveScriptSiteInterruptPoll
, riid
)) {
218 TRACE("(%p)->(IID_IActiveScriptSiteInterruprtPoll %p)\n", This
, ppv
);
219 *ppv
= ACTSCPPOLL(This
);
220 }else if(IsEqualGUID(&IID_IActiveScriptSiteWindow
, riid
)) {
221 TRACE("(%p)->(IID_IActiveScriptSiteWindow %p)\n", This
, ppv
);
222 *ppv
= ACTSCPWIN(This
);
223 }else if(IsEqualGUID(&IID_IActiveScriptSiteDebug32
, riid
)) {
224 TRACE("(%p)->(IID_IActiveScriptSiteDebug32 %p)\n", This
, ppv
);
225 *ppv
= ACTSCPDBG32(This
);
227 FIXME("(%p)->(%s %p)\n", This
, debugstr_guid(riid
), ppv
);
228 return E_NOINTERFACE
;
231 IUnknown_AddRef((IUnknown
*)*ppv
);
235 static ULONG WINAPI
ActiveScriptSite_AddRef(IActiveScriptSite
*iface
)
237 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
238 LONG ref
= InterlockedIncrement(&This
->ref
);
240 TRACE("(%p) ref=%d\n", This
, ref
);
245 static ULONG WINAPI
ActiveScriptSite_Release(IActiveScriptSite
*iface
)
247 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
248 LONG ref
= InterlockedDecrement(&This
->ref
);
250 TRACE("(%p) ref=%d\n", This
, ref
);
253 release_script_engine(This
);
255 list_remove(&This
->entry
);
262 static HRESULT WINAPI
ActiveScriptSite_GetLCID(IActiveScriptSite
*iface
, LCID
*plcid
)
264 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
266 TRACE("(%p)->(%p)\n", This
, plcid
);
268 *plcid
= GetUserDefaultLCID();
272 static HRESULT WINAPI
ActiveScriptSite_GetItemInfo(IActiveScriptSite
*iface
, LPCOLESTR pstrName
,
273 DWORD dwReturnMask
, IUnknown
**ppiunkItem
, ITypeInfo
**ppti
)
275 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
277 TRACE("(%p)->(%s %x %p %p)\n", This
, debugstr_w(pstrName
), dwReturnMask
, ppiunkItem
, ppti
);
279 if(dwReturnMask
!= SCRIPTINFO_IUNKNOWN
) {
280 FIXME("Unsupported mask %x\n", dwReturnMask
);
286 if(strcmpW(pstrName
, windowW
))
287 return DISP_E_MEMBERNOTFOUND
;
292 /* FIXME: Return proxy object */
293 *ppiunkItem
= (IUnknown
*)HTMLWINDOW2(This
->doc
->window
);
294 IUnknown_AddRef(*ppiunkItem
);
299 static HRESULT WINAPI
ActiveScriptSite_GetDocVersionString(IActiveScriptSite
*iface
, BSTR
*pbstrVersion
)
301 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
302 FIXME("(%p)->(%p)\n", This
, pbstrVersion
);
306 static HRESULT WINAPI
ActiveScriptSite_OnScriptTerminate(IActiveScriptSite
*iface
,
307 const VARIANT
*pvarResult
, const EXCEPINFO
*pexcepinfo
)
309 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
310 FIXME("(%p)->(%p %p)\n", This
, pvarResult
, pexcepinfo
);
314 static HRESULT WINAPI
ActiveScriptSite_OnStateChange(IActiveScriptSite
*iface
, SCRIPTSTATE ssScriptState
)
316 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
318 TRACE("(%p)->(%x)\n", This
, ssScriptState
);
320 This
->script_state
= ssScriptState
;
324 static HRESULT WINAPI
ActiveScriptSite_OnScriptError(IActiveScriptSite
*iface
, IActiveScriptError
*pscripterror
)
326 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
327 FIXME("(%p)->(%p)\n", This
, pscripterror
);
331 static HRESULT WINAPI
ActiveScriptSite_OnEnterScript(IActiveScriptSite
*iface
)
333 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
335 TRACE("(%p)->()\n", This
);
340 static HRESULT WINAPI
ActiveScriptSite_OnLeaveScript(IActiveScriptSite
*iface
)
342 ScriptHost
*This
= ACTSCPSITE_THIS(iface
);
344 TRACE("(%p)->()\n", This
);
349 #undef ACTSCPSITE_THIS
351 static const IActiveScriptSiteVtbl ActiveScriptSiteVtbl
= {
352 ActiveScriptSite_QueryInterface
,
353 ActiveScriptSite_AddRef
,
354 ActiveScriptSite_Release
,
355 ActiveScriptSite_GetLCID
,
356 ActiveScriptSite_GetItemInfo
,
357 ActiveScriptSite_GetDocVersionString
,
358 ActiveScriptSite_OnScriptTerminate
,
359 ActiveScriptSite_OnStateChange
,
360 ActiveScriptSite_OnScriptError
,
361 ActiveScriptSite_OnEnterScript
,
362 ActiveScriptSite_OnLeaveScript
365 #define ACTSCPPOLL_THIS(iface) DEFINE_THIS(ScriptHost, IActiveScriptSiteInterruptPoll, iface)
367 static HRESULT WINAPI
ActiveScriptSiteInterruptPoll_QueryInterface(IActiveScriptSiteInterruptPoll
*iface
,
368 REFIID riid
, void **ppv
)
370 ScriptHost
*This
= ACTSCPPOLL_THIS(iface
);
371 return IActiveScriptSite_QueryInterface(ACTSCPSITE(This
), riid
, ppv
);
374 static ULONG WINAPI
ActiveScriptSiteInterruptPoll_AddRef(IActiveScriptSiteInterruptPoll
*iface
)
376 ScriptHost
*This
= ACTSCPPOLL_THIS(iface
);
377 return IActiveScriptSite_AddRef(ACTSCPSITE(This
));
380 static ULONG WINAPI
ActiveScriptSiteInterruptPoll_Release(IActiveScriptSiteInterruptPoll
*iface
)
382 ScriptHost
*This
= ACTSCPPOLL_THIS(iface
);
383 return IActiveScriptSite_Release(ACTSCPSITE(This
));
386 static HRESULT WINAPI
ActiveScriptSiteInterruptPoll_QueryContinue(IActiveScriptSiteInterruptPoll
*iface
)
388 ScriptHost
*This
= ACTSCPPOLL_THIS(iface
);
390 TRACE("(%p)\n", This
);
395 #undef ACTSCPPOLL_THIS
397 static const IActiveScriptSiteInterruptPollVtbl ActiveScriptSiteInterruptPollVtbl
= {
398 ActiveScriptSiteInterruptPoll_QueryInterface
,
399 ActiveScriptSiteInterruptPoll_AddRef
,
400 ActiveScriptSiteInterruptPoll_Release
,
401 ActiveScriptSiteInterruptPoll_QueryContinue
404 #define ACTSCPWIN_THIS(iface) DEFINE_THIS(ScriptHost, IActiveScriptSiteWindow, iface)
406 static HRESULT WINAPI
ActiveScriptSiteWindow_QueryInterface(IActiveScriptSiteWindow
*iface
,
407 REFIID riid
, void **ppv
)
409 ScriptHost
*This
= ACTSCPWIN_THIS(iface
);
410 return IActiveScriptSite_QueryInterface(ACTSCPSITE(This
), riid
, ppv
);
413 static ULONG WINAPI
ActiveScriptSiteWindow_AddRef(IActiveScriptSiteWindow
*iface
)
415 ScriptHost
*This
= ACTSCPWIN_THIS(iface
);
416 return IActiveScriptSite_AddRef(ACTSCPSITE(This
));
419 static ULONG WINAPI
ActiveScriptSiteWindow_Release(IActiveScriptSiteWindow
*iface
)
421 ScriptHost
*This
= ACTSCPWIN_THIS(iface
);
422 return IActiveScriptSite_Release(ACTSCPSITE(This
));
425 static HRESULT WINAPI
ActiveScriptSiteWindow_GetWindow(IActiveScriptSiteWindow
*iface
, HWND
*phwnd
)
427 ScriptHost
*This
= ACTSCPWIN_THIS(iface
);
428 FIXME("(%p)->(%p)\n", This
, phwnd
);
432 static HRESULT WINAPI
ActiveScriptSiteWindow_EnableModeless(IActiveScriptSiteWindow
*iface
, BOOL fEnable
)
434 ScriptHost
*This
= ACTSCPWIN_THIS(iface
);
435 FIXME("(%p)->(%x)\n", This
, fEnable
);
439 #undef ACTSCPWIN_THIS
441 static const IActiveScriptSiteWindowVtbl ActiveScriptSiteWindowVtbl
= {
442 ActiveScriptSiteWindow_QueryInterface
,
443 ActiveScriptSiteWindow_AddRef
,
444 ActiveScriptSiteWindow_Release
,
445 ActiveScriptSiteWindow_GetWindow
,
446 ActiveScriptSiteWindow_EnableModeless
449 #define ACTSCPDBG32_THIS(iface) DEFINE_THIS(ScriptHost, IActiveScriptSiteDebug32, iface)
451 static HRESULT WINAPI
ActiveScriptSiteDebug32_QueryInterface(IActiveScriptSiteDebug32
*iface
,
452 REFIID riid
, void **ppv
)
454 ScriptHost
*This
= ACTSCPDBG32_THIS(iface
);
455 return IActiveScriptSite_QueryInterface(ACTSCPSITE(This
), riid
, ppv
);
458 static ULONG WINAPI
ActiveScriptSiteDebug32_AddRef(IActiveScriptSiteDebug32
*iface
)
460 ScriptHost
*This
= ACTSCPDBG32_THIS(iface
);
461 return IActiveScriptSite_AddRef(ACTSCPSITE(This
));
464 static ULONG WINAPI
ActiveScriptSiteDebug32_Release(IActiveScriptSiteDebug32
*iface
)
466 ScriptHost
*This
= ACTSCPDBG32_THIS(iface
);
467 return IActiveScriptSite_Release(ACTSCPSITE(This
));
470 static HRESULT WINAPI
ActiveScriptSiteDebug32_GetDocumentContextFromPosition(IActiveScriptSiteDebug32
*iface
,
471 DWORD dwSourceContext
, ULONG uCharacterOffset
, ULONG uNumChars
, IDebugDocumentContext
**ppsc
)
473 ScriptHost
*This
= ACTSCPDBG32_THIS(iface
);
474 FIXME("(%p)->(%x %u %u %p)\n", This
, dwSourceContext
, uCharacterOffset
, uNumChars
, ppsc
);
478 static HRESULT WINAPI
ActiveScriptSiteDebug32_GetApplication(IActiveScriptSiteDebug32
*iface
, IDebugApplication32
**ppda
)
480 ScriptHost
*This
= ACTSCPDBG32_THIS(iface
);
481 FIXME("(%p)->(%p)\n", This
, ppda
);
485 static HRESULT WINAPI
ActiveScriptSiteDebug32_GetRootApplicationNode(IActiveScriptSiteDebug32
*iface
,
486 IDebugApplicationNode
**ppdanRoot
)
488 ScriptHost
*This
= ACTSCPDBG32_THIS(iface
);
489 FIXME("(%p)->(%p)\n", This
, ppdanRoot
);
493 static HRESULT WINAPI
ActiveScriptSiteDebug32_OnScriptErrorDebug(IActiveScriptSiteDebug32
*iface
,
494 IActiveScriptErrorDebug
*pErrorDebug
, BOOL
*pfEnterDebugger
, BOOL
*pfCallOnScriptErrorWhenContinuing
)
496 ScriptHost
*This
= ACTSCPDBG32_THIS(iface
);
497 FIXME("(%p)->(%p %p %p)\n", This
, pErrorDebug
, pfEnterDebugger
, pfCallOnScriptErrorWhenContinuing
);
501 #undef ACTSCPDBG32_THIS
503 static const IActiveScriptSiteDebug32Vtbl ActiveScriptSiteDebug32Vtbl
= {
504 ActiveScriptSiteDebug32_QueryInterface
,
505 ActiveScriptSiteDebug32_AddRef
,
506 ActiveScriptSiteDebug32_Release
,
507 ActiveScriptSiteDebug32_GetDocumentContextFromPosition
,
508 ActiveScriptSiteDebug32_GetApplication
,
509 ActiveScriptSiteDebug32_GetRootApplicationNode
,
510 ActiveScriptSiteDebug32_OnScriptErrorDebug
513 static ScriptHost
*create_script_host(HTMLDocument
*doc
, const GUID
*guid
)
518 ret
= heap_alloc_zero(sizeof(*ret
));
519 ret
->lpIActiveScriptSiteVtbl
= &ActiveScriptSiteVtbl
;
520 ret
->lpIActiveScriptSiteInterruptPollVtbl
= &ActiveScriptSiteInterruptPollVtbl
;
521 ret
->lpIActiveScriptSiteWindowVtbl
= &ActiveScriptSiteWindowVtbl
;
522 ret
->lpIActiveScriptSiteDebug32Vtbl
= &ActiveScriptSiteDebug32Vtbl
;
525 ret
->script_state
= SCRIPTSTATE_UNINITIALIZED
;
528 list_add_tail(&doc
->script_hosts
, &ret
->entry
);
530 hres
= CoCreateInstance(&ret
->guid
, NULL
, CLSCTX_INPROC_SERVER
|CLSCTX_INPROC_HANDLER
,
531 &IID_IActiveScript
, (void**)&ret
->script
);
533 WARN("Could not load script engine: %08x\n", hres
);
534 else if(!init_script_engine(ret
))
535 release_script_engine(ret
);
540 static void parse_text(ScriptHost
*script_host
, LPCWSTR text
)
546 static const WCHAR script_endW
[] = {'<','/','S','C','R','I','P','T','>',0};
548 TRACE("%s\n", debugstr_w(text
));
551 memset(&excepinfo
, 0, sizeof(excepinfo
));
552 hres
= IActiveScriptParse_ParseScriptText(script_host
->parse
, text
, windowW
, NULL
, script_endW
,
553 0, 0, SCRIPTTEXT_ISVISIBLE
|SCRIPTTEXT_HOSTMANAGESSOURCE
,
556 WARN("ParseScriptText failed: %08x\n", hres
);
560 static void parse_extern_script(ScriptHost
*script_host
, LPCWSTR src
)
568 static const WCHAR wine_schemaW
[] = {'w','i','n','e',':'};
570 if(strlenW(src
) > sizeof(wine_schemaW
)/sizeof(WCHAR
) && !memcmp(src
, wine_schemaW
, sizeof(wine_schemaW
)))
571 src
+= sizeof(wine_schemaW
)/sizeof(WCHAR
);
573 hres
= CreateURLMoniker(NULL
, src
, &mon
);
577 hres
= bind_mon_to_buffer(script_host
->doc
, mon
, (void**)&buf
, &size
);
578 IMoniker_Release(mon
);
582 len
= MultiByteToWideChar(CP_ACP
, 0, buf
, size
, NULL
, 0);
583 text
= heap_alloc((len
+1)*sizeof(WCHAR
));
584 MultiByteToWideChar(CP_ACP
, 0, buf
, size
, text
, len
);
588 parse_text(script_host
, text
);
593 static void parse_inline_script(ScriptHost
*script_host
, nsIDOMHTMLScriptElement
*nsscript
)
595 const PRUnichar
*text
;
599 nsAString_Init(&text_str
, NULL
);
601 nsres
= nsIDOMHTMLScriptElement_GetText(nsscript
, &text_str
);
603 if(NS_SUCCEEDED(nsres
)) {
604 nsAString_GetData(&text_str
, &text
);
605 parse_text(script_host
, text
);
607 ERR("GetText failed: %08x\n", nsres
);
610 nsAString_Finish(&text_str
);
613 static void parse_script_elem(ScriptHost
*script_host
, nsIDOMHTMLScriptElement
*nsscript
)
615 const PRUnichar
*src
;
619 nsAString_Init(&src_str
, NULL
);
621 nsres
= nsIDOMHTMLScriptElement_GetSrc(nsscript
, &src_str
);
622 nsAString_GetData(&src_str
, &src
);
625 ERR("GetSrc failed: %08x\n", nsres
);
627 parse_extern_script(script_host
, src
);
629 parse_inline_script(script_host
, nsscript
);
631 nsAString_Finish(&src_str
);
634 static BOOL
get_guid_from_type(LPCWSTR type
, GUID
*guid
)
636 const WCHAR text_javascriptW
[] =
637 {'t','e','x','t','/','j','a','v','a','s','c','r','i','p','t',0};
639 /* FIXME: Handle more types */
640 if(!strcmpW(type
, text_javascriptW
)) {
641 *guid
= CLSID_JScript
;
643 FIXME("Unknown type %s\n", debugstr_w(type
));
650 static BOOL
get_guid_from_language(LPCWSTR type
, GUID
*guid
)
654 hres
= CLSIDFromProgID(type
, guid
);
658 /* FIXME: Check CATID_ActiveScriptParse */
663 static BOOL
get_script_guid(nsIDOMHTMLScriptElement
*nsscript
, GUID
*guid
)
665 nsAString attr_str
, val_str
;
669 static const PRUnichar languageW
[] = {'l','a','n','g','u','a','g','e',0};
671 nsAString_Init(&val_str
, NULL
);
673 nsres
= nsIDOMHTMLScriptElement_GetType(nsscript
, &val_str
);
674 if(NS_SUCCEEDED(nsres
)) {
675 const PRUnichar
*type
;
677 nsAString_GetData(&val_str
, &type
);
679 ret
= get_guid_from_type(type
, guid
);
680 nsAString_Finish(&val_str
);
684 ERR("GetType failed: %08x\n", nsres
);
687 nsAString_Init(&attr_str
, languageW
);
689 nsres
= nsIDOMHTMLScriptElement_GetAttribute(nsscript
, &attr_str
, &val_str
);
690 if(NS_SUCCEEDED(nsres
)) {
691 const PRUnichar
*language
;
693 nsAString_GetData(&val_str
, &language
);
696 ret
= get_guid_from_language(language
, guid
);
698 *guid
= CLSID_JScript
;
702 ERR("GetAttribute(language) failed: %08x\n", nsres
);
705 nsAString_Finish(&attr_str
);
706 nsAString_Finish(&val_str
);
711 static ScriptHost
*get_script_host(HTMLDocument
*doc
, const GUID
*guid
)
715 if(IsEqualGUID(&CLSID_JScript
, &guid
) && doc
->scriptmode
!= SCRIPTMODE_ACTIVESCRIPT
) {
716 TRACE("Ignoring JScript\n");
720 LIST_FOR_EACH_ENTRY(iter
, &doc
->script_hosts
, ScriptHost
, entry
) {
721 if(IsEqualGUID(guid
, &iter
->guid
))
725 return create_script_host(doc
, guid
);
728 void doc_insert_script(HTMLDocument
*doc
, nsIDOMHTMLScriptElement
*nsscript
)
730 ScriptHost
*script_host
;
733 if(!get_script_guid(nsscript
, &guid
)) {
734 WARN("Could not find script GUID\n");
738 script_host
= get_script_host(doc
, &guid
);
742 if(script_host
->parse
)
743 parse_script_elem(script_host
, nsscript
);
746 IDispatch
*script_parse_event(HTMLDocument
*doc
, LPCWSTR text
)
748 ScriptHost
*script_host
;
749 GUID guid
= CLSID_JScript
;
754 static const WCHAR delimiterW
[] = {'\"',0};
756 for(ptr
= text
; isalnumW(*ptr
); ptr
++);
761 language
= heap_alloc((ptr
-text
+1)*sizeof(WCHAR
));
762 memcpy(language
, text
, (ptr
-text
)*sizeof(WCHAR
));
763 language
[ptr
-text
] = 0;
765 b
= get_guid_from_language(language
, &guid
);
770 WARN("Could not find language\n");
779 script_host
= get_script_host(doc
, &guid
);
780 if(!script_host
|| !script_host
->parse_proc
)
783 hres
= IActiveScriptParseProcedure_ParseProcedureText(script_host
->parse_proc
, ptr
, NULL
, emptyW
,
784 NULL
, NULL
, delimiterW
, 0 /* FIXME */, 0,
785 SCRIPTPROC_HOSTMANAGESSOURCE
|SCRIPTPROC_IMPLICIT_THIS
|SCRIPTPROC_IMPLICIT_PARENTS
, &disp
);
787 WARN("ParseProcedureText failed: %08x\n", hres
);
791 TRACE("ret %p\n", disp
);
795 static BOOL
is_jscript_available(void)
797 static BOOL available
, checked
;
801 HRESULT hres
= CoGetClassObject(&CLSID_JScript
, CLSCTX_INPROC_SERVER
, NULL
, &IID_IUnknown
, (void**)&unk
);
803 if(SUCCEEDED(hres
)) {
805 IUnknown_Release(unk
);
815 void set_script_mode(HTMLDocument
*doc
, SCRIPTMODE mode
)
817 nsIWebBrowserSetup
*setup
;
820 if(mode
== SCRIPTMODE_ACTIVESCRIPT
&& !is_jscript_available()) {
821 TRACE("jscript.dll not available\n");
822 doc
->scriptmode
= SCRIPTMODE_GECKO
;
826 doc
->scriptmode
= mode
;
828 if(!doc
->nscontainer
|| !doc
->nscontainer
->webbrowser
)
831 nsres
= nsIWebBrowser_QueryInterface(doc
->nscontainer
->webbrowser
,
832 &IID_nsIWebBrowserSetup
, (void**)&setup
);
833 if(NS_SUCCEEDED(nsres
)) {
834 nsres
= nsIWebBrowserSetup_SetProperty(setup
, SETUP_ALLOW_JAVASCRIPT
,
835 doc
->scriptmode
== SCRIPTMODE_GECKO
);
836 nsIWebBrowserSetup_Release(setup
);
840 ERR("JavaScript setup failed: %08x\n", nsres
);
843 void release_script_hosts(HTMLDocument
*doc
)
847 while(!list_empty(&doc
->script_hosts
)) {
848 iter
= LIST_ENTRY(list_head(&doc
->script_hosts
), ScriptHost
, entry
);
850 release_script_engine(iter
);
851 list_remove(&iter
->entry
);
853 IActiveScript_Release(ACTSCPSITE(iter
));