The storage event url prop fix is tested after the location.hash tests are added, implicitly. I didn't find a need to add extra tests for no reason there.
The super_navigate changes for fragments is also necessary for the location.hash tests (and its behavior, apparently)…
-- v4: mshtml: Implement document.importNode. mshtml: Implement HTMLLocation_put_hash. mshtml: Always use super_navigate when navigating fragments. mshtml: Don't include fragment in storage event's url prop. mshtml: Return E_ABORT if wine-gecko's OnDataAvailable aborts the binding. mshtml: Improve locale stub for KeyboardEvent. mshtml: Implement isContentEditable for HTML elements. mshtml/tests: Handle broken localStorage on native.
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/tests/events.c | 20 +++++++++++++++++--- dlls/mshtml/tests/misc.c | 16 +++++++++++++--- 2 files changed, 30 insertions(+), 6 deletions(-)
diff --git a/dlls/mshtml/tests/events.c b/dlls/mshtml/tests/events.c index b53851d61bf..8175205b830 100644 --- a/dlls/mshtml/tests/events.c +++ b/dlls/mshtml/tests/events.c @@ -4024,12 +4024,19 @@ static void test_storage_events(const char *doc_str) ok(hres == S_OK, "Could not get IHTMLWindow6: %08lx\n", hres); IHTMLWindow2_Release(window);
- hres = IHTMLWindow6_get_sessionStorage(window6, &session_storage[i]); - ok(hres == S_OK, "get_sessionStorage[%u] failed: %08lx\n", i, hres); - ok(session_storage[i] != NULL, "session_storage[%u] == NULL\n", i); hres = IHTMLWindow6_get_localStorage(window6, &local_storage[i]); + + /* w10pro64 testbot VM sometimes returns this for some reason */ + if(hres == WININET_E_INTERNAL_ERROR) { + win_skip("localStorage is buggy and not available, skipping storage events tests\n"); + goto done; + } + ok(hres == S_OK, "get_localStorage[%u] failed: %08lx\n", i, hres); ok(local_storage[i] != NULL, "local_storage[%u] == NULL\n", i); + hres = IHTMLWindow6_get_sessionStorage(window6, &session_storage[i]); + ok(hres == S_OK, "get_sessionStorage[%u] failed: %08lx\n", i, hres); + ok(session_storage[i] != NULL, "session_storage[%u] == NULL\n", i);
hres = IHTMLDocument2_QueryInterface(doc[i], &IID_IHTMLDocument6, (void**)&doc6); if(SUCCEEDED(hres)) { @@ -4125,6 +4132,9 @@ static void test_storage_events(const char *doc_str) pump_msgs(&called_doc1_onstoragecommit); CHECK_CALLED(doc1_onstoragecommit);
+ for(i = 0; i < ARRAY_SIZE(local_storage); i++) + IHTMLStorage_Release(local_storage[i]); + /* session storage */ key = SysAllocString(L"foobar"); hres = IHTMLStorage_removeItem(session_storage[0], key); @@ -4184,6 +4194,10 @@ static void test_storage_events(const char *doc_str) CHECK_CALLED(doc1_onstorage); if(document_mode >= 9) CHECK_CALLED(window1_onstorage);
+ for(i = 0; i < ARRAY_SIZE(session_storage); i++) + IHTMLStorage_Release(session_storage[i]); + +done: set_client_site(doc[0], FALSE); set_client_site(doc[1], FALSE); IHTMLDocument2_Release(doc[0]); diff --git a/dlls/mshtml/tests/misc.c b/dlls/mshtml/tests/misc.c index 5f38f9d45fb..e4703a3b646 100644 --- a/dlls/mshtml/tests/misc.c +++ b/dlls/mshtml/tests/misc.c @@ -161,8 +161,14 @@ static HRESULT get_localstorage(IHTMLDocument2 *doc, IHTMLStorage **storage) }
hres = IHTMLWindow6_get_localStorage(window6, storage); - ok(hres == S_OK, "get_localStorage failed: %08lx\n", hres); - ok(*storage != NULL, "*storage == NULL\n"); + + /* w10pro64 testbot VM sometimes returns this for some reason */ + if(hres == WININET_E_INTERNAL_ERROR) + win_skip("localStorage is buggy and not available, skipping tests\n"); + else { + ok(hres == S_OK, "get_localStorage failed: %08lx\n", hres); + ok(*storage != NULL, "*storage == NULL\n"); + }
IHTMLWindow6_Release(window6); return hres; @@ -206,7 +212,11 @@ static void test_HTMLStorage(void) doc2 = create_doc_from_url(L"http://www.codeweavers.com/");
hres = get_localstorage(doc, &storage); - ok(hres == S_OK, "got %08lx\n", hres); + if(hres != S_OK) { + IHTMLDocument2_Release(doc2); + IHTMLDocument2_Release(doc); + return; + }
hres = get_localstorage(doc2, &storage2); ok(hres == S_OK, "got %08lx\n", hres);
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlelem.c | 15 +++++++++++++-- dlls/mshtml/tests/dom.c | 16 ++++++++++++++++ 2 files changed, 29 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlelem.c b/dlls/mshtml/htmlelem.c index 8a45a354a04..4d92929b985 100644 --- a/dlls/mshtml/htmlelem.c +++ b/dlls/mshtml/htmlelem.c @@ -4256,8 +4256,19 @@ static HRESULT WINAPI HTMLElement3_get_contentEditable(IHTMLElement3 *iface, BST static HRESULT WINAPI HTMLElement3_get_isContentEditable(IHTMLElement3 *iface, VARIANT_BOOL *p) { HTMLElement *This = impl_from_IHTMLElement3(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + nsresult nsres; + cpp_bool r; + + TRACE("(%p)->(%p)\n", This, p); + + if(!This->html_element) { + FIXME("non-HTML element\n"); + return E_NOTIMPL; + } + + nsres = nsIDOMHTMLElement_GetIsContentEditable(This->html_element, &r); + *p = variant_bool(NS_SUCCEEDED(nsres) && r); + return S_OK; }
static HRESULT WINAPI HTMLElement3_put_hideFocus(IHTMLElement3 *iface, VARIANT_BOOL v) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index 6f4e8ed007b..70b047ccbe1 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -3945,6 +3945,7 @@ static void test_contenteditable(IUnknown *unk) IHTMLElement3 *elem3 = get_elem3_iface(unk); HRESULT hres; BSTR str, strDefault; + VARIANT_BOOL vbool;
hres = IHTMLElement3_get_contentEditable(elem3, &strDefault); ok(hres == S_OK, "get_contentEditable failed: 0x%08lx\n", hres); @@ -3957,6 +3958,21 @@ static void test_contenteditable(IUnknown *unk) ok(hres == S_OK, "get_contentEditable failed: 0x%08lx\n", hres); ok(!lstrcmpW(str, L"true"), "Got %s, expected %s\n", wine_dbgstr_w(str), "true"); SysFreeString(str); + hres = IHTMLElement3_get_isContentEditable(elem3, &vbool); + ok(hres == S_OK, "get_isContentEditable failed: 0x%08lx\n", hres); + ok(vbool == VARIANT_TRUE, "Got %d, expected VARIANT_TRUE\n", vbool); + + str = SysAllocString(L"inherit"); + hres = IHTMLElement3_put_contentEditable(elem3, str); + ok(hres == S_OK, "put_contentEditable(%s) failed: 0x%08lx\n", wine_dbgstr_w(str), hres); + SysFreeString(str); + hres = IHTMLElement3_get_contentEditable(elem3, &str); + ok(hres == S_OK, "get_contentEditable failed: 0x%08lx\n", hres); + ok(!lstrcmpW(str, L"inherit"), "Got %s, expected %s\n", wine_dbgstr_w(str), "inherit"); + SysFreeString(str); + hres = IHTMLElement3_get_isContentEditable(elem3, &vbool); + ok(hres == S_OK, "get_isContentEditable failed: 0x%08lx\n", hres); + ok(vbool == VARIANT_FALSE, "Got %d, expected VARIANT_FALSE\n", vbool);
/* Restore origin contentEditable */ hres = IHTMLElement3_put_contentEditable(elem3, strDefault);
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlevent.c | 7 +++++-- dlls/mshtml/tests/events.js | 1 + 2 files changed, 6 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlevent.c b/dlls/mshtml/htmlevent.c index 59a8d50d40e..835e11c74aa 100644 --- a/dlls/mshtml/htmlevent.c +++ b/dlls/mshtml/htmlevent.c @@ -2154,8 +2154,11 @@ static HRESULT WINAPI DOMKeyboardEvent_get_char(IDOMKeyboardEvent *iface, VARIAN static HRESULT WINAPI DOMKeyboardEvent_get_locale(IDOMKeyboardEvent *iface, BSTR *p) { DOMKeyboardEvent *This = impl_from_IDOMKeyboardEvent(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + FIXME("(%p)->(%p) semi-stub\n", This, p); + + *p = SysAllocString(L""); + return *p ? S_OK : E_OUTOFMEMORY; }
static const IDOMKeyboardEventVtbl DOMKeyboardEventVtbl = { diff --git a/dlls/mshtml/tests/events.js b/dlls/mshtml/tests/events.js index 156330e984b..3b29798e9a1 100644 --- a/dlls/mshtml/tests/events.js +++ b/dlls/mshtml/tests/events.js @@ -760,6 +760,7 @@ sync_test("keyboard_event", function() { ok(e.location === 0, "location = " + e.location); ok(e.detail === 0, "detail = " + e.detail); ok(e.which === 0, "which = " + e.which); + ok(e.locale === "", "locale = " + e.locale); });
sync_test("custom_event", function() {
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/navigate.c | 6 ++++-- dlls/mshtml/nsembed.c | 2 ++ 2 files changed, 6 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/navigate.c b/dlls/mshtml/navigate.c index 3594cfe0a6c..66542fbd676 100644 --- a/dlls/mshtml/navigate.c +++ b/dlls/mshtml/navigate.c @@ -1184,8 +1184,10 @@ static HRESULT read_stream_data(nsChannelBSC *This, IStream *stream) (nsIRequest*)&This->nschannel->nsIHttpChannel_iface, This->nscontext, &This->nsstream->nsIInputStream_iface, This->bsc.read-This->nsstream->buf_size, This->nsstream->buf_size); - if(NS_FAILED(nsres)) - ERR("OnDataAvailable failed: %08lx\n", nsres); + if(NS_FAILED(nsres)) { + WARN("OnDataAvailable failed: %08lx\n", nsres); + return map_nsresult(nsres); + }
if(This->nsstream->buf_size == sizeof(This->nsstream->buf)) { ERR("buffer is full\n"); diff --git a/dlls/mshtml/nsembed.c b/dlls/mshtml/nsembed.c index 67d40ca0085..0b16cd90306 100644 --- a/dlls/mshtml/nsembed.c +++ b/dlls/mshtml/nsembed.c @@ -911,6 +911,8 @@ HRESULT map_nsresult(nsresult nsres) return E_UNEXPECTED; case NS_ERROR_DOM_NO_MODIFICATION_ALLOWED_ERR: return 0x80700007; /* according to tests */ + case NS_BINDING_ABORTED: + return E_ABORT; } return E_FAIL; }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlstorage.c | 14 ++++++++++---- dlls/mshtml/tests/documentmode.js | 2 +- 2 files changed, 11 insertions(+), 5 deletions(-)
diff --git a/dlls/mshtml/htmlstorage.c b/dlls/mshtml/htmlstorage.c index bf93e28fdf6..d8ecf573b2b 100644 --- a/dlls/mshtml/htmlstorage.c +++ b/dlls/mshtml/htmlstorage.c @@ -235,7 +235,7 @@ struct send_storage_event_ctx { BSTR key; BSTR old_value; BSTR new_value; - const WCHAR *url; + BSTR url; };
static HRESULT push_storage_event_task(struct send_storage_event_ctx *ctx, HTMLInnerWindow *window, BOOL commit) @@ -324,11 +324,16 @@ static HRESULT send_storage_event(HTMLStorage *storage, BSTR key, BSTR old_value BSTR hostname = NULL; HRESULT hres = S_OK;
+ ctx.url = NULL; if(!window) goto done; - get_top_window(window->base.outer_window, &top_window); + if(window->base.outer_window->uri_nofrag) { + hres = IUri_GetDisplayUri(window->base.outer_window->uri_nofrag, &ctx.url); + if(hres != S_OK) + goto done; + }
- ctx.url = window->base.outer_window->url; + get_top_window(window->base.outer_window, &top_window); ctx.key = key; ctx.old_value = old_value; ctx.new_value = new_value; @@ -351,9 +356,10 @@ static HRESULT send_storage_event(HTMLStorage *storage, BSTR key, BSTR old_value hres = push_storage_event_task(&ctx, window, TRUE);
done: + SysFreeString(ctx.url); SysFreeString(hostname); SysFreeString(old_value); - return hres; + return FAILED(hres) ? hres : S_OK; }
static HRESULT WINAPI HTMLStorage_QueryInterface(IHTMLStorage *iface, REFIID riid, void **ppv) diff --git a/dlls/mshtml/tests/documentmode.js b/dlls/mshtml/tests/documentmode.js index a0f170c73b4..92f30f8b7e9 100644 --- a/dlls/mshtml/tests/documentmode.js +++ b/dlls/mshtml/tests/documentmode.js @@ -1468,7 +1468,7 @@ async_test("storage events", function() { ok(e.key === key, "key = " + e.key + ", expected " + key); ok(e.oldValue === oldValue, "oldValue = " + e.oldValue + ", expected " + oldValue); ok(e.newValue === newValue, "newValue = " + e.newValue + ", expected " + newValue); - s = (idx ? iframe.contentWindow : window)["location"]["href"]; + s = (idx ? iframe.contentWindow : window)["location"]["href"].split('#', 1)[0]; ok(e.url === s, "url = " + e.url + ", expected " + s); }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/binding.h | 1 + dlls/mshtml/navigate.c | 34 +++++++++++++++++++++------------- 2 files changed, 22 insertions(+), 13 deletions(-)
diff --git a/dlls/mshtml/binding.h b/dlls/mshtml/binding.h index 479cb71cf15..2b3693a8c89 100644 --- a/dlls/mshtml/binding.h +++ b/dlls/mshtml/binding.h @@ -136,6 +136,7 @@ typedef struct { #define BINDING_REFRESH 0x0008 #define BINDING_SUBMIT 0x0010 #define BINDING_NOFRAG 0x0020 +#define BINDING_FRAGNAV 0x0040
HRESULT set_http_header(struct list*,const WCHAR*,int,const WCHAR*,int) DECLSPEC_HIDDEN; HRESULT create_redirect_nschannel(const WCHAR*,nsChannel*,nsChannel**) DECLSPEC_HIDDEN; diff --git a/dlls/mshtml/navigate.c b/dlls/mshtml/navigate.c index 66542fbd676..b0459cbeda8 100644 --- a/dlls/mshtml/navigate.c +++ b/dlls/mshtml/navigate.c @@ -2213,15 +2213,10 @@ HRESULT super_navigate(HTMLOuterWindow *window, IUri *uri, DWORD flags, const WC } }
- if(!(flags & BINDING_NOFRAG) && window->uri_nofrag && !post_data_size) { - BOOL eq; - - hres = IUri_IsEqual(uri_nofrag, window->uri_nofrag, &eq); - if(SUCCEEDED(hres) && eq) { - IUri_Release(uri_nofrag); - TRACE("fragment navigate\n"); - return navigate_fragment(window, uri); - } + if(flags & BINDING_FRAGNAV) { + IUri_Release(uri_nofrag); + TRACE("fragment navigate\n"); + return navigate_fragment(window, uri); }
hres = CreateURLMonikerEx2(NULL, uri_nofrag, &mon, URL_MK_UNIFORM); @@ -2449,6 +2444,9 @@ HRESULT hlink_frame_navigate(HTMLDocumentObj *doc, LPCWSTR url, nsChannel *nscha static HRESULT navigate_uri(HTMLOuterWindow *window, IUri *uri, const WCHAR *display_uri, const request_data_t *request_data, DWORD flags) { + DWORD post_data_len = request_data ? request_data->post_data_len : 0; + void *post_data = post_data_len ? request_data->post_data : NULL; + const WCHAR *headers = request_data ? request_data->headers : NULL; nsWineURI *nsuri; HRESULT hres;
@@ -2457,11 +2455,18 @@ static HRESULT navigate_uri(HTMLOuterWindow *window, IUri *uri, const WCHAR *dis if(!window->browser) return E_UNEXPECTED;
- if(window->browser->doc->webbrowser) { - DWORD post_data_len = request_data ? request_data->post_data_len : 0; - void *post_data = post_data_len ? request_data->post_data : NULL; - const WCHAR *headers = request_data ? request_data->headers : NULL; + if(!(flags & BINDING_NOFRAG) && window->uri_nofrag && !post_data_len) { + IUri *uri_nofrag = get_uri_nofrag(uri); + if(uri_nofrag) { + BOOL frag_nav = FALSE; + IUri_IsEqual(uri_nofrag, window->uri_nofrag, &frag_nav); + IUri_Release(uri_nofrag); + if(frag_nav) + flags |= BINDING_FRAGNAV; + } + }
+ if(window->browser->doc->webbrowser) { if(!(flags & BINDING_REFRESH)) { BSTR frame_name = NULL; BOOL cancel = FALSE; @@ -2488,6 +2493,9 @@ static HRESULT navigate_uri(HTMLOuterWindow *window, IUri *uri, const WCHAR *dis if(is_main_content_window(window)) { BOOL cancel;
+ if(flags & BINDING_FRAGNAV) + return super_navigate(window, uri, flags, headers, post_data, post_data_len); + hres = hlink_frame_navigate(window->base.inner_window->doc->doc_obj, display_uri, NULL, 0, &cancel); if(FAILED(hres)) return hres;
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmllocation.c | 25 +++++++++++++++++++++++-- dlls/mshtml/tests/documentmode.js | 12 ++++++++++++ 2 files changed, 35 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmllocation.c b/dlls/mshtml/htmllocation.c index 8f7800ff2a3..26365a7a5d0 100644 --- a/dlls/mshtml/htmllocation.c +++ b/dlls/mshtml/htmllocation.c @@ -524,8 +524,29 @@ static HRESULT WINAPI HTMLLocation_get_search(IHTMLLocation *iface, BSTR *p) static HRESULT WINAPI HTMLLocation_put_hash(IHTMLLocation *iface, BSTR v) { HTMLLocation *This = impl_from_IHTMLLocation(iface); - FIXME("(%p)->(%s)\n", This, debugstr_w(v)); - return E_NOTIMPL; + WCHAR *hash = v; + HRESULT hres; + + TRACE("(%p)->(%s)\n", This, debugstr_w(v)); + + if(!This->window || !This->window->base.outer_window) { + FIXME("No window available\n"); + return E_FAIL; + } + + if(hash[0] != '#') { + unsigned size = (1 /* # */ + wcslen(v) + 1) * sizeof(WCHAR); + if(!(hash = heap_alloc(size))) + return E_OUTOFMEMORY; + hash[0] = '#'; + memcpy(hash + 1, v, size - sizeof(WCHAR)); + } + + hres = navigate_url(This->window->base.outer_window, hash, This->window->base.outer_window->uri, BINDING_NAVIGATED); + + if(hash != v) + heap_free(hash); + return hres; }
static HRESULT WINAPI HTMLLocation_get_hash(IHTMLLocation *iface, BSTR *p) diff --git a/dlls/mshtml/tests/documentmode.js b/dlls/mshtml/tests/documentmode.js index 92f30f8b7e9..5da89349d6d 100644 --- a/dlls/mshtml/tests/documentmode.js +++ b/dlls/mshtml/tests/documentmode.js @@ -895,6 +895,18 @@ async_test("script_load", function() { external.writeStream("simple", "ready_states += 'exec,';"); });
+sync_test("location", function() { + document.body.innerHTML = '<a name="testanchor">test</a>'; + + ok(location.hash === "", "initial location.hash = " + location.hash); + location.hash = "TestAnchor"; + ok(location.hash === "#TestAnchor", "location.hash after set to TestAnchor = " + location.hash); + location.hash = "##foo"; + ok(location.hash === "##foo", "location.hash after set to ##foo = " + location.hash); + location.hash = "#testanchor"; + ok(location.hash === "#testanchor", "location.hash after set to #testanchor = " + location.hash); +}); + sync_test("navigator", function() { var v = document.documentMode, re; var app = navigator.appVersion;
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmldoc.c | 37 ++++++++++++++++++++++++++++++++++-- dlls/mshtml/htmlnode.c | 5 +++++ dlls/mshtml/mshtml_private.h | 2 ++ dlls/mshtml/tests/dom.js | 27 ++++++++++++++++++++++++++ 4 files changed, 69 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmldoc.c b/dlls/mshtml/htmldoc.c index dd7d9f44d48..0988d34f85b 100644 --- a/dlls/mshtml/htmldoc.c +++ b/dlls/mshtml/htmldoc.c @@ -4375,8 +4375,41 @@ static HRESULT WINAPI HTMLDocument7_importNode(IHTMLDocument7 *iface, IHTMLDOMNo VARIANT_BOOL fDeep, IHTMLDOMNode3 **ppNodeDest) { HTMLDocumentNode *This = impl_from_IHTMLDocument7(iface); - FIXME("(%p)->(%p %x %p)\n", This, pNodeSource, fDeep, ppNodeDest); - return E_NOTIMPL; + nsIDOMNode *nsnode = NULL; + HTMLDOMNode *node; + nsresult nsres; + HRESULT hres; + + TRACE("(%p)->(%p %x %p)\n", This, pNodeSource, fDeep, ppNodeDest); + + if(!This->nsdoc) { + WARN("NULL nsdoc\n"); + return E_UNEXPECTED; + } + + if(!(node = unsafe_impl_from_IHTMLDOMNode(pNodeSource))) { + ERR("not our node\n"); + return E_FAIL; + } + + nsres = nsIDOMHTMLDocument_ImportNode(This->nsdoc, node->nsnode, !!fDeep, 1, &nsnode); + if(NS_FAILED(nsres)) { + ERR("ImportNode failed: %08lx\n", nsres); + return map_nsresult(nsres); + } + + if(!nsnode) { + *ppNodeDest = NULL; + return S_OK; + } + + hres = get_node(nsnode, TRUE, &node); + nsIDOMNode_Release(nsnode); + if(FAILED(hres)) + return hres; + + *ppNodeDest = &node->IHTMLDOMNode3_iface; + return hres; }
static HRESULT WINAPI HTMLDocument7_get_parentWindow(IHTMLDocument7 *iface, IHTMLWindow2 **p) diff --git a/dlls/mshtml/htmlnode.c b/dlls/mshtml/htmlnode.c index 42ac37a7736..a293b332a9f 100644 --- a/dlls/mshtml/htmlnode.c +++ b/dlls/mshtml/htmlnode.c @@ -1067,6 +1067,11 @@ static const IHTMLDOMNodeVtbl HTMLDOMNodeVtbl = { HTMLDOMNode_get_nextSibling };
+HTMLDOMNode *unsafe_impl_from_IHTMLDOMNode(IHTMLDOMNode *iface) +{ + return iface->lpVtbl == &HTMLDOMNodeVtbl ? impl_from_IHTMLDOMNode(iface) : NULL; +} + static HTMLDOMNode *get_node_obj(IHTMLDOMNode *iface) { HTMLDOMNode *ret; diff --git a/dlls/mshtml/mshtml_private.h b/dlls/mshtml/mshtml_private.h index c403b4efc54..23eeb0ec11b 100644 --- a/dlls/mshtml/mshtml_private.h +++ b/dlls/mshtml/mshtml_private.h @@ -807,6 +807,8 @@ struct HTMLDOMNode { HTMLDocumentNode *doc; };
+HTMLDOMNode *unsafe_impl_from_IHTMLDOMNode(IHTMLDOMNode*) DECLSPEC_HIDDEN; + static inline void node_addref(HTMLDOMNode *node) { IHTMLDOMNode_AddRef(&node->IHTMLDOMNode_iface); diff --git a/dlls/mshtml/tests/dom.js b/dlls/mshtml/tests/dom.js index 43c52d89757..5a31b869c8f 100644 --- a/dlls/mshtml/tests/dom.js +++ b/dlls/mshtml/tests/dom.js @@ -722,3 +722,30 @@ sync_test("classList", function() { ok(("" + classList) === " testclass foobar ", "Expected classList value ' testclass foobar ', got " + classList); ok(classList.toString() === " testclass foobar ", "Expected classList toString ' testclass foobar ', got " + classList.toString()); }); + +sync_test("importNode", function() { + var node, node2, orig_node, doc = document.implementation.createHTMLDocument("TestDoc"); + doc.body.innerHTML = '<div id="test"><span/></div>'; + orig_node = doc.getElementById("test"); + + node = document.importNode(orig_node, false); + ok(node !== orig_node, "node = orig_node"); + ok(orig_node.hasChildNodes() === true, "orig_node does not have child nodes"); + ok(orig_node.parentNode === doc.body, "orig_node.parentNode = " + orig_node.parentNode); + ok(node.hasChildNodes() === false, "node has child nodes with shallow import"); + ok(node.parentNode === null, "node.parentNode = " + node.parentNode); + + node = document.importNode(orig_node, true); + ok(node !== orig_node, "node = orig_node"); + ok(orig_node.hasChildNodes() === true, "orig_node does not have child nodes"); + ok(orig_node.parentNode === doc.body, "orig_node.parentNode = " + orig_node.parentNode); + ok(node.hasChildNodes() === true, "node does not have child nodes with deep import"); + ok(node.parentNode === null, "node.parentNode = " + node.parentNode); + + node2 = document.importNode(node, false); + ok(node !== node2, "node = node2"); + ok(node.hasChildNodes() === true, "node does not have child nodes"); + ok(node.parentNode === null, "node.parentNode = " + node.parentNode); + ok(node2.hasChildNodes() === false, "node2 has child nodes"); + ok(node2.parentNode === null, "node2.parentNode = " + node2.parentNode); +});
Hi,
It looks like your patch introduced the new failures shown below. Please investigate and fix them before resubmitting your patch. If they are not new, fixing them anyway would help a lot. Otherwise please ask for the known failures list to be updated.
The tests also ran into some preexisting test failures. If you know how to fix them that would be helpful. See the TestBot job for the details:
The full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=125723
Your paranoid android.
=== w10pro64 (32 bit report) ===
mshtml: events.c:1098: Test failed: unexpected call img_onerror events: Timeout
=== w10pro64 (64 bit report) ===
mshtml: events.c:1098: Test failed: unexpected call img_onerror events: Timeout
=== w1064 (64 bit report) ===
mshtml: htmldoc.c:351: Test failed: expected Exec_SETTITLE htmldoc.c:2938: Test failed: unexpected call Exec_SETTITLE
=== w10pro64 (64 bit report) ===
mshtml: htmldoc.c:3163: Test failed: Incorrect error code: -2146697211 htmldoc.c:3168: Test failed: Page address: L"http://test.winehq.org/tests/winehq_snapshot/" htmldoc.c:5950: Test failed: expected OnChanged_1012 htmldoc.c:5951: Test failed: expected Exec_HTTPEQUIV htmldoc.c:5953: Test failed: expected Exec_SETTITLE htmldoc.c:5994: Test failed: expected FireNavigateComplete2
=== w10pro64_ja (64 bit report) ===
mshtml: htmldoc.c:351: Test failed: expected Exec_SETTITLE htmldoc.c:2938: Test failed: unexpected call Exec_SETTITLE
Jacek Caban (@jacek) commented about dlls/mshtml/navigate.c:
if(is_main_content_window(window)) { BOOL cancel;
if(flags & BINDING_FRAGNAV)
return super_navigate(window, uri, flags, headers, post_data, post_data_len);
Now fragment-only navigation is not using `navigate_fragment()`. Why do you insist on using `super_navigate()`? You could just call `navigate_fragment()` from `navigate_uri()` when needed.
On Fri Nov 4 10:52:55 2022 +0000, Jacek Caban wrote:
Now fragment-only navigation is not using `navigate_fragment()`. Why do you insist on using `super_navigate()`? You could just call `navigate_fragment()` from `navigate_uri()` when needed.
But the flag with BINDING_FRAGNAV is passed to super_navigate, so it should be using navigate_fragment, unless I'm missing something? I just moved the fragment check out of it since it's the only place where it was used, anyway (the other place has BINDING_NOFRAG).
As for why, AFAIK some tests failed if they didn't receive the notification before the fragment navigation, which super_navigate does.
On Fri Nov 4 13:43:33 2022 +0000, Gabriel Ivăncescu wrote:
But the flag with BINDING_FRAGNAV is passed to super_navigate, so it should be using navigate_fragment, unless I'm missing something? I just moved the fragment check out of it since it's the only place where it was used, anyway (the other place has BINDING_NOFRAG). As for why, AFAIK some tests failed if they didn't receive the notification before the fragment navigation, which super_navigate does.
Nevermind, it seems it's not needed, I probably messed something up last time, so I guess I'll use navigate_fragment then.