There is Aborted crash on browser when I resize window. My web app is based on VTK wasm.
Test.js:8 Uncaught RuntimeError: Aborted(Assertion failed: attempt to write non-integer (undefined) into integer heap)
at abort (Test.js:8:14216)
at assert (Test.js:8:8111)
at checkInt (Test.js:8:20560)
at checkInt32 (Test.js:8:20963)
at Object.uiEventHandlerFunc [as handlerFunc] (Test.js:8:300701)
at jsEventHandler (Test.js:8:197167)
at WasmCanvas.tsx:54:12
resize event!
wasmModule.ts:298 Aborted(Assertion failed: attempt to write non-integer (undefined) into integer heap)
overrideMethod @ hook.js:608
logErr @ wasmModule.ts:298
abort @ Test.js:8
assert @ Test.js:8
checkInt @ Test.js:8
checkInt32 @ Test.js:8
uiEventHandlerFunc @ Test.js:8
jsEventHandler @ Test.js:8Understand this warningAI
Test.js:8 Uncaught RuntimeError: Aborted(Assertion failed: attempt to write non-integer (undefined) into integer heap)
at abort (Test.js:8:14216)
at assert (Test.js:8:8111)
at checkInt (Test.js:8:20560)
at checkInt32 (Test.js:8:20963)
at Object.uiEventHandlerFunc [as handlerFunc] (Test.js:8:300701)
at jsEventHandler (Test.js:8:197167)
Check uiEventHandlerFunc in Test.js:
function registerUiEventCallback(target, userData, useCapture, callbackfunc, eventTypeId, eventTypeString, targetThread) {
targetThread = JSEvents.getTargetThreadForEventCallback(targetThread);
if (!JSEvents.uiEvent)
JSEvents.uiEvent = _malloc(36);
target = findEventTarget(target);
var uiEventHandlerFunc = function(e=event) {
if (e.target != target) {
return
}
var b = document.body;
if (!b) {
return
}
var uiEvent = targetThread ? _malloc(36) : JSEvents.uiEvent;
GROWABLE_HEAP_I32()[uiEvent >>> 2] = e.detail;
checkInt32(e.detail); // 高版本中一直存在
GROWABLE_HEAP_I32()[uiEvent + 4 >>> 2] = b.clientWidth;
checkInt32(b.clientWidth);
GROWABLE_HEAP_I32()[uiEvent + 8 >>> 2] = b.clientHeight;
checkInt32(b.clientHeight);
GROWABLE_HEAP_I32()[uiEvent + 12 >>> 2] = innerWidth;
checkInt32(innerWidth);
GROWABLE_HEAP_I32()[uiEvent + 16 >>> 2] = innerHeight;
checkInt32(innerHeight);
GROWABLE_HEAP_I32()[uiEvent + 20 >>> 2] = outerWidth;
checkInt32(outerWidth);
GROWABLE_HEAP_I32()[uiEvent + 24 >>> 2] = outerHeight;
checkInt32(outerHeight);
GROWABLE_HEAP_I32()[uiEvent + 28 >>> 2] = pageXOffset;
checkInt32(pageXOffset);
GROWABLE_HEAP_I32()[uiEvent + 32 >>> 2] = pageYOffset;
checkInt32(pageYOffset);
if (targetThread)
JSEvents.queueEventHandlerOnThread_iiii(targetThread, callbackfunc, eventTypeId, uiEvent, userData);
else if (getWasmTableEntry(callbackfunc)(eventTypeId, uiEvent, userData))
e.preventDefault()
};
Then we can read /emsdk/upstream/emscripten/src/library_html5.js
and find registerUiEventCallback
and uiEventHandlerFunc
on the file.
var uiEventHandlerFunc = (e = event) => {
if (e.target != target) {
// Never take ui events such as scroll via a 'bubbled' route, but always from the direct element that
// was targeted. Otherwise e.g. if app logs a message in response to a page scroll, the Emscripten log
// message box could cause to scroll, generating a new (bubbled) scroll message, causing a new log print,
// causing a new scroll, etc..
return;
}
var b = document.body; // Take document.body to a variable, Closure compiler does not outline access to it on its own.
if (!b) {
// During a page unload 'body' can be null, with "Cannot read property 'clientWidth' of null" being thrown
return;
}
#if PTHREADS
var uiEvent = targetThread ? _malloc({{{ C_STRUCTS.EmscriptenUiEvent.__size__ }}}) : JSEvents.uiEvent;
#else
var uiEvent = JSEvents.uiEvent;
#endif
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.detail, 'e.detail', 'i32') }}};
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.documentBodyClientWidth, 'b.clientWidth', 'i32') }}};
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.documentBodyClientHeight, 'b.clientHeight', 'i32') }}};
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.windowInnerWidth, 'innerWidth', 'i32') }}};
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.windowInnerHeight, 'innerHeight', 'i32') }}};
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.windowOuterWidth, 'outerWidth', 'i32') }}};
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.windowOuterHeight, 'outerHeight', 'i32') }}};
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.scrollTop, 'pageXOffset', 'i32') }}};
{{{ makeSetValue('uiEvent', C_STRUCTS.EmscriptenUiEvent.scrollLeft, 'pageYOffset', 'i32') }}};
#if PTHREADS
if (targetThread) __emscripten_run_callback_on_thread(targetThread, callbackfunc, eventTypeId, uiEvent, userData);
else
#endif
if ({{{ makeDynCall('iipp', 'callbackfunc') }}}(eventTypeId, uiEvent, userData)) e.preventDefault();
};
There is checkInt32(e.detail) in registerUiEventCallback in exported js file Test.js which was generated from emsdk 3.1.51 but emsdk 3.1.29 has not it.
Compare uiEventHandlerFunc on /emsdk/upstream/emscripten/src/library_html5.js
of 3.1.51 and 3.1.29.
Compare uiEventHandlerFunc on Test.js (exported js file) from 3.1.51 and 3.1.29.
That is to say, emcc makes the code compiled from makeSetValue different. Relevant file: src\parseTools.js
We continue to trace, and find that the higher version generates checkInt logic.
From the log, it can be seen that the parameter e passed into the uiEventHandlerFunc, its member detail (e.detail) is undefined, so it can’t pass through checkInt32 (assert in mapSetValue):
So it’s not recommaned to use the newer emsdk to generate wam file about window app before fixing this bug.