diff options
author | Benoit Germain <bnt period germain arrobase gmail period com> | 2014-02-18 09:56:23 +0100 |
---|---|---|
committer | Benoit Germain <bnt period germain arrobase gmail period com> | 2014-02-18 09:56:23 +0100 |
commit | 48517ca661895a0c70093e78f165866cb9363206 (patch) | |
tree | a440e16a69b0a85cdb5663ba181a1c3ac2bf0bc5 /src/tools.c | |
parent | 5f092fe0ec8b6942c63262e7c14c7e4ba913b023 (diff) | |
download | lanes-48517ca661895a0c70093e78f165866cb9363206.tar.gz lanes-48517ca661895a0c70093e78f165866cb9363206.tar.bz2 lanes-48517ca661895a0c70093e78f165866cb9363206.zip |
Lanes init crash fix
* bumped version to 3.9.1
* keeper array is allocated with master state's alloc function instead
of malloc()/free()
* prevent application crash when specifying a very large number of
keepers in the configuration options
* removed some keeper desinit legacy dead code
* any error occuring during one-time inits is raised outside the
one-time mutex protected code region
Diffstat (limited to 'src/tools.c')
-rw-r--r-- | src/tools.c | 33 |
1 files changed, 22 insertions, 11 deletions
diff --git a/src/tools.c b/src/tools.c index 2aa9b82..d149f9b 100644 --- a/src/tools.c +++ b/src/tools.c | |||
@@ -591,7 +591,7 @@ void populate_func_lookup_table( lua_State* L, int _i, char const* name_) | |||
591 | DEBUGSPEW_CODE( -- debugspew_indent_depth); | 591 | DEBUGSPEW_CODE( -- debugspew_indent_depth); |
592 | } | 592 | } |
593 | 593 | ||
594 | void call_on_state_create( lua_State* L, lua_State* from_, enum eLookupMode mode_) | 594 | int call_on_state_create( lua_State* L, lua_State* from_, enum eLookupMode mode_) |
595 | { | 595 | { |
596 | if( s_on_state_create_func != NULL) | 596 | if( s_on_state_create_func != NULL) |
597 | { | 597 | { |
@@ -607,7 +607,8 @@ void call_on_state_create( lua_State* L, lua_State* from_, enum eLookupMode mode | |||
607 | if( mode_ != eLM_LaneBody) | 607 | if( mode_ != eLM_LaneBody) |
608 | { | 608 | { |
609 | // if attempting to call in a keeper state, do nothing because the function doesn't exist there | 609 | // if attempting to call in a keeper state, do nothing because the function doesn't exist there |
610 | return; | 610 | // this doesn't count as an error though |
611 | return 0; | ||
611 | } | 612 | } |
612 | lua_getfield( L, LUA_REGISTRYINDEX, CONFIG_REGKEY); | 613 | lua_getfield( L, LUA_REGISTRYINDEX, CONFIG_REGKEY); |
613 | lua_getfield( L, -1, "on_state_create"); | 614 | lua_getfield( L, -1, "on_state_create"); |
@@ -616,10 +617,12 @@ void call_on_state_create( lua_State* L, lua_State* from_, enum eLookupMode mode | |||
616 | // capture error and forward it to main state | 617 | // capture error and forward it to main state |
617 | if( lua_pcall( L, 0, 0, 0) != LUA_OK) | 618 | if( lua_pcall( L, 0, 0, 0) != LUA_OK) |
618 | { | 619 | { |
619 | (void) luaL_error( from_, "on_state_create failed: \"%s\"", lua_isstring( L, -1) ? lua_tostring( L, -1) : lua_typename( L, lua_type( L, -1))); | 620 | lua_pushfstring( from_, "on_state_create failed: \"%s\"", lua_isstring( L, -1) ? lua_tostring( L, -1) : lua_typename( L, lua_type( L, -1))); |
621 | return 1; | ||
620 | } | 622 | } |
621 | STACK_END( L, 0); | 623 | STACK_END( L, 0); |
622 | } | 624 | } |
625 | return 0; | ||
623 | } | 626 | } |
624 | 627 | ||
625 | /* | 628 | /* |
@@ -637,7 +640,7 @@ void call_on_state_create( lua_State* L, lua_State* from_, enum eLookupMode mode | |||
637 | */ | 640 | */ |
638 | lua_State* luaG_newstate( lua_State* from_, char const* libs_) | 641 | lua_State* luaG_newstate( lua_State* from_, char const* libs_) |
639 | { | 642 | { |
640 | // reuse alloc function from the originating state | 643 | // re-use alloc function from the originating state |
641 | #if PROPAGATE_ALLOCF | 644 | #if PROPAGATE_ALLOCF |
642 | PROPAGATE_ALLOCF_PREP( from_); | 645 | PROPAGATE_ALLOCF_PREP( from_); |
643 | #endif // PROPAGATE_ALLOCF | 646 | #endif // PROPAGATE_ALLOCF |
@@ -648,7 +651,7 @@ lua_State* luaG_newstate( lua_State* from_, char const* libs_) | |||
648 | (void) luaL_error( from_, "luaG_newstate() failed while creating state; out of memory"); | 651 | (void) luaL_error( from_, "luaG_newstate() failed while creating state; out of memory"); |
649 | } | 652 | } |
650 | 653 | ||
651 | // we'll need this everytime we transfer some C function from/to this state | 654 | // we'll need this every time we transfer some C function from/to this state |
652 | lua_newtable( L); | 655 | lua_newtable( L); |
653 | lua_setfield( L, LUA_REGISTRYINDEX, LOOKUP_REGKEY); | 656 | lua_setfield( L, LUA_REGISTRYINDEX, LOOKUP_REGKEY); |
654 | 657 | ||
@@ -720,7 +723,11 @@ lua_State* luaG_newstate( lua_State* from_, char const* libs_) | |||
720 | lua_gc( L, LUA_GCRESTART, 0); | 723 | lua_gc( L, LUA_GCRESTART, 0); |
721 | 724 | ||
722 | // call this after the base libraries are loaded and GC is restarted | 725 | // call this after the base libraries are loaded and GC is restarted |
723 | call_on_state_create( L, from_, eLM_LaneBody); | 726 | if( call_on_state_create( L, from_, eLM_LaneBody)) |
727 | { | ||
728 | // if something went wrong, the error message is pushed on the stack | ||
729 | lua_error( from_); | ||
730 | } | ||
724 | 731 | ||
725 | STACK_CHECK( L); | 732 | STACK_CHECK( L); |
726 | // after all this, register everything we find in our name<->function database | 733 | // after all this, register everything we find in our name<->function database |
@@ -2158,17 +2165,20 @@ int luaG_inter_move( lua_State* L, lua_State* L2, uint_t n, enum eLookupMode mod | |||
2158 | return ret; | 2165 | return ret; |
2159 | } | 2166 | } |
2160 | 2167 | ||
2161 | void luaG_inter_copy_package( lua_State* L, lua_State* L2, int _idx, enum eLookupMode mode_) | 2168 | int luaG_inter_copy_package( lua_State* L, lua_State* L2, int package_idx_, enum eLookupMode mode_) |
2162 | { | 2169 | { |
2163 | DEBUGSPEW_CODE( fprintf( stderr, INDENT_BEGIN "luaG_inter_copy_package()\n" INDENT_END)); | 2170 | DEBUGSPEW_CODE( fprintf( stderr, INDENT_BEGIN "luaG_inter_copy_package()\n" INDENT_END)); |
2164 | DEBUGSPEW_CODE( ++ debugspew_indent_depth); | 2171 | DEBUGSPEW_CODE( ++ debugspew_indent_depth); |
2165 | // package | 2172 | // package |
2166 | STACK_CHECK( L); | 2173 | STACK_CHECK( L); |
2167 | STACK_CHECK( L2); | 2174 | STACK_CHECK( L2); |
2168 | _idx = lua_absindex( L, _idx); | 2175 | package_idx_ = lua_absindex( L, package_idx_); |
2169 | if( lua_type( L, _idx) != LUA_TTABLE) | 2176 | if( lua_type( L, package_idx_) != LUA_TTABLE) |
2170 | { | 2177 | { |
2171 | (void) luaL_error( L, "expected package as table, got %s", luaL_typename( L, _idx)); | 2178 | lua_pushfstring( L, "expected package as table, got %s", luaL_typename( L, package_idx_)); |
2179 | STACK_MID( L, 1); | ||
2180 | // raise the error when copying from lane to lane, else just leave it on the stack to be raised later | ||
2181 | return ( mode_ == eLM_LaneBody) ? lua_error( L) : 1; | ||
2172 | } | 2182 | } |
2173 | lua_getglobal( L2, "package"); | 2183 | lua_getglobal( L2, "package"); |
2174 | if( !lua_isnil( L2, -1)) // package library not loaded: do nothing | 2184 | if( !lua_isnil( L2, -1)) // package library not loaded: do nothing |
@@ -2182,7 +2192,7 @@ void luaG_inter_copy_package( lua_State* L, lua_State* L2, int _idx, enum eLooku | |||
2182 | for( i = 0; entries[i]; ++ i) | 2192 | for( i = 0; entries[i]; ++ i) |
2183 | { | 2193 | { |
2184 | DEBUGSPEW_CODE( fprintf( stderr, INDENT_BEGIN "%s\n" INDENT_END, entries[i])); | 2194 | DEBUGSPEW_CODE( fprintf( stderr, INDENT_BEGIN "%s\n" INDENT_END, entries[i])); |
2185 | lua_getfield( L, _idx, entries[i]); | 2195 | lua_getfield( L, package_idx_, entries[i]); |
2186 | if( lua_isnil( L, -1)) | 2196 | if( lua_isnil( L, -1)) |
2187 | { | 2197 | { |
2188 | lua_pop( L, 1); | 2198 | lua_pop( L, 1); |
@@ -2204,6 +2214,7 @@ void luaG_inter_copy_package( lua_State* L, lua_State* L2, int _idx, enum eLooku | |||
2204 | STACK_END( L2, 0); | 2214 | STACK_END( L2, 0); |
2205 | STACK_END( L, 0); | 2215 | STACK_END( L, 0); |
2206 | DEBUGSPEW_CODE( -- debugspew_indent_depth); | 2216 | DEBUGSPEW_CODE( -- debugspew_indent_depth); |
2217 | return 0; | ||
2207 | } | 2218 | } |
2208 | 2219 | ||
2209 | 2220 | ||