aboutsummaryrefslogtreecommitdiff
path: root/src/tools.c
diff options
context:
space:
mode:
authordptr1988 <junk_mail@dptr1988.mooo.com>2011-01-19 17:43:07 -0800
committerdptr1988 <junk_mail@dptr1988.mooo.com>2011-01-19 17:43:07 -0800
commit8ce207a848429e8581e8a900b645927f86e78435 (patch)
treec0eaced5fb675e25e697bb9ecc91326888c20f8d /src/tools.c
parent088834240ba6304ae930494e1be5f0c987c3c361 (diff)
downloadlanes-8ce207a848429e8581e8a900b645927f86e78435.tar.gz
lanes-8ce207a848429e8581e8a900b645927f86e78435.tar.bz2
lanes-8ce207a848429e8581e8a900b645927f86e78435.zip
Changed luaG_push_proxy to cache deep userdata proxies.
Diffstat (limited to 'src/tools.c')
-rw-r--r--src/tools.c49
1 files changed, 46 insertions, 3 deletions
diff --git a/src/tools.c b/src/tools.c
index 2f3140d..6692890 100644
--- a/src/tools.c
+++ b/src/tools.c
@@ -188,6 +188,13 @@ const char *luaG_openlibs( lua_State *L, const char *libs ) {
188#define DEEP_LOOKUP_KEY ((void*)set_deep_lookup) 188#define DEEP_LOOKUP_KEY ((void*)set_deep_lookup)
189 // any unique light userdata 189 // any unique light userdata
190 190
191
192/*
193* The deep proxy cache is a weak valued table listing all deep UD proxies indexed by the deep UD that they are proxying
194*/
195#define DEEP_PROXY_CACHE_KEY ((void*)luaG_push_proxy)
196
197static void push_registry_subtable_mode( lua_State *L, void *token, const char* mode );
191static void push_registry_subtable( lua_State *L, void *token ); 198static void push_registry_subtable( lua_State *L, void *token );
192 199
193/* 200/*
@@ -350,6 +357,18 @@ int deep_userdata_gc( lua_State *L ) {
350void luaG_push_proxy( lua_State *L, lua_CFunction idfunc, DEEP_PRELUDE *prelude ) { 357void luaG_push_proxy( lua_State *L, lua_CFunction idfunc, DEEP_PRELUDE *prelude ) {
351 DEEP_PRELUDE **proxy; 358 DEEP_PRELUDE **proxy;
352 359
360 // Check if a proxy already exists
361 push_registry_subtable_mode(L, DEEP_PROXY_CACHE_KEY, "v");
362 lua_pushlightuserdata(L, prelude->deep);
363 lua_rawget(L, -2);
364 if (!lua_isnil(L, -1)) {
365 lua_remove(L, -2); // deep proxy cache table
366 return;
367 } else {
368 lua_pop(L, 2); // Pop the nil and proxy cache table
369 }
370
371
353 MUTEX_LOCK( &deep_lock ); 372 MUTEX_LOCK( &deep_lock );
354 ++(prelude->refcount); // one more proxy pointing to this deep data 373 ++(prelude->refcount); // one more proxy pointing to this deep data
355 MUTEX_UNLOCK( &deep_lock ); 374 MUTEX_UNLOCK( &deep_lock );
@@ -413,6 +432,13 @@ void luaG_push_proxy( lua_State *L, lua_CFunction idfunc, DEEP_PRELUDE *prelude
413 432
414 lua_setmetatable( L, -2 ); 433 lua_setmetatable( L, -2 );
415 434
435 // If we're here, we obviously had to create a new proxy, so cache it.
436 push_registry_subtable_mode(L, DEEP_PROXY_CACHE_KEY, "v");
437 lua_pushlightuserdata(L, (*proxy)->deep);
438 lua_pushvalue(L, -3); // Copy of the proxy
439 lua_rawset(L, -3);
440 lua_pop(L, 1); // Remove the cache proxy table
441
416 STACK_END(L,1) 442 STACK_END(L,1)
417 // [-1]: proxy userdata 443 // [-1]: proxy userdata
418} 444}
@@ -544,11 +570,10 @@ lua_CFunction luaG_copydeep( lua_State *L, lua_State *L2, int index ) {
544 */ 570 */
545 571
546/* 572/*
547* Push a registry subtable (keyed by unique 'token') onto the stack. 573* Does what the original 'push_registry_subtable' function did, but adds an optional mode argument to it
548* If the subtable does not exist, it is created and chained.
549*/ 574*/
550static 575static
551void push_registry_subtable( lua_State *L, void *token ) { 576void push_registry_subtable_mode( lua_State *L, void *token, const char* mode ) {
552 577
553 STACK_GROW(L,3); 578 STACK_GROW(L,3);
554 579
@@ -570,12 +595,30 @@ void push_registry_subtable( lua_State *L, void *token ) {
570 // [-1]: value 595 // [-1]: value
571 596
572 lua_rawset( L, LUA_REGISTRYINDEX ); 597 lua_rawset( L, LUA_REGISTRYINDEX );
598
599 // Set it's metatable if requested
600 if (mode) {
601 lua_newtable(L);
602 lua_pushliteral(L, "__mode");
603 lua_pushstring(L, mode);
604 lua_rawset(L, -3);
605 lua_setmetatable(L, -2);
606 }
573 } 607 }
574 STACK_END(L,1) 608 STACK_END(L,1)
575 609
576 ASSERT_L( lua_istable(L,-1) ); 610 ASSERT_L( lua_istable(L,-1) );
577} 611}
578 612
613/*
614* Push a registry subtable (keyed by unique 'token') onto the stack.
615* If the subtable does not exist, it is created and chained.
616*/
617static
618void push_registry_subtable( lua_State *L, void *token ) {
619 push_registry_subtable_mode(L, token, NULL);
620}
621
579#define REG_MTID ( (void*) get_mt_id ) 622#define REG_MTID ( (void*) get_mt_id )
580 623
581/* 624/*