diff options
Diffstat (limited to 'src/lanes.cpp')
-rw-r--r-- | src/lanes.cpp | 329 |
1 files changed, 152 insertions, 177 deletions
diff --git a/src/lanes.cpp b/src/lanes.cpp index 17d4f67..3aa3365 100644 --- a/src/lanes.cpp +++ b/src/lanes.cpp | |||
@@ -101,8 +101,63 @@ THE SOFTWARE. | |||
101 | 101 | ||
102 | #include <atomic> | 102 | #include <atomic> |
103 | 103 | ||
104 | // forwarding (will do things better later) | 104 | // ################################################################################################# |
105 | static void tracking_add(Lane* lane_); | 105 | |
106 | #if HAVE_LANE_TRACKING() | ||
107 | |||
108 | // The chain is ended by '(Lane*)(-1)', not nullptr: | ||
109 | // 'tracking_first -> ... -> ... -> (-1)' | ||
110 | #define TRACKING_END ((Lane *)(-1)) | ||
111 | |||
112 | /* | ||
113 | * Add the lane to tracking chain; the ones still running at the end of the | ||
114 | * whole process will be cancelled. | ||
115 | */ | ||
116 | static void tracking_add(Lane* lane_) | ||
117 | { | ||
118 | std::lock_guard<std::mutex> guard{ lane_->U->tracking_cs }; | ||
119 | assert(lane_->tracking_next == nullptr); | ||
120 | |||
121 | lane_->tracking_next = lane_->U->tracking_first; | ||
122 | lane_->U->tracking_first = lane_; | ||
123 | } | ||
124 | |||
125 | // ################################################################################################# | ||
126 | |||
127 | /* | ||
128 | * A free-running lane has ended; remove it from tracking chain | ||
129 | */ | ||
130 | [[nodiscard]] static bool tracking_remove(Lane* lane_) | ||
131 | { | ||
132 | bool found{ false }; | ||
133 | std::lock_guard<std::mutex> guard{ lane_->U->tracking_cs }; | ||
134 | // Make sure (within the MUTEX) that we actually are in the chain | ||
135 | // still (at process exit they will remove us from chain and then | ||
136 | // cancel/kill). | ||
137 | // | ||
138 | if (lane_->tracking_next != nullptr) | ||
139 | { | ||
140 | Lane** ref = (Lane**) &lane_->U->tracking_first; | ||
141 | |||
142 | while( *ref != TRACKING_END) | ||
143 | { | ||
144 | if (*ref == lane_) | ||
145 | { | ||
146 | *ref = lane_->tracking_next; | ||
147 | lane_->tracking_next = nullptr; | ||
148 | found = true; | ||
149 | break; | ||
150 | } | ||
151 | ref = (Lane**) &((*ref)->tracking_next); | ||
152 | } | ||
153 | assert( found); | ||
154 | } | ||
155 | return found; | ||
156 | } | ||
157 | |||
158 | #endif // HAVE_LANE_TRACKING() | ||
159 | |||
160 | // ################################################################################################# | ||
106 | 161 | ||
107 | Lane::Lane(Universe* U_, lua_State* L_) | 162 | Lane::Lane(Universe* U_, lua_State* L_) |
108 | : U{ U_ } | 163 | : U{ U_ } |
@@ -180,114 +235,44 @@ static constexpr UniqueKey FINALIZER_REGKEY{ 0x188fccb8bf348e09ull }; | |||
180 | 235 | ||
181 | // ################################################################################################# | 236 | // ################################################################################################# |
182 | 237 | ||
183 | /* | 238 | Lane::~Lane() |
184 | * Push a table stored in registry onto Lua stack. | ||
185 | * | ||
186 | * If there is no existing table, create one if 'create' is true. | ||
187 | * | ||
188 | * Returns: true if a table was pushed | ||
189 | * false if no table found, not created, and nothing pushed | ||
190 | */ | ||
191 | [[nodiscard]] static bool push_registry_table(lua_State* L, UniqueKey key, bool create) | ||
192 | { | 239 | { |
193 | STACK_GROW(L, 3); | 240 | // Clean up after a (finished) thread |
194 | STACK_CHECK_START_REL(L, 0); | 241 | // |
195 | 242 | #if HAVE_LANE_TRACKING() | |
196 | key.pushValue(L); // ? | 243 | if (U->tracking_first != nullptr) |
197 | if (lua_isnil(L, -1)) // nil? | ||
198 | { | 244 | { |
199 | lua_pop(L, 1); // | 245 | // Lane was cleaned up, no need to handle at process termination |
200 | STACK_CHECK(L, 0); | 246 | std::ignore = tracking_remove(this); |
201 | |||
202 | if (!create) | ||
203 | { | ||
204 | return false; | ||
205 | } | ||
206 | |||
207 | lua_newtable(L); // t | ||
208 | key.setValue(L, [](lua_State* L) { lua_pushvalue(L, -2); }); | ||
209 | } | 247 | } |
210 | STACK_CHECK(L, 1); | 248 | #endif // HAVE_LANE_TRACKING() |
211 | return true; // table pushed | ||
212 | } | 249 | } |
213 | 250 | ||
214 | // ################################################################################################# | 251 | // ################################################################################################# |
252 | // ########################################## Finalizer ############################################ | ||
253 | // ################################################################################################# | ||
215 | 254 | ||
216 | #if HAVE_LANE_TRACKING() | ||
217 | 255 | ||
218 | // The chain is ended by '(Lane*)(-1)', not nullptr: | 256 | // Push the finalizers table on the stack. |
219 | // 'tracking_first -> ... -> ... -> (-1)' | 257 | // If there is no existing table, create ti. |
220 | #define TRACKING_END ((Lane *)(-1)) | 258 | static void push_finalizers_table(lua_State* L) |
221 | |||
222 | /* | ||
223 | * Add the lane to tracking chain; the ones still running at the end of the | ||
224 | * whole process will be cancelled. | ||
225 | */ | ||
226 | static void tracking_add(Lane* lane_) | ||
227 | { | 259 | { |
228 | std::lock_guard<std::mutex> guard{ lane_->U->tracking_cs }; | 260 | STACK_GROW(L, 3); |
229 | assert(lane_->tracking_next == nullptr); | 261 | STACK_CHECK_START_REL(L, 0); |
230 | |||
231 | lane_->tracking_next = lane_->U->tracking_first; | ||
232 | lane_->U->tracking_first = lane_; | ||
233 | } | ||
234 | |||
235 | // ################################################################################################# | ||
236 | 262 | ||
237 | /* | 263 | FINALIZER_REGKEY.pushValue(L); // ? |
238 | * A free-running lane has ended; remove it from tracking chain | 264 | if (lua_isnil(L, -1)) // nil? |
239 | */ | ||
240 | [[nodiscard]] static bool tracking_remove(Lane* lane_) | ||
241 | { | ||
242 | bool found{ false }; | ||
243 | std::lock_guard<std::mutex> guard{ lane_->U->tracking_cs }; | ||
244 | // Make sure (within the MUTEX) that we actually are in the chain | ||
245 | // still (at process exit they will remove us from chain and then | ||
246 | // cancel/kill). | ||
247 | // | ||
248 | if (lane_->tracking_next != nullptr) | ||
249 | { | 265 | { |
250 | Lane** ref = (Lane**) &lane_->U->tracking_first; | 266 | lua_pop(L, 1); // |
251 | 267 | // store a newly created table in the registry, but leave it on the stack too | |
252 | while( *ref != TRACKING_END) | 268 | lua_newtable(L); // t |
253 | { | 269 | FINALIZER_REGKEY.setValue(L, [](lua_State* L) { lua_pushvalue(L, -2); }); // t |
254 | if (*ref == lane_) | ||
255 | { | ||
256 | *ref = lane_->tracking_next; | ||
257 | lane_->tracking_next = nullptr; | ||
258 | found = true; | ||
259 | break; | ||
260 | } | ||
261 | ref = (Lane**) &((*ref)->tracking_next); | ||
262 | } | ||
263 | assert( found); | ||
264 | } | 270 | } |
265 | return found; | 271 | STACK_CHECK(L, 1); |
266 | } | 272 | } |
267 | 273 | ||
268 | #endif // HAVE_LANE_TRACKING() | ||
269 | |||
270 | // ################################################################################################# | 274 | // ################################################################################################# |
271 | 275 | ||
272 | Lane::~Lane() | ||
273 | { | ||
274 | // Clean up after a (finished) thread | ||
275 | // | ||
276 | #if HAVE_LANE_TRACKING() | ||
277 | if (U->tracking_first != nullptr) | ||
278 | { | ||
279 | // Lane was cleaned up, no need to handle at process termination | ||
280 | std::ignore = tracking_remove(this); | ||
281 | } | ||
282 | #endif // HAVE_LANE_TRACKING() | ||
283 | } | ||
284 | |||
285 | /* | ||
286 | * ############################################################################################### | ||
287 | * ########################################## Finalizer ########################################## | ||
288 | * ############################################################################################### | ||
289 | */ | ||
290 | |||
291 | //--- | 276 | //--- |
292 | // void= finalizer( finalizer_func ) | 277 | // void= finalizer( finalizer_func ) |
293 | // | 278 | // |
@@ -296,12 +281,12 @@ Lane::~Lane() | |||
296 | // Add a function that will be called when exiting the lane, either via | 281 | // Add a function that will be called when exiting the lane, either via |
297 | // normal return or an error. | 282 | // normal return or an error. |
298 | // | 283 | // |
299 | LUAG_FUNC( set_finalizer) | 284 | LUAG_FUNC(set_finalizer) |
300 | { | 285 | { |
301 | luaL_argcheck(L, lua_isfunction(L, 1), 1, "finalizer should be a function"); | 286 | luaL_argcheck(L, lua_isfunction(L, 1), 1, "finalizer should be a function"); |
302 | luaL_argcheck(L, lua_gettop( L) == 1, 1, "too many arguments"); | 287 | luaL_argcheck(L, lua_gettop( L) == 1, 1, "too many arguments"); |
303 | // Get the current finalizer table (if any), create one if it doesn't exist | 288 | // Get the current finalizer table (if any), create one if it doesn't exist |
304 | std::ignore = push_registry_table(L, FINALIZER_REGKEY, true); // finalizer {finalisers} | 289 | push_finalizers_table(L); // finalizer {finalisers} |
305 | STACK_GROW(L, 2); | 290 | STACK_GROW(L, 2); |
306 | lua_pushinteger(L, lua_rawlen(L, -1) + 1); // finalizer {finalisers} idx | 291 | lua_pushinteger(L, lua_rawlen(L, -1) + 1); // finalizer {finalisers} idx |
307 | lua_pushvalue(L, 1); // finalizer {finalisers} idx finalizer | 292 | lua_pushvalue(L, 1); // finalizer {finalisers} idx finalizer |
@@ -310,7 +295,44 @@ LUAG_FUNC( set_finalizer) | |||
310 | return 0; | 295 | return 0; |
311 | } | 296 | } |
312 | 297 | ||
298 | // ################################################################################################# | ||
299 | |||
300 | static void push_stack_trace(lua_State* L, int rc_, int stk_base_) | ||
301 | { | ||
302 | // Lua 5.1 error handler is limited to one return value; it stored the stack trace in the registry | ||
303 | switch(rc_) | ||
304 | { | ||
305 | case LUA_OK: // no error, body return values are on the stack | ||
306 | break; | ||
313 | 307 | ||
308 | case LUA_ERRRUN: // cancellation or a runtime error | ||
309 | #if ERROR_FULL_STACK // when ERROR_FULL_STACK, we installed a handler | ||
310 | { | ||
311 | STACK_CHECK_START_REL(L, 0); | ||
312 | // fetch the call stack table from the registry where the handler stored it | ||
313 | STACK_GROW(L, 1); | ||
314 | // yields nil if no stack was generated (in case of cancellation for example) | ||
315 | STACKTRACE_REGKEY.pushValue(L); // err trace|nil | ||
316 | STACK_CHECK(L, 1); | ||
317 | |||
318 | // For cancellation the error message is CANCEL_ERROR, and a stack trace isn't placed | ||
319 | // For other errors, the message can be whatever was thrown, and we should have a stack trace table | ||
320 | ASSERT_L(lua_type(L, 1 + stk_base_) == (CANCEL_ERROR.equals(L, stk_base_) ? LUA_TNIL : LUA_TTABLE)); | ||
321 | // Just leaving the stack trace table on the stack is enough to get it through to the master. | ||
322 | break; | ||
323 | } | ||
324 | #endif // fall through if not ERROR_FULL_STACK | ||
325 | |||
326 | case LUA_ERRMEM: // memory allocation error (handler not called) | ||
327 | case LUA_ERRERR: // error while running the error handler (if any, for example an out-of-memory condition) | ||
328 | default: | ||
329 | // we should have a single value which is either a string (the error message) or CANCEL_ERROR | ||
330 | ASSERT_L((lua_gettop(L) == stk_base_) && ((lua_type(L, stk_base_) == LUA_TSTRING) || CANCEL_ERROR.equals(L, stk_base_))); | ||
331 | break; | ||
332 | } | ||
333 | } | ||
334 | |||
335 | // ################################################################################################# | ||
314 | //--- | 336 | //--- |
315 | // Run finalizers - if any - with the given parameters | 337 | // Run finalizers - if any - with the given parameters |
316 | // | 338 | // |
@@ -324,43 +346,37 @@ LUAG_FUNC( set_finalizer) | |||
324 | // | 346 | // |
325 | // TBD: should we add stack trace on failing finalizer, wouldn't be hard.. | 347 | // TBD: should we add stack trace on failing finalizer, wouldn't be hard.. |
326 | // | 348 | // |
327 | static void push_stack_trace( lua_State* L, int rc_, int stk_base_); | ||
328 | 349 | ||
329 | [[nodiscard]] static int run_finalizers(lua_State* L, int lua_rc) | 350 | [[nodiscard]] static int run_finalizers(lua_State* L, int lua_rc_) |
330 | { | 351 | { |
331 | int finalizers_index; | 352 | FINALIZER_REGKEY.pushValue(L); // ... finalizers? |
332 | int n; | 353 | if (lua_isnil(L, -1)) |
333 | int err_handler_index = 0; | ||
334 | int rc = LUA_OK; // ... | ||
335 | if (!push_registry_table(L, FINALIZER_REGKEY, false)) // ... finalizers? | ||
336 | { | 354 | { |
355 | lua_pop(L, 1); | ||
337 | return 0; // no finalizers | 356 | return 0; // no finalizers |
338 | } | 357 | } |
339 | 358 | ||
340 | STACK_GROW(L, 5); | 359 | STACK_GROW(L, 5); |
341 | 360 | ||
342 | finalizers_index = lua_gettop( L); | 361 | int const finalizers_index{ lua_gettop(L) }; |
343 | 362 | int const err_handler_index{ ERROR_FULL_STACK ? (lua_pushcfunction(L, lane_error), lua_gettop(L)) : 0 }; | |
344 | #if ERROR_FULL_STACK | ||
345 | lua_pushcfunction(L, lane_error); // ... finalizers lane_error | ||
346 | err_handler_index = lua_gettop( L); | ||
347 | #endif // ERROR_FULL_STACK | ||
348 | 363 | ||
349 | for( n = (int) lua_rawlen(L, finalizers_index); n > 0; -- n) | 364 | int rc{ LUA_OK }; |
365 | for (int n = static_cast<int>(lua_rawlen(L, finalizers_index)); n > 0; --n) | ||
350 | { | 366 | { |
351 | int args = 0; | 367 | int args = 0; |
352 | lua_pushinteger(L, n); // ... finalizers lane_error n | 368 | lua_pushinteger(L, n); // ... finalizers lane_error n |
353 | lua_rawget(L, finalizers_index); // ... finalizers lane_error finalizer | 369 | lua_rawget(L, finalizers_index); // ... finalizers lane_error finalizer |
354 | ASSERT_L( lua_isfunction(L, -1)); | 370 | ASSERT_L(lua_isfunction(L, -1)); |
355 | if (lua_rc != LUA_OK) // we have an error message and an optional stack trace at the bottom of the stack | 371 | if (lua_rc_ != LUA_OK) // we have an error message and an optional stack trace at the bottom of the stack |
356 | { | 372 | { |
357 | ASSERT_L( finalizers_index == 2 || finalizers_index == 3); | 373 | ASSERT_L( finalizers_index == 2 || finalizers_index == 3); |
358 | //char const* err_msg = lua_tostring(L, 1); | 374 | //char const* err_msg = lua_tostring(L, 1); |
359 | lua_pushvalue(L, 1); // ... finalizers lane_error finalizer err_msg | 375 | lua_pushvalue(L, 1); // ... finalizers lane_error finalizer err_msg |
360 | // note we don't always have a stack trace for example when CANCEL_ERROR, or when we got an error that doesn't call our handler, such as LUA_ERRMEM | 376 | // note we don't always have a stack trace for example when CANCEL_ERROR, or when we got an error that doesn't call our handler, such as LUA_ERRMEM |
361 | if (finalizers_index == 3) | 377 | if (finalizers_index == 3) |
362 | { | 378 | { |
363 | lua_pushvalue(L, 2); // ... finalizers lane_error finalizer err_msg stack_trace | 379 | lua_pushvalue(L, 2); // ... finalizers lane_error finalizer err_msg stack_trace |
364 | } | 380 | } |
365 | args = finalizers_index - 1; | 381 | args = finalizers_index - 1; |
366 | } | 382 | } |
@@ -369,21 +385,21 @@ static void push_stack_trace( lua_State* L, int rc_, int stk_base_); | |||
369 | rc = lua_pcall(L, args, 0, err_handler_index); // ... finalizers lane_error err_msg2? | 385 | rc = lua_pcall(L, args, 0, err_handler_index); // ... finalizers lane_error err_msg2? |
370 | if (rc != LUA_OK) | 386 | if (rc != LUA_OK) |
371 | { | 387 | { |
372 | push_stack_trace(L, rc, lua_gettop( L)); | 388 | push_stack_trace(L, rc, lua_gettop(L)); |
373 | // If one finalizer fails, don't run the others. Return this | 389 | // If one finalizer fails, don't run the others. Return this |
374 | // as the 'real' error, replacing what we could have had (or not) | 390 | // as the 'real' error, replacing what we could have had (or not) |
375 | // from the actual code. | 391 | // from the actual code. |
376 | break; | 392 | break; |
377 | } | 393 | } |
378 | // no error, proceed to next finalizer // ... finalizers lane_error | 394 | // no error, proceed to next finalizer // ... finalizers lane_error |
379 | } | 395 | } |
380 | 396 | ||
381 | if (rc != LUA_OK) | 397 | if (rc != LUA_OK) |
382 | { | 398 | { |
383 | // ERROR_FULL_STACK accounts for the presence of lane_error on the stack | 399 | // ERROR_FULL_STACK accounts for the presence of lane_error on the stack |
384 | int nb_err_slots = lua_gettop( L) - finalizers_index - ERROR_FULL_STACK; | 400 | int const nb_err_slots{ lua_gettop(L) - finalizers_index - ERROR_FULL_STACK }; |
385 | // a finalizer generated an error, this is what we leave of the stack | 401 | // a finalizer generated an error, this is what we leave of the stack |
386 | for( n = nb_err_slots; n > 0; -- n) | 402 | for (int n = nb_err_slots; n > 0; --n) |
387 | { | 403 | { |
388 | lua_replace(L, n); | 404 | lua_replace(L, n); |
389 | } | 405 | } |
@@ -399,9 +415,9 @@ static void push_stack_trace( lua_State* L, int rc_, int stk_base_); | |||
399 | } | 415 | } |
400 | 416 | ||
401 | /* | 417 | /* |
402 | * ############################################################################################### | 418 | * ################################################################################################ |
403 | * ########################################### Threads ########################################### | 419 | * ########################################### Threads ############################################ |
404 | * ############################################################################################### | 420 | * ################################################################################################ |
405 | */ | 421 | */ |
406 | 422 | ||
407 | // | 423 | // |
@@ -425,7 +441,7 @@ static void selfdestruct_add(Lane* lane_) | |||
425 | lane_->U->selfdestruct_first = lane_; | 441 | lane_->U->selfdestruct_first = lane_; |
426 | } | 442 | } |
427 | 443 | ||
428 | // ############################################################################################### | 444 | // ################################################################################################# |
429 | 445 | ||
430 | /* | 446 | /* |
431 | * A free-running lane has ended; remove it from selfdestruct chain | 447 | * A free-running lane has ended; remove it from selfdestruct chain |
@@ -460,7 +476,7 @@ static void selfdestruct_add(Lane* lane_) | |||
460 | return found; | 476 | return found; |
461 | } | 477 | } |
462 | 478 | ||
463 | // ############################################################################################### | 479 | // ################################################################################################# |
464 | 480 | ||
465 | /* | 481 | /* |
466 | * Process end; cancel any still free-running threads | 482 | * Process end; cancel any still free-running threads |
@@ -567,7 +583,7 @@ static void selfdestruct_add(Lane* lane_) | |||
567 | return 0; | 583 | return 0; |
568 | } | 584 | } |
569 | 585 | ||
570 | // ############################################################################################### | 586 | // ################################################################################################# |
571 | 587 | ||
572 | //--- | 588 | //--- |
573 | // = _single( [cores_uint=1] ) | 589 | // = _single( [cores_uint=1] ) |
@@ -597,7 +613,7 @@ LUAG_FUNC( set_singlethreaded) | |||
597 | #endif | 613 | #endif |
598 | } | 614 | } |
599 | 615 | ||
600 | // ############################################################################################### | 616 | // ################################################################################################# |
601 | 617 | ||
602 | /* | 618 | /* |
603 | * str= lane_error( error_val|str ) | 619 | * str= lane_error( error_val|str ) |
@@ -710,41 +726,6 @@ LUAG_FUNC( set_error_reporting) | |||
710 | } | 726 | } |
711 | #endif // ERROR_FULL_STACK | 727 | #endif // ERROR_FULL_STACK |
712 | 728 | ||
713 | static void push_stack_trace( lua_State* L, int rc_, int stk_base_) | ||
714 | { | ||
715 | // Lua 5.1 error handler is limited to one return value; it stored the stack trace in the registry | ||
716 | switch( rc_) | ||
717 | { | ||
718 | case LUA_OK: // no error, body return values are on the stack | ||
719 | break; | ||
720 | |||
721 | case LUA_ERRRUN: // cancellation or a runtime error | ||
722 | #if ERROR_FULL_STACK // when ERROR_FULL_STACK, we installed a handler | ||
723 | { | ||
724 | STACK_CHECK_START_REL(L, 0); | ||
725 | // fetch the call stack table from the registry where the handler stored it | ||
726 | STACK_GROW(L, 1); | ||
727 | // yields nil if no stack was generated (in case of cancellation for example) | ||
728 | STACKTRACE_REGKEY.pushValue(L); // err trace|nil | ||
729 | STACK_CHECK(L, 1); | ||
730 | |||
731 | // For cancellation the error message is CANCEL_ERROR, and a stack trace isn't placed | ||
732 | // For other errors, the message can be whatever was thrown, and we should have a stack trace table | ||
733 | ASSERT_L(lua_type(L, 1 + stk_base_) == (CANCEL_ERROR.equals(L, stk_base_) ? LUA_TNIL : LUA_TTABLE)); | ||
734 | // Just leaving the stack trace table on the stack is enough to get it through to the master. | ||
735 | break; | ||
736 | } | ||
737 | #endif // fall through if not ERROR_FULL_STACK | ||
738 | |||
739 | case LUA_ERRMEM: // memory allocation error (handler not called) | ||
740 | case LUA_ERRERR: // error while running the error handler (if any, for example an out-of-memory condition) | ||
741 | default: | ||
742 | // we should have a single value which is either a string (the error message) or CANCEL_ERROR | ||
743 | ASSERT_L((lua_gettop(L) == stk_base_) && ((lua_type(L, stk_base_) == LUA_TSTRING) || CANCEL_ERROR.equals(L, stk_base_))); | ||
744 | break; | ||
745 | } | ||
746 | } | ||
747 | |||
748 | // ################################################################################################# | 729 | // ################################################################################################# |
749 | 730 | ||
750 | LUAG_FUNC(set_debug_threadname) | 731 | LUAG_FUNC(set_debug_threadname) |
@@ -772,7 +753,7 @@ LUAG_FUNC(set_debug_threadname) | |||
772 | 753 | ||
773 | LUAG_FUNC(get_debug_threadname) | 754 | LUAG_FUNC(get_debug_threadname) |
774 | { | 755 | { |
775 | Lane* const lane{ lua_toLane(L, 1) }; | 756 | Lane* const lane{ ToLane(L, 1) }; |
776 | luaL_argcheck(L, lua_gettop(L) == 1, 2, "too many arguments"); | 757 | luaL_argcheck(L, lua_gettop(L) == 1, 2, "too many arguments"); |
777 | lua_pushstring(L, lane->debug_name); | 758 | lua_pushstring(L, lane->debug_name); |
778 | return 1; | 759 | return 1; |
@@ -828,8 +809,7 @@ static struct errcode_name s_errcodes[] = | |||
828 | }; | 809 | }; |
829 | static char const* get_errcode_name( int _code) | 810 | static char const* get_errcode_name( int _code) |
830 | { | 811 | { |
831 | int i; | 812 | for (int i{ 0 }; i < 7; ++i) |
832 | for( i = 0; i < 7; ++ i) | ||
833 | { | 813 | { |
834 | if (s_errcodes[i].code == _code) | 814 | if (s_errcodes[i].code == _code) |
835 | { | 815 | { |
@@ -891,7 +871,6 @@ static void lane_main(Lane* lane) | |||
891 | push_stack_trace(L, rc, 1); // retvals|error [trace] | 871 | push_stack_trace(L, rc, 1); // retvals|error [trace] |
892 | 872 | ||
893 | DEBUGSPEW_CODE(fprintf(stderr, INDENT_BEGIN "Lane %p body: %s (%s)\n" INDENT_END, L, get_errcode_name(rc), CANCEL_ERROR.equals(L, 1) ? "cancelled" : lua_typename(L, lua_type(L, 1)))); | 873 | DEBUGSPEW_CODE(fprintf(stderr, INDENT_BEGIN "Lane %p body: %s (%s)\n" INDENT_END, L, get_errcode_name(rc), CANCEL_ERROR.equals(L, 1) ? "cancelled" : lua_typename(L, lua_type(L, 1)))); |
894 | // STACK_DUMP(L); | ||
895 | // Call finalizers, if the script has set them up. | 874 | // Call finalizers, if the script has set them up. |
896 | // | 875 | // |
897 | int rc2{ run_finalizers(L, rc) }; | 876 | int rc2{ run_finalizers(L, rc) }; |
@@ -1295,7 +1274,7 @@ LUAG_FUNC(lane_new) | |||
1295 | [[nodiscard]] static int lane_gc(lua_State* L) | 1274 | [[nodiscard]] static int lane_gc(lua_State* L) |
1296 | { | 1275 | { |
1297 | bool have_gc_cb{ false }; | 1276 | bool have_gc_cb{ false }; |
1298 | Lane* const lane{ lua_toLane(L, 1) }; // ud | 1277 | Lane* const lane{ ToLane(L, 1) }; // ud |
1299 | 1278 | ||
1300 | // if there a gc callback? | 1279 | // if there a gc callback? |
1301 | lua_getiuservalue(L, 1, 1); // ud uservalue | 1280 | lua_getiuservalue(L, 1, 1); // ud uservalue |
@@ -1393,7 +1372,7 @@ void push_thread_status(lua_State* L, Lane* lane_) | |||
1393 | // | 1372 | // |
1394 | LUAG_FUNC(thread_join) | 1373 | LUAG_FUNC(thread_join) |
1395 | { | 1374 | { |
1396 | Lane* const lane{ lua_toLane(L, 1) }; | 1375 | Lane* const lane{ ToLane(L, 1) }; |
1397 | lua_Duration const duration{ luaL_optnumber(L, 2, -1.0) }; | 1376 | lua_Duration const duration{ luaL_optnumber(L, 2, -1.0) }; |
1398 | lua_State* const L2{ lane->L }; | 1377 | lua_State* const L2{ lane->L }; |
1399 | 1378 | ||
@@ -1474,7 +1453,7 @@ LUAG_FUNC(thread_index) | |||
1474 | static constexpr int UD{ 1 }; | 1453 | static constexpr int UD{ 1 }; |
1475 | static constexpr int KEY{ 2 }; | 1454 | static constexpr int KEY{ 2 }; |
1476 | static constexpr int USR{ 3 }; | 1455 | static constexpr int USR{ 3 }; |
1477 | Lane* const lane{ lua_toLane(L, UD) }; | 1456 | Lane* const lane{ ToLane(L, UD) }; |
1478 | ASSERT_L(lua_gettop(L) == 2); | 1457 | ASSERT_L(lua_gettop(L) == 2); |
1479 | 1458 | ||
1480 | STACK_GROW(L, 8); // up to 8 positions are needed in case of error propagation | 1459 | STACK_GROW(L, 8); // up to 8 positions are needed in case of error propagation |
@@ -1647,11 +1626,9 @@ LUAG_FUNC(threads) | |||
1647 | } | 1626 | } |
1648 | #endif // HAVE_LANE_TRACKING() | 1627 | #endif // HAVE_LANE_TRACKING() |
1649 | 1628 | ||
1650 | /* | 1629 | // ################################################################################################# |
1651 | * ############################################################################################### | 1630 | // ######################################## Timer support ########################################## |
1652 | * ######################################## Timer support ######################################## | 1631 | // ################################################################################################# |
1653 | * ############################################################################################### | ||
1654 | */ | ||
1655 | 1632 | ||
1656 | /* | 1633 | /* |
1657 | * secs = now_secs() | 1634 | * secs = now_secs() |
@@ -1722,11 +1699,9 @@ LUAG_FUNC(wakeup_conv) | |||
1722 | return 1; | 1699 | return 1; |
1723 | } | 1700 | } |
1724 | 1701 | ||
1725 | /* | 1702 | // ################################################################################################# |
1726 | * ############################################################################################### | 1703 | // ######################################## Module linkage ######################################### |
1727 | * ######################################## Module linkage ####################################### | 1704 | // ################################################################################################# |
1728 | * ############################################################################################### | ||
1729 | */ | ||
1730 | 1705 | ||
1731 | extern int LG_linda(lua_State* L); | 1706 | extern int LG_linda(lua_State* L); |
1732 | static struct luaL_Reg const lanes_functions[] = | 1707 | static struct luaL_Reg const lanes_functions[] = |