AlloSphere-Research-Group / allolib

Library for interactive multimedia application development
BSD 3-Clause "New" or "Revised" License
36 stars 14 forks source link

cling: experiments and exploration #49

Open kybr opened 2 years ago

kybr commented 2 years ago

We have already worked on this a bit. I thought I would start a record of the journey and a conversation.

For many reasons, it would be nice to interact with our framework from a REPL. cling (https://root.cern/cling/) offers an opportunity for that.

Thank you Andrés for your work on compiling shared libraries. This allows us to link in cling because (at the moment) cling only supports dynamic linking to shared libraries.

Here is the state of things on macOS 10.15.7 on Intel x64:

cd path/to/allolib
cling -std=c++14
****************** CLING ******************
* Type C++ code and press enter to run it *
*             Type .q to exit             *
*******************************************
[cling]$ #include "prelude.h" // takes a second
[cling]$ al::Vec3f v(al::rnd::uniform())
(al::Vec3f &) { 0.340817f, 0.340817f, 0.340817f }
[cling]$

I installed cling with brew install cling.

I compiled AlloLib after configuring the CMakeLists.txt. I turned on building shared libraries:

option(ALLOLIB_BUILD_SHARED "Build all libraries as shared libraries" ON)

Here is the contents of prelude.h:

// load libraries..
//
#pragma cling load("build/libal.dylib")
#pragma cling load("build/external/libimgui.dylib")
#pragma cling load("build/external/Gamma/libGamma.dylib")
#pragma cling load("build/external/rtmidi/librtmidi.dylib")
#pragma cling load("build/external/liboscpack.dylib")
#pragma cling load("build/external/rtaudio/librtaudio.dylib")
#pragma cling load("build/external/glad/libglad.dylib")
#pragma cling load("build/external/libserial.dylib")
#pragma cling load("build/external/glfw/src/libglfw.dylib")

// include PATHs
//
#pragma cling add_include_path("include")
#pragma cling add_include_path("external/Gamma")
#pragma cling add_include_path("external/glad/include")

// include headers
//
#include "al/app/al_App.hpp"
#include "al/math/al_Functions.hpp"
#include "al/math/al_Random.hpp"

If someone could try Linux and report back, it would be appreciated.

cling binaries and supporting libraries are hard to come by for Windows. My attempts to build cling.exe ended in failure (so far). This GitHub repository has binaries that worked for me:

https://github.com/boydingham/cling.for.windows

..but I would not ask others to trust the binaries of some random "author". If someone succeeds at building cling on windows or finds a reputable source of binaries, please report this. I will try to test on Windows with what I have.

kybr commented 2 years ago

I can also report that this opens a window and draws a red background:

cd path/to/allolib
cling -std=c++14
****************** CLING ******************
* Type C++ code and press enter to run it *
*             Type .q to exit             *
*******************************************
[cling]$ #include "prelude.h" // takes a second
[cling]$ struct Foo : al::App { void onDraw(al::Graphics& g) override { g.clear(1, 0, 0); }};
[cling]$ Foo().start()
Parameter OSC Handshake server running on 0.0.0.0:16987
Parameter Server OSC port (primary): 0.0.0.0:9010
[cling]$

The cling terminal hangs---Foo().start() blocks. And, the terminal comes back only after we quit the app. But (!) the app does not really quit. We get the pinwheel and the window will not disappear.

kybr commented 2 years ago

cling is at the heart of CERN's data analysis framework, ROOT: https://root.cern.ch/.

ROOT is sort of like the Python Notebook stack or MATLAB, but the underlying language is C++. I am not sure how many scientists use ROOT rather than MATLAB, python, R, Julia or some other stack.

ROOT enables statistically sound scientific analyses and visualization of large amounts of data: today, more than 1 exabyte (1,000,000,000 gigabyte) are stored in ROOT files. The Higgs was found with ROOT!

kybr commented 2 years ago

Can we use a thread to make an app start non-blocking? I tried these two methods:

cling -std=c++14
****************** CLING ******************
* Type C++ code and press enter to run it *
*             Type .q to exit             *
*******************************************
[cling]$ #include "prelude.h"
[cling]$ #include <thread>
[cling]$ struct Foo : al::App { void onDraw(al::Graphics& g) override { g.clear(1, 0, 0); }};
[cling]$ std::thread t([]{ Foo().start(); }); // CRASH
cling -std=c++14
****************** CLING ******************
* Type C++ code and press enter to run it *
*             Type .q to exit             *
*******************************************
[cling]$ #include "prelude.h"
[cling]$ #include <thread>
[cling]$ struct Foo : al::App { void onDraw(al::Graphics& g) override { g.clear(1, 0, 0); }};
[cling]$ Foo foo;
[cling]$ std::thread t([&]{ foo.start(); }); // CRASH

The crash report looked like this:

Crashed Thread:        1

Exception Type:        EXC_CRASH (SIGABRT)
Exception Codes:       0x0000000000000000, 0x0000000000000000
Exception Note:        EXC_CORPSE_NOTIFY

Application Specific Information:
abort() called
terminating with uncaught exception of type NSException
*** Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: '+[NSUndoManager(NSInternal) _endTopLevelGroupings] is only safe to invoke on the main thread.'

Application Specific Backtrace 1:
0   CoreFoundation                      0x00007fff2d6364d7 __exceptionPreprocess + 250
1   libobjc.A.dylib                     0x00007fff661af5bf objc_exception_throw + 48
2   CoreFoundation                      0x00007fff2d65f678 +[NSException raise:format:arguments:] + 88
3   Foundation                          0x00007fff2fd5490d -[NSAssertionHandler handleFailureInMethod:object:file:lineNumber:description:] + 191
4   Foundation                          0x00007fff2fc9105e +[NSUndoManager(NSPrivate) _endTopLevelGroupings] + 440
5   AppKit                              0x00007fff2a81dc7c -[NSApplication run] + 864
6   libglfw.3.3.dylib                   0x0000000115826c6f _glfwPlatformCreateWindow + 79
7   libglfw.3.3.dylib                   0x000000011581ce8d glfwCreateWindow + 1021
8   libal.dylib                         0x0000000114caae4f _ZN2al6Window10implCreateEb + 271
9   libal.dylib                         0x0000000114ca6c2d _ZN2al6Window6createEb + 61
10  libal.dylib                         0x0000000114b8e67e _ZN2al22GLFWOpenGLWindowDomain4initEPNS_17ComputationDomainE + 414
11  libal.dylib                         0x0000000114b8d9cd _ZN2al20OpenGLGraphicsDomain9newWindowEv + 77
12  libal.dylib                         0x0000000114aee864 _ZN2al3App5startEv + 84
13  ???                                 0x0000000115ec6fc2 0x0 + 4662783938
14  ???                                 0x0000000115ec6eeb 0x0 + 4662783723
15  ???                                 0x0000000115ec6e3a 0x0 + 4662783546
16  ???                                 0x0000000115ec6482 0x0 + 4662781058
17  libsystem_pthread.dylib             0x00007fff6755c109 _pthread_start + 148
18  libsystem_pthread.dylib             0x00007fff67557b8b thread_start + 15