Thursday, July 9, 2020

WebAssmebly passing string from C to JavaScript

Recently, I am working on a project that involves WebAssembly. In the project I would need to call out a JavaScript function with a C string char *string as parameter.

I could not get the string in JavaScript function, searching on the internet does not result in any useful information. None of the solutions I found are elegant. Then I realized I had used the WebSocket APIs from Emscripten, which is passing the URL as a C string to the underline JavaScript support function. How does it do that? I digged out the source of it and found in function emscripten_websocket_new, it is using UTF8ToString to convert the C string to a JavaScript String. UTF8ToString is Emscripten's runtime function, I could not call it directly from my JavaScript function.

According to the preamble.js document, I would need to use -s 'EXTRA_EXPORTED_RUNTIME_METHODS=["UTF8ToString"]' on the linker command to export the function and use it as Module.UTF8ToString. Problem solved.

Below are sample code that demonstrate the usage:
JavaScirpt function:

function processing_string_from_c(ptr, len) {
    var text = Module.UTF8ToString(ptr, len);
    ....
}
In the C code:
 char *string;
 ...
 EM_ASM({process_string_from_c($0, $1);}, string, strlen(string));
 ...
And in the linker line, remember to use
-s 'EXTRA_EXPORTED_RUNTIME_METHODS=["UTF8ToString"]'
P.S. In the latest release of emscripten, the export functions become global scope. So calls would be UTF8ToString() directly.