For I/O, you can have a look at my IO system, at the frontend there's a 
simple IO::Load() function which takes an URL, a success, and a failure 
callback. The callbacks are usually provided as C++11 lambdas (but can also 
be traditional C function pointers). Under the hood I have a threaded (no 
native platforms) and unthreaded (for emscripten) version. The threaded 
version has one or more worker threads which call blocking IO functions, 
and the non-threaded version calls into emscripten asynchronous file 
functions (which also take a success and failure callback).

Here's how it looks on the user-side:

https://github.com/floooh/oryol/blob/master/code/Samples/IOQueueSample/IOQueueSample.cc#L45

Under the hood it looks a bit ugly, since both the threaded and 
non-threaded version use a message queue (I tried to keep code size for the 
2 implementations small even at the cost of some efficiency):

https://github.com/floooh/oryol/blob/master/code/Modules/IO/FS/ioWorker.cc#L52

The IO requests then end up in a 'plugin filesystem' implementation, here's 
the emscripten version of the HTTP filesystem, this simply calls into the 
async_wget functions, and has a success- and failure-callback. All this is 
running on the main thread, but is non-blocking:

https://github.com/floooh/oryol/blob/master/code/Modules/HTTP/emsc/emscURLLoader.cc

...and here is one native implementation using curl, this is running in 
1..N worker threads, and uses blocking curl calls:

https://github.com/floooh/oryol/blob/master/code/Modules/HTTP/curl/curlURLLoader.cc

>From the outside, both the threaded and non-threaded versions work the 
same. You call the async IO::Load() function and provide a success- and 
failure-callback. Once the IO request has been handled, the callbacks will 
be called (always from the main thread).

For networking I have implemented a transparent socket/websocket solution. 
On the server I would have 2 ports open, one for native clients, and one 
for emscripten clients. The emscripten port implemented a WebSocket 
wrapper. Both would call into the same message handler functions. So from 
the outside on the server side, it wouldn't matter if a native client (via 
TCP) or an emscripten client (via WebSocket) connected.

On the client, the emscripten client would use the non-blocking socket() 
wrapper functions (the code looks pretty much identical like a non-blocking 
socket connection, emscripten simply doesn't implement the blocking socket 
behaviour). On the native clients, I had threads with blocking socket calls.

One thing I was considering but didn't implement was to use WebSocket's 
message framing also for the native socket connection. Chances are that you 
have your own message framing on top of TCP streams anyway, and the 
WebSocket framing looks quite efficient, so I would use WebSocket's framing 
also on native connections, which would save some code on the server side.

For the socket/websocket stuff, I don't have any open source code to show 
unfortunately, but writing a websocket wrapper is really simple, I used 
John McCutchan's blog post as 
base: 
http://www.gamasutra.com/view/news/129227/Indepth_Writing_your_own_WebSocket_server.php

Hope this helps :)
-Floh.


Am Dienstag, 27. September 2016 12:24:38 UTC+2 schrieb Ciprian Tomoiaga:
>
> Hi all,
>
> I'm trying to figure out how I can use emscripten to get my project on the 
> web. Any pointers or ideas would be greatly appreciated!
> I have a rendering application in C that uses:
>
>    1. OpenGL (with user buffers) and FreeGLUT
>    2. sockets to dynamically get rendering data from a server
>    3. threads (pThreads or OpenMP) to do point 2 asynchronously, without 
>    blocking the rendering thread
>
> Basically, the background thread gets updated data from the server and 
> puts it in a global array. The main (rendering) thread just renders this 
> global array.
>
>
> If I were to port it by hand, here's what I would do in JS (single 
> threaded):
>
>    - I would detect the need to update and query the server via websocket 
>    (and websockify proxy)
>    - in the "on_message" event, I would save the new data, passing it 
>    from binary into doubles
>    - the server closes the connection after every query; therefore, in 
>    the "on_close" event I would set a signal need_to_update = true;
>    - in the rendering function, if need_to_update I would update the 
>    buffers with the previous data 
>    
> This is mono-threaded and most functions are quite small workers, I 
> believe.
>
>
> It seems to be that the 2 approaches are highly incompatible, but I don't 
> want to port by hand all the data structure and rendering process.
>
> I was thinking of modifying the C code to resemble the JS structure 
> (removing the threads), but since C isn't event based, I'm not sure how to 
> proceed with the "on_message" part.
>
>
> What solutions can I use ? Is there any example of any similar porting ?
>
> Many thanks for reading all this! :) Your experience will be greatly 
> appreciated.
>
>
> Ciprian
>
>
>

-- 
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 [email protected].
For more options, visit https://groups.google.com/d/optout.

Reply via email to