Support for externref

537 views
Skip to first unread message

ben layet

unread,
Jan 23, 2021, 6:49:30 AM1/23/21
to emscripten-discuss
Does emscripten support externref reference types for holding opaque handles to JS objects in C++? If not, any idea when?

Thomas Lively

unread,
Jan 23, 2021, 12:54:25 PM1/23/21
to emscripte...@googlegroups.com
Not yet, but there are some folks working on this. Perhaps it will be ready to use in a few months? It’s hard to say for sure.

On Sat, Jan 23, 2021 at 03:49 ben layet <lay...@gmail.com> wrote:
Does emscripten support externref reference types for holding opaque handles to JS objects in C++? If not, any idea when?

--
You received this message because you are subscribed to the Google Groups "emscripten-discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email to emscripten-disc...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/emscripten-discuss/7f6178fa-bd05-4f65-aa7c-9e5a405bf851n%40googlegroups.com.

ben layet

unread,
Jan 25, 2021, 3:55:18 AM1/25/21
to emscripten-discuss
Thanks!
Is there a feature ticket in a publicly visible ticket tracker that I can keep an eye on?
cheers
ben

Thomas Lively

unread,
Jan 25, 2021, 1:51:36 PM1/25/21
to emscripte...@googlegroups.com
I don't think so, but you can keep an eye on commits from "wingo" and "pmatos" on reviews.llvm.org to keep track of the progress.

Karl Werner

unread,
Oct 10, 2022, 11:56:34 AM10/10/22
to emscripten-discuss
Does anyone have news on this topic?

Thaina Yu

unread,
Mar 17, 2023, 11:23:13 AM3/17/23
to emscripten-discuss
Is this mean externref already usable?

https://github.com/emscripten-core/emscripten/pull/15913

Thomas Lively

unread,
Mar 17, 2023, 11:35:55 AM3/17/23
to emscripte...@googlegroups.com
Yes, but note that the usage in that commit is only in hand-written assembly code, not in C/C++.

More recently, support for externref landed upstream in clang: https://github.com/llvm/llvm-project/blob/main/clang/test/CodeGen/WebAssembly/wasm-externref.c. AFAIK we haven't yet experimented with it in Emscripten, but in principle it should work.

Thaina Yu

unread,
Mar 23, 2023, 9:51:59 AM3/23/23
to emscripten-discuss
Do we have anyway to write hand-written assembly code along with emscripten? And is it possible to return that externref from wasm code into emscripten world?

I am actually using unity which use emscripten to build webgl. Would it possible to use EM_ASM_PTR to write wasm code to return as pointer (externref ? (an so I might return pointer as IntPtr in C#)) ?

Sam Clegg

unread,
Mar 23, 2023, 12:17:52 PM3/23/23
to emscripte...@googlegroups.com
On Thu, Mar 23, 2023 at 6:52 AM Thaina Yu <thai...@gmail.com> wrote:
Do we have anyway to write hand-written assembly code along with emscripten? And is it possible to return that externref from wasm code into emscripten world?

Here is the example how to use externref in assembly:  https://github.com/emscripten-core/emscripten/blob/main/test/core/test_externref.s

Until recently there was no way to communicate those references directly to C++ but it maybe possible now that upstream clan support has landed.

There is no current support for externref in EM_ASM.   We could potentially add EM_ASM_REF which returns a ref to C/C++ but until recently that would have been impossible.

Thaina Yu

unread,
Mar 23, 2023, 12:20:34 PM3/23/23
to emscripten-discuss
Thank you very much. Are there any public discussion or roadmap to add EM_ASM_REF into emscripten?

Sam Clegg

unread,
Mar 23, 2023, 12:34:43 PM3/23/23
to emscripte...@googlegroups.com
On Thu, Mar 23, 2023 at 9:20 AM Thaina Yu <thai...@gmail.com> wrote:
Thank you very much. Are there any public discussion or roadmap to add EM_ASM_REF into emscripten?

You are the first person that I know of to suggest it.

Be aware that using externref directly in C/C++ is very limited, even after the recent changes.  For example you can't store them in structs or class or store them to memory.  All you can really do with them is pass them around and (maybe) put them in tables.  So in practice I'm not sure how useful this stuff is yet, but I could be wrong?


 

Thaina Yu

unread,
Mar 23, 2023, 12:51:17 PM3/23/23
to emscripten-discuss
I am actually using emscripten from unity and I mainly use C# code from unity side. But there are tons of 3rd party library and SDK that written with assumption that we will only use JavaScript. It then need us to construct javascript object in javascript and pass javascript object reference all over the places. For example, the google's firebase SDK that we need to construct it special object type to work with its complex services

It then become very frustrating to wrap everything in an API with mergeInto library that kept growing for everythings related to js object

With just the ability to pass externref into C# as IntPtr or int64 and so C# can pass it to another js API after it was done everything in C# is just what we really need, everything would come together as a flow of reference. The chain of bottleneck is that unity rely on emscripten to fully support externref first then it could start support it in some future. So the sluggish are stacking up

Sam Clegg

unread,
Mar 23, 2023, 1:03:02 PM3/23/23
to emscripte...@googlegroups.com
On Thu, Mar 23, 2023 at 9:51 AM Thaina Yu <thai...@gmail.com> wrote:
I am actually using emscripten from unity and I mainly use C# code from unity side. But there are tons of 3rd party library and SDK that written with assumption that we will only use JavaScript. It then need us to construct javascript object in javascript and pass javascript object reference all over the places. For example, the google's firebase SDK that we need to construct it special object type to work with its complex services

It then become very frustrating to wrap everything in an API with mergeInto library that kept growing for everythings related to js object

With just the ability to pass externref into C# as IntPtr or int64 and so C# can pass it to another js API after it was done everything in C# is just what we really need, everything would come together as a flow of reference. The chain of bottleneck is that unity rely on emscripten to fully support externref first then it could start support it in some future. So the sluggish are stacking up

But `IntPtr` and `int64` are fundamentally not externref, right?   Or are you imagining those being indexes into a table of externref perhaps?  That would work, but then the tricky part becoming managing that table.  This is mind what embind does when it refers to JS object from native code I believe.

Thaina Yu

unread,
Mar 23, 2023, 1:12:11 PM3/23/23
to emscripten-discuss
I don't actually know which things unity would use to hold the value of externref, just guessing it would be IntPtr. But by anything it require that emscripten can officially define externref first anyway

Sam Clegg

unread,
Mar 23, 2023, 2:47:20 PM3/23/23
to emscripte...@googlegroups.com
On Thu, Mar 23, 2023 at 10:12 AM Thaina Yu <thai...@gmail.com> wrote:
I don't actually know which things unity would use to hold the value of externref, just guessing it would be IntPtr. But by anything it require that emscripten can officially define externref first anyway

The problem is that externref can't live in memory, so it can't live inside a struct or class or array or any C#/C++/C data type.  So it's not going to be very usable IIUC.   We already have `EM_VAL` in emscripten which is a way to refer to a JS object via an integer handle.   I don't think we can build anything better than EM_VAL any time soon, at least nothing that can work well with C/C++/C#, but perhaps I'm missing something?

  

Thaina Yu

unread,
Mar 23, 2023, 9:50:24 PM3/23/23
to emscripten-discuss
I am not sure how limited it is but there are many situation that we just need a value to pass object from one function to another immediately in the same flow

By the way, which the handle would be returned as EM_ASM_INT or EM_ASM_PTR ?

Sam Clegg

unread,
Mar 24, 2023, 12:27:13 PM3/24/23
to emscripte...@googlegroups.com
On Thu, Mar 23, 2023 at 6:50 PM Thaina Yu <thai...@gmail.com> wrote:
I am not sure how limited it is but there are many situation that we just need a value to pass object from one function to another immediately in the same flow

By the way, which the handle would be returned as EM_ASM_INT or EM_ASM_PTR ?

 EM_ASM_INT is probably what you want if you want to return an integer handle to JS object.    e.g. Something like an EM_VAL or a handle to JS promise.  

In emscripten we use this thing called a HandleAllocator to map integers to JS objects:  https://github.com/emscripten-core/emscripten/blob/3cf83fdc4711e9bf3b01cf9821e717311a13c1b5/src/library.js#L3714-L3715

Because native code wants to deal with integers whenever we want to pass a JS object to native code we go through this handle allocator.   When JS receives an integer handle from native code it can turn it back into a JS object by looking it up in a given handle allocator.   In theory being able to pass externref directly looks like a way to remove the need for the extra mapping, but in practice C/C++ needs to be able to store handles in memory (and in data structures that live in memory) so using externref instead of `int` for EM_VAL doesn't work (at least not today).


Thaina Yu

unread,
Mar 24, 2023, 12:28:48 PM3/24/23
to emscripten-discuss
Thank you very much
Reply all
Reply to author
Forward
0 new messages