add compile time configs for tracy, mimalloc and qrencode

This commit is contained in:
2025-07-18 05:23:00 -05:00
parent 881407a64f
commit 7bfd244bf2
6 changed files with 116 additions and 27 deletions

View File

@@ -1,7 +1,7 @@
project('cell', ['c', 'cpp'], project('cell', ['c', 'cpp'],
version: '0.9.3', version: '0.9.3',
meson_version: '>=1.4', meson_version: '>=1.4',
default_options : [ 'cpp_std=c++11']) default_options : [ 'cpp_std=c++11', 'default_library=static'])
libtype = get_option('default_library') libtype = get_option('default_library')
@@ -138,7 +138,8 @@ if host_machine.system() == 'windows'
deps += cc.find_library('bcrypt') deps += cc.find_library('bcrypt')
sdl3_opts.add_cmake_defines({'HAVE_ISINF': '1'}) # Hack for MSYS2 sdl3_opts.add_cmake_defines({'HAVE_ISINF': '1'}) # Hack for MSYS2
sdl3_opts.add_cmake_defines({'HAVE_ISNAN': '1'}) sdl3_opts.add_cmake_defines({'HAVE_ISNAN': '1'})
link += '-static' link += ['-static', '-static-libgcc', '-static-libstdc++']
add_project_link_arguments('-static-libgcc', '-static-libstdc++', language: ['c', 'cpp'])
endif endif
if host_machine.system() == 'emscripten' if host_machine.system() == 'emscripten'
@@ -232,18 +233,31 @@ if host_machine.system() != 'emscripten'
endif endif
src += 'qjs_enet.c' src += 'qjs_enet.c'
deps += dependency('mimalloc') mimalloc_enabled = get_option('mimalloc')
if mimalloc_enabled
tracy_opts = ['fibers=true', 'no_exit=true', 'on_demand=true'] message('⚙ Using mimalloc subproject for static linking...')
add_project_arguments('-DTRACY_ENABLE', language:['c','cpp']) deps += dependency('mimalloc', static:true)
add_project_arguments('-DHAVE_MIMALLOC', language: ['c', 'cpp'])
# Try to find system-installed tracy first
tracy_dep = dependency('tracy', static: true, required: false)
if not tracy_dep.found()
message('⚙ System tracy not found, building subproject...')
deps += dependency('tracy', static:true, default_options:tracy_opts)
else else
deps += tracy_dep message('⚙ Mimalloc support disabled')
endif
tracy_enabled = get_option('tracy')
if tracy_enabled
message('⚙ Tracy profiling enabled')
tracy_opts = ['fibers=true', 'no_exit=true', 'on_demand=true']
add_project_arguments('-DTRACY_ENABLE', language:['c','cpp'])
# Try to find system-installed tracy first
tracy_dep = dependency('tracy', static: true, required: false)
if not tracy_dep.found()
message('⚙ System tracy not found, building subproject...')
deps += dependency('tracy', static:true, default_options:tracy_opts)
else
deps += tracy_dep
endif
else
message('⚙ Tracy profiling disabled')
endif endif
src += 'qjs_dmon.c' src += 'qjs_dmon.c'
@@ -258,13 +272,20 @@ else
deps += soloud_dep deps += soloud_dep
endif endif
# Try to find system-installed qrencode first # QR code support (optional)
qr_dep = dependency('qrencode', static: true, required: false) qrencode_enabled = get_option('qrencode')
if not qr_dep.found() if qrencode_enabled
message('⚙ System qrencode not found, building subproject...') qr_dep = dependency('qrencode', static: true, required: false)
deps += dependency('libqrencode', static:true) if not qr_dep.found()
message('⚙ System qrencode not found, building subproject...')
deps += dependency('libqrencode', static:true)
else
deps += qr_dep
endif
add_project_arguments('-DHAVE_QRENCODE', language: ['c', 'cpp'])
src += 'qjs_qr.c'
else else
deps += qr_dep message('⚙ QR code support disabled')
endif endif
# Always build for Steam unless it's Emscripten # Always build for Steam unless it's Emscripten
@@ -308,7 +329,7 @@ src += [
'anim.c', 'config.c', 'datastream.c','font.c','HandmadeMath.c','jsffi.c','model.c', 'anim.c', 'config.c', 'datastream.c','font.c','HandmadeMath.c','jsffi.c','model.c',
'render.c','simplex.c','spline.c', 'transform.c','cell.c', 'wildmatch.c', 'render.c','simplex.c','spline.c', 'transform.c','cell.c', 'wildmatch.c',
'sprite.c', 'rtree.c', 'qjs_nota.c', 'qjs_soloud.c', 'qjs_sdl.c', 'qjs_sdl_input.c', 'qjs_sdl_video.c', 'qjs_sdl_surface.c', 'qjs_math.c', 'qjs_geometry.c', 'qjs_transform.c', 'qjs_sprite.c', 'qjs_io.c', 'qjs_fd.c', 'qjs_os.c', 'qjs_actor.c', 'sprite.c', 'rtree.c', 'qjs_nota.c', 'qjs_soloud.c', 'qjs_sdl.c', 'qjs_sdl_input.c', 'qjs_sdl_video.c', 'qjs_sdl_surface.c', 'qjs_math.c', 'qjs_geometry.c', 'qjs_transform.c', 'qjs_sprite.c', 'qjs_io.c', 'qjs_fd.c', 'qjs_os.c', 'qjs_actor.c',
'qjs_qr.c', 'qjs_wota.c', 'monocypher.c', 'qjs_blob.c', 'qjs_crypto.c', 'qjs_time.c', 'qjs_http.c', 'qjs_rtree.c', 'qjs_spline.c', 'qjs_js.c', 'qjs_debug.c', 'picohttpparser.c', 'qjs_miniz.c', 'timer.c', 'qjs_socket.c', 'qjs_kim.c', 'qjs_utf8.c', 'qjs_fit.c', 'qjs_text.c', 'qjs_layout.c' 'qjs_wota.c', 'monocypher.c', 'qjs_blob.c', 'qjs_crypto.c', 'qjs_time.c', 'qjs_http.c', 'qjs_rtree.c', 'qjs_spline.c', 'qjs_js.c', 'qjs_debug.c', 'picohttpparser.c', 'qjs_miniz.c', 'timer.c', 'qjs_socket.c', 'qjs_kim.c', 'qjs_utf8.c', 'qjs_fit.c', 'qjs_text.c', 'qjs_layout.c'
] ]
# quirc src # quirc src
src += [ src += [

View File

@@ -1,3 +1,6 @@
option('editor', type:'boolean', value:true) option('editor', type:'boolean', value:true)
option('chipmunk', type:'boolean', value:true) option('chipmunk', type:'boolean', value:true)
option('storefront', type:'combo', choices:['none','steam', 'gog', 'egs'], value:'none') option('storefront', type:'combo', choices:['none','steam', 'gog', 'egs'], value:'none')
option('qrencode', type:'boolean', value:false)
option('mimalloc', type:'boolean', value:false)
option('tracy', type:'boolean', value:false)

View File

@@ -190,7 +190,8 @@ globalThis.use = function use(file, ...args) {
loadingStack.push(path) loadingStack.push(path)
// Determine the compiled file path in .cell directory // Determine the compiled file path in .cell directory
var compiledPath = ".cell/build/" + io.realdir(path) + "/" + path + '.o' var cleanPath = (io.realdir(path) + "/" + path).replace(/[:\\]/g, '/').replace(/\/+/g, '/')
var compiledPath = ".cell/build/" + cleanPath + '.o'
io.mkdir(compiledPath.dir()) io.mkdir(compiledPath.dir())

View File

@@ -11,7 +11,9 @@
#include <sys/stat.h> #include <sys/stat.h>
#include <time.h> #include <time.h>
#ifdef HAVE_MIMALLOC
#include <mimalloc.h> #include <mimalloc.h>
#endif
#ifdef __APPLE__ #ifdef __APPLE__
#include <sys/types.h> #include <sys/types.h>
@@ -185,7 +187,9 @@ void actor_free(cell_rt *actor)
SDL_UnlockMutex(actor->msg_mutex); SDL_UnlockMutex(actor->msg_mutex);
SDL_DestroyMutex(actor->msg_mutex); SDL_DestroyMutex(actor->msg_mutex);
#ifdef HAVE_MIMALLOC
mi_heap_destroy(actor->heap); mi_heap_destroy(actor->heap);
#endif
free(actor); free(actor);
SDL_LockMutex(actors_mutex); SDL_LockMutex(actors_mutex);
@@ -219,16 +223,26 @@ void *js_mi_malloc(JSMallocState *s, size_t sz) {
assert(sz != 0); assert(sz != 0);
if (unlikely(s->malloc_size + sz > s->malloc_limit)) return NULL; if (unlikely(s->malloc_size + sz > s->malloc_limit)) return NULL;
#ifdef HAVE_MIMALLOC
cell_rt *actor = (cell_rt*)s->opaque; cell_rt *actor = (cell_rt*)s->opaque;
ptr = mi_heap_malloc(actor->heap, sz); ptr = mi_heap_malloc(actor->heap, sz);
#else
ptr = malloc(sz);
#endif
if (!ptr) return NULL; if (!ptr) return NULL;
s->malloc_count++; s->malloc_count++;
s->malloc_size += js_mi_malloc_usable_size(ptr) + MALLOC_OVERHEAD; s->malloc_size += js_mi_malloc_usable_size(ptr) + MALLOC_OVERHEAD;
#ifdef TRACY_ENABLE #ifdef TRACY_ENABLE
if (tracy_profiling_enabled) if (tracy_profiling_enabled) {
#ifdef HAVE_MIMALLOC
cell_rt *actor = (cell_rt*)s->opaque;
TracyCAllocN(ptr, js_mi_malloc_usable_size(ptr) + MALLOC_OVERHEAD, actor->name); TracyCAllocN(ptr, js_mi_malloc_usable_size(ptr) + MALLOC_OVERHEAD, actor->name);
#else
TracyCAllocN(ptr, js_mi_malloc_usable_size(ptr) + MALLOC_OVERHEAD, "actor");
#endif
}
#endif #endif
return ptr; return ptr;
@@ -242,17 +256,24 @@ void js_mi_free(JSMallocState *s, void *p) {
#ifdef TRACY_ENABLE #ifdef TRACY_ENABLE
if (tracy_profiling_enabled) { if (tracy_profiling_enabled) {
#ifdef HAVE_MIMALLOC
cell_rt *actor = s->opaque; cell_rt *actor = s->opaque;
TracyCFreeN(p, actor->name); TracyCFreeN(p, actor->name);
#else
TracyCFreeN(p, "actor");
#endif
} }
#endif #endif
#ifdef HAVE_MIMALLOC
mi_free(p); mi_free(p);
#else
free(p);
#endif
} }
void *js_mi_realloc(JSMallocState *s, void *p, size_t sz) { void *js_mi_realloc(JSMallocState *s, void *p, size_t sz) {
size_t old_size; size_t old_size;
cell_rt *actor = (cell_rt*)s->opaque;
if (!p) return sz ? js_mi_malloc(s, sz) : NULL; if (!p) return sz ? js_mi_malloc(s, sz) : NULL;
@@ -261,39 +282,68 @@ void *js_mi_realloc(JSMallocState *s, void *p, size_t sz) {
s->malloc_count--; s->malloc_count--;
s->malloc_size -= old_size + MALLOC_OVERHEAD; s->malloc_size -= old_size + MALLOC_OVERHEAD;
#ifdef TRACY_ENABLE #ifdef TRACY_ENABLE
if (tracy_profiling_enabled) if (tracy_profiling_enabled) {
#ifdef HAVE_MIMALLOC
cell_rt *actor = (cell_rt*)s->opaque;
TracyCFreeN(p, actor->name); TracyCFreeN(p, actor->name);
#else
TracyCFreeN(p, "actor");
#endif #endif
}
#endif
#ifdef HAVE_MIMALLOC
mi_free(p); mi_free(p);
#else
free(p);
#endif
return NULL; return NULL;
} }
if (s->malloc_size + sz - old_size > s->malloc_limit) return NULL; if (s->malloc_size + sz - old_size > s->malloc_limit) return NULL;
#ifdef TRACY_ENABLE #ifdef TRACY_ENABLE
if (tracy_profiling_enabled) if (tracy_profiling_enabled) {
#ifdef HAVE_MIMALLOC
cell_rt *actor = (cell_rt*)s->opaque;
TracyCFreeN(p, actor->name); TracyCFreeN(p, actor->name);
#else
TracyCFreeN(p, "actor");
#endif
}
#endif #endif
#ifdef HAVE_MIMALLOC
cell_rt *actor = (cell_rt*)s->opaque;
p = mi_heap_realloc(actor->heap, p, sz); p = mi_heap_realloc(actor->heap, p, sz);
#else
p = realloc(p, sz);
#endif
if (!p) return NULL; if (!p) return NULL;
s->malloc_size += js_mi_malloc_usable_size(p) - old_size; s->malloc_size += js_mi_malloc_usable_size(p) - old_size;
#ifdef TRACY_ENABLE #ifdef TRACY_ENABLE
if (tracy_profiling_enabled) if (tracy_profiling_enabled) {
#ifdef HAVE_MIMALLOC
cell_rt *actor = (cell_rt*)s->opaque;
TracyCAllocN(p, js_mi_malloc_usable_size(p) + MALLOC_OVERHEAD, actor->name); TracyCAllocN(p, js_mi_malloc_usable_size(p) + MALLOC_OVERHEAD, actor->name);
#else
TracyCAllocN(p, js_mi_malloc_usable_size(p) + MALLOC_OVERHEAD, "actor");
#endif
}
#endif #endif
return p; return p;
} }
#ifdef HAVE_MIMALLOC
static const JSMallocFunctions mimalloc_funcs = { static const JSMallocFunctions mimalloc_funcs = {
js_mi_malloc, js_mi_malloc,
js_mi_free, js_mi_free,
js_mi_realloc, js_mi_realloc,
js_mi_malloc_usable_size js_mi_malloc_usable_size
}; };
#endif
static void free_zip(void) static void free_zip(void)
{ {
@@ -393,7 +443,9 @@ void actor_unneeded(cell_rt *actor, JSValue fn, double seconds)
cell_rt *create_actor(void *wota) cell_rt *create_actor(void *wota)
{ {
cell_rt *actor = calloc(sizeof(*actor), 1); cell_rt *actor = calloc(sizeof(*actor), 1);
#ifdef HAVE_MIMALLOC
actor->heap = mi_heap_new(); actor->heap = mi_heap_new();
#endif
actor->init_wota = wota; actor->init_wota = wota;
actor->idx_buffer = JS_NULL; actor->idx_buffer = JS_NULL;
actor->message_handle = JS_NULL; actor->message_handle = JS_NULL;
@@ -739,7 +791,11 @@ void script_startup(cell_rt *prt)
{ {
JSRuntime *rt; JSRuntime *rt;
#ifdef HAVE_MIMALLOC
rt = JS_NewRuntime2(&mimalloc_funcs, prt); rt = JS_NewRuntime2(&mimalloc_funcs, prt);
#else
rt = JS_NewRuntime();
#endif
JSContext *js = JS_NewContextRaw(rt); JSContext *js = JS_NewContextRaw(rt);
JS_SetInterruptHandler(rt, actor_interrupt_cb, prt); JS_SetInterruptHandler(rt, actor_interrupt_cb, prt);

View File

@@ -11,7 +11,9 @@
extern "C" { extern "C" {
#endif #endif
#ifdef HAVE_MIMALLOC
typedef struct mi_heap_s mi_heap_t; typedef struct mi_heap_s mi_heap_t;
#endif
/* Letter type for unified message queue */ /* Letter type for unified message queue */
typedef enum { typedef enum {
@@ -53,7 +55,9 @@ typedef struct {
typedef struct cell_rt { typedef struct cell_rt {
JSContext *context; JSContext *context;
mi_heap_t *heap; #ifdef HAVE_MIMALLOC
mi_heap_t *heap;
#endif
JSValue idx_buffer; JSValue idx_buffer;
JSValue on_exception; JSValue on_exception;
JSValue message_handle; JSValue message_handle;

View File

@@ -36,7 +36,9 @@
#include "qjs_nota.h" #include "qjs_nota.h"
#include "qjs_wota.h" #include "qjs_wota.h"
#include "qjs_soloud.h" #include "qjs_soloud.h"
#ifdef HAVE_QRENCODE
#include "qjs_qr.h" #include "qjs_qr.h"
#endif
#include "qjs_sdl.h" #include "qjs_sdl.h"
#include "qjs_sdl_video.h" #include "qjs_sdl_video.h"
#include "qjs_math.h" #include "qjs_math.h"
@@ -1635,7 +1637,9 @@ void ffi_load(JSContext *js)
arrput(rt->module_registry, ((ModuleEntry){"fd", js_fd_use})); arrput(rt->module_registry, ((ModuleEntry){"fd", js_fd_use}));
arrput(rt->module_registry, MISTLINE(socket)); arrput(rt->module_registry, MISTLINE(socket));
arrput(rt->module_registry, ((ModuleEntry){"os", js_os_use})); arrput(rt->module_registry, ((ModuleEntry){"os", js_os_use}));
#ifdef HAVE_QRENCODE
arrput(rt->module_registry, MISTLINE(qr)); arrput(rt->module_registry, MISTLINE(qr));
#endif
arrput(rt->module_registry, MISTLINE(http)); arrput(rt->module_registry, MISTLINE(http));
arrput(rt->module_registry, MISTLINE(crypto)); arrput(rt->module_registry, MISTLINE(crypto));
arrput(rt->module_registry, MISTLINE(miniz)); arrput(rt->module_registry, MISTLINE(miniz));