aboutsummaryrefslogtreecommitdiff
path: root/unit_tests/init_and_shutdown.cpp
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--unit_tests/init_and_shutdown.cpp962
1 files changed, 534 insertions, 428 deletions
diff --git a/unit_tests/init_and_shutdown.cpp b/unit_tests/init_and_shutdown.cpp
index 7e4c215..69e4f1b 100644
--- a/unit_tests/init_and_shutdown.cpp
+++ b/unit_tests/init_and_shutdown.cpp
@@ -3,7 +3,7 @@
3 3
4// ################################################################################################# 4// #################################################################################################
5 5
6TEST_CASE("lanes.require 'lanes'") 6TEST_CASE("Lua.require_lanes")
7{ 7{
8 LuaState L{ LuaState::WithBaseLibs{ false }, LuaState::WithFixture{ false } }; 8 LuaState L{ LuaState::WithBaseLibs{ false }, LuaState::WithFixture{ false } };
9 9
@@ -56,612 +56,717 @@ TEST_CASE("lanes.require 'lanes'")
56} 56}
57 57
58// ################################################################################################# 58// #################################################################################################
59// ################################################################################################# 59
60// allocator should be "protected", a C function returning a suitable userdata, or nil 60// allocator should be "protected", a C function returning a suitable userdata, or nil
61TEST_CASE("lanes.configure.allocator/bool_number_table_string")
62{
63 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
64
65 SECTION("allocator = false")
66 {
67 L.requireFailure("require 'lanes'.configure{allocator = false}");
68 }
69
70 // ---------------------------------------------------------------------------------------------
71
72 SECTION("allocator = true")
73 {
74 L.requireFailure("require 'lanes'.configure{allocator = true}");
75 }
76
77 // ---------------------------------------------------------------------------------------------
78
79 SECTION("allocator = <number>")
80 {
81 L.requireFailure("require 'lanes'.configure{allocator = 33}");
82 }
83
84 // ---------------------------------------------------------------------------------------------
85
86 SECTION("allocator = <table>")
87 {
88 L.requireFailure("require 'lanes'.configure{allocator = {}}");
89 }
90
91 // ---------------------------------------------------------------------------------------------
92
93 SECTION("allocator = <string with a typo>")
94 {
95 // oops, a typo
96 L.requireFailure("require 'lanes'.configure{allocator = 'Protected'}");
97 }
98}
99
100// #################################################################################################
61 101
62TEST_CASE("lanes.configure") 102TEST_CASE("lanes.configure.allocator/bad_functions")
63{ 103{
64 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } }; 104 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
65 105
66 // --------------------------------------------------------------------------------------------- 106 // ---------------------------------------------------------------------------------------------
67 107
68 SECTION("allocator", "[allocator]") 108 SECTION("allocator = <Lua function>")
69 { 109 {
70 SECTION("allocator = false") 110 L.requireFailure("require 'lanes'.configure{allocator = function() return {}, 12, 'yoy' end}");
71 { 111 }
72 L.requireFailure("require 'lanes'.configure{allocator = false}");
73 }
74 112
75 // ----------------------------------------------------------------------------------------- 113 // ---------------------------------------------------------------------------------------------
76 114
77 SECTION("allocator = true") 115 SECTION("allocator = <bad C function>")
78 { 116 {
79 L.requireFailure("require 'lanes'.configure{allocator = true}"); 117 // a C function that doesn't return what we expect should cause an error too
80 } 118 // TODO: for some reason, we use os.getenv here because using 'print' as the culprit, the tests deadlock in Release builds
119 L.requireFailure("return type(require 'lanes'.configure{allocator = os.getenv})");
120 }
81 121
82 // ----------------------------------------------------------------------------------------- 122 // ---------------------------------------------------------------------------------------------
83 123
84 SECTION("allocator = <number>") 124 SECTION("allocator not returning an AllocatorDefinition")
85 { 125 {
86 L.requireFailure("require 'lanes'.configure{allocator = 33}"); 126 // a function that provides something that is definitely not an AllocatorDefinition, should cause an error
87 } 127 static constexpr lua_CFunction _provideAllocator = +[](lua_State* const L_) {
128 lua_newtable(L_);
129 return 1;
130 };
131 lua_pushcfunction(L, _provideAllocator);
132 lua_setglobal(L, "ProvideAllocator");
133 // force value of internal_allocator so that the LuaJIT-default 'libc' is not selected
134 // which would prevent us from calling _provideAllocator
135 L.requireFailure("require 'lanes'.configure{allocator = ProvideAllocator, internal_allocator = 'allocator'}");
136 }
88 137
89 // ----------------------------------------------------------------------------------------- 138 // ---------------------------------------------------------------------------------------------
90 139
91 SECTION("allocator = <table>") 140 SECTION("allocator returning an AllocatorDefinition with the wrong signature")
92 { 141 {
93 L.requireFailure("require 'lanes'.configure{allocator = {}}"); 142 // a function that provides something that is too small to contain an AllocatorDefinition, should cause an error
94 } 143 static constexpr lua_CFunction _provideAllocator = +[](lua_State* const L_) {
144 // create a full userdata that is too small (it only contains enough to store a version tag, but not the rest
145 auto* const _duck{ static_cast<lanes::AllocatorDefinition::version_t*>(lua_newuserdata(L_, sizeof(lanes::AllocatorDefinition::version_t))) };
146 *_duck = 666777;
147 return 1;
148 };
149 lua_pushcfunction(L, _provideAllocator);
150 lua_setglobal(L, "ProvideAllocator");
151 // force value of internal_allocator so that the LuaJIT-default 'libc' is not selected
152 // which would prevent us from calling _provideAllocator
153 L.requireFailure("require 'lanes'.configure{allocator = ProvideAllocator, internal_allocator = 'allocator'}");
154 }
95 155
96 // ----------------------------------------------------------------------------------------- 156 // -----------------------------------------------------------------------------------------
97 157
98 SECTION("allocator = <Lua function>") 158 SECTION("allocator returning something too small to be a valid AllocatorDefinition")
99 { 159 {
100 L.requireFailure("require 'lanes'.configure{allocator = function() return {}, 12, 'yoy' end}"); 160 // a function that provides something that attempts to pass as an AllocatorDefinition, but is not, should cause an error
101 } 161 static constexpr lua_CFunction _provideAllocator = +[](lua_State* const L_) {
162 // create a full userdata of the correct size, but of course the contents don't match
163 int* const _duck{ static_cast<int*>(lua_newuserdata(L_, sizeof(lanes::AllocatorDefinition))) };
164 _duck[0] = 666;
165 _duck[1] = 777;
166 return 1;
167 };
168 lua_pushcfunction(L, _provideAllocator);
169 lua_setglobal(L, "ProvideAllocator");
170 // force value of internal_allocator so that the LuaJIT-default 'libc' is not selected
171 // which would prevent us from calling _provideAllocator
172 L.requireFailure("require 'lanes'.configure{allocator = ProvideAllocator, internal_allocator = 'allocator'}");
173 }
174}
102 175
103 // ----------------------------------------------------------------------------------------- 176// #################################################################################################
104 177
105 SECTION("allocator = <bad C function>") 178TEST_CASE("lanes.configure.allocator/good_function")
106 { 179{
107 // a C function that doesn't return what we expect should cause an error too 180 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
108 L.requireFailure("require 'lanes'.configure{allocator = print}");
109 }
110 181
111 // ----------------------------------------------------------------------------------------- 182 SECTION("allocator = <good custom C allocator>")
183 {
184 // a function that provides what we expect is fine
185 static constexpr lua_CFunction _provideAllocator = +[](lua_State* const L_) {
186 lanes::AllocatorDefinition* const _def{ new (L_) lanes::AllocatorDefinition{} };
187 _def->initFrom(L_);
188 return 1;
189 };
190 lua_pushcfunction(L, _provideAllocator);
191 lua_setglobal(L, "ProvideAllocator");
192 L.requireSuccess("require 'lanes'.configure{allocator = ProvideAllocator}");
193 }
194}
112 195
113 SECTION("allocator = <string with a typo>") 196// #################################################################################################
114 {
115 // oops, a typo
116 L.requireFailure("require 'lanes'.configure{allocator = 'Protected'}");
117 }
118 197
119 // ----------------------------------------------------------------------------------------- 198// TODO: investigate why this test crashes under AppVerifier on lanes_core.dll unload when running against Lua 5.1, 5.2 and 5.4 RELEASE ONLY!
199// apparently, the mutex of ProtectedAllocator is deemed still in use. Crash goes away if I don't use it in protected_lua_Alloc
200TEST_CASE(("lanes.configure.allocator/protected"))
201{
202 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
120 203
121 SECTION("allocator = 'protected'") 204 // no typo, should work
122 { 205 L.requireSuccess("require 'lanes'.configure{allocator = 'protected'}");
123 // no typo, should work 206}
124 L.requireSuccess("require 'lanes'.configure{allocator = 'protected'}");
125 }
126 207
127 // -----------------------------------------------------------------------------------------
128 208
129 SECTION("allocator = <good custom C allocator>") 209// #################################################################################################
130 {
131 // a function that provides what we expect is fine
132 static constexpr lua_CFunction _provideAllocator = +[](lua_State* const L_) {
133 lanes::AllocatorDefinition* const _def{ new (L_) lanes::AllocatorDefinition{} };
134 _def->initFrom(L_);
135 return 1;
136 };
137 lua_pushcfunction(L, _provideAllocator);
138 lua_setglobal(L, "ProvideAllocator");
139 L.requireSuccess("require 'lanes'.configure{allocator = ProvideAllocator}");
140 }
141 210
142 // ----------------------------------------------------------------------------------------- 211TEST_CASE("lanes.configure.internal_allocator")
212{
213 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
143 214
144 SECTION("allocator not returning an AllocatorDefinition") 215 // internal_allocator should be a string, "libc"/"allocator"
145 { 216
146 // a function that provides something that is definitely not an AllocatorDefinition, should cause an error 217 SECTION("internal_allocator = false")
147 static constexpr lua_CFunction _provideAllocator = +[](lua_State* const L_) { 218 {
148 lua_newtable(L_); 219 L.requireFailure("require 'lanes'.configure{internal_allocator = false}");
149 return 1; 220 }
150 };
151 lua_pushcfunction(L, _provideAllocator);
152 lua_setglobal(L, "ProvideAllocator");
153 // force value of internal_allocator so that the LuaJIT-default 'libc' is not selected
154 // which would prevent us from calling _provideAllocator
155 L.requireFailure("require 'lanes'.configure{allocator = ProvideAllocator, internal_allocator = 'allocator'}");
156 }
157 221
158 // ----------------------------------------------------------------------------------------- 222 // ---------------------------------------------------------------------------------------------
159 223
160 SECTION("allocator returning an AllocatorDefinition with the wrong signature") 224 SECTION("internal_allocator = true")
161 { 225 {
162 // a function that provides something that is too small to contain an AllocatorDefinition, should cause an error 226 L.requireFailure("require 'lanes'.configure{internal_allocator = true}");
163 static constexpr lua_CFunction _provideAllocator = +[](lua_State* const L_) { 227 }
164 // create a full userdata that is too small (it only contains enough to store a version tag, but not the rest
165 auto* const _duck{ static_cast<lanes::AllocatorDefinition::version_t*>(lua_newuserdata(L_, sizeof(lanes::AllocatorDefinition::version_t))) };
166 *_duck = 666777;
167 return 1;
168 };
169 lua_pushcfunction(L, _provideAllocator);
170 lua_setglobal(L, "ProvideAllocator");
171 // force value of internal_allocator so that the LuaJIT-default 'libc' is not selected
172 // which would prevent us from calling _provideAllocator
173 L.requireFailure("require 'lanes'.configure{allocator = ProvideAllocator, internal_allocator = 'allocator'}");
174 }
175 228
176 // ----------------------------------------------------------------------------------------- 229 // ---------------------------------------------------------------------------------------------
177 230
178 SECTION("allocator returning something too small to be a valid AllocatorDefinition") 231 SECTION("internal_allocator = <table>")
179 { 232 {
180 // a function that provides something that attempts to pass as an AllocatorDefinition, but is not, should cause an error 233 L.requireFailure("require 'lanes'.configure{internal_allocator = {}}");
181 static constexpr lua_CFunction _provideAllocator = +[](lua_State* const L_) {
182 // create a full userdata of the correct size, but of course the contents don't match
183 int* const _duck{ static_cast<int*>(lua_newuserdata(L_, sizeof(lanes::AllocatorDefinition))) };
184 _duck[0] = 666;
185 _duck[1] = 777;
186 return 1;
187 };
188 lua_pushcfunction(L, _provideAllocator);
189 lua_setglobal(L, "ProvideAllocator");
190 // force value of internal_allocator so that the LuaJIT-default 'libc' is not selected
191 // which would prevent us from calling _provideAllocator
192 L.requireFailure("require 'lanes'.configure{allocator = ProvideAllocator, internal_allocator = 'allocator'}");
193 }
194 } 234 }
195 235
196 // --------------------------------------------------------------------------------------------- 236 // ---------------------------------------------------------------------------------------------
197 // internal_allocator should be a string, "libc"/"allocator"
198 237
199 SECTION("[internal_allocator") 238 SECTION("internal_allocator = <Lua function>")
200 { 239 {
201 SECTION("internal_allocator = false") 240 L.requireFailure("require 'lanes'.configure{internal_allocator = function() end}");
202 { 241 }
203 L.requireFailure("require 'lanes'.configure{internal_allocator = false}");
204 }
205 242
206 // ----------------------------------------------------------------------------------------- 243 // ---------------------------------------------------------------------------------------------
207 244
208 SECTION("internal_allocator = true") 245 SECTION("internal_allocator = <bad string>")
209 { 246 {
210 L.requireFailure("require 'lanes'.configure{internal_allocator = true}"); 247 L.requireFailure("require 'lanes'.configure{internal_allocator = 'gluh'}");
211 } 248 }
212 249
213 // ----------------------------------------------------------------------------------------- 250 // ---------------------------------------------------------------------------------------------
214 251
215 SECTION("internal_allocator = <table>") 252 SECTION("internal_allocator = 'libc'")
216 { 253 {
217 L.requireFailure("require 'lanes'.configure{internal_allocator = {}}"); 254 L.requireSuccess("require 'lanes'.configure{internal_allocator = 'libc'}");
218 } 255 }
219 256
220 // ----------------------------------------------------------------------------------------- 257 // ---------------------------------------------------------------------------------------------
221 258
222 SECTION("internal_allocator = <Lua function>") 259 SECTION("internal_allocator = 'allocator'")
223 { 260 {
224 L.requireFailure("require 'lanes'.configure{internal_allocator = function() end}"); 261 L.requireSuccess("require 'lanes'.configure{internal_allocator = 'allocator'}");
225 } 262 }
263}
226 264
227 // ----------------------------------------------------------------------------------------- 265// #################################################################################################
228 266
229 SECTION("internal_allocator = <bad string>") 267TEST_CASE("lanes.configure.keepers_gc_threshold")
230 { 268{
231 L.requireFailure("require 'lanes'.configure{internal_allocator = 'gluh'}"); 269 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
232 }
233 270
234 // ----------------------------------------------------------------------------------------- 271 // keepers_gc_threshold should be a number in [0, 100]
235 272
236 SECTION("internal_allocator = 'libc'") 273 SECTION("keepers_gc_threshold = <table>")
237 { 274 {
238 L.requireSuccess("require 'lanes'.configure{internal_allocator = 'libc'}"); 275 L.requireFailure("require 'lanes'.configure{keepers_gc_threshold = {}}");
239 } 276 }
240 277
241 // ----------------------------------------------------------------------------------------- 278 // ---------------------------------------------------------------------------------------------
242 279
243 SECTION("internal_allocator = 'allocator'") 280 SECTION("keepers_gc_threshold = <string>")
244 { 281 {
245 L.requireSuccess("require 'lanes'.configure{internal_allocator = 'allocator'}"); 282 L.requireFailure("require 'lanes'.configure{keepers_gc_threshold = 'gluh'}");
246 }
247 } 283 }
248 284
249 // --------------------------------------------------------------------------------------------- 285 // ---------------------------------------------------------------------------------------------
250 // keepers_gc_threshold should be a number in [0, 100]
251 286
252 SECTION("keepers_gc_threshold") 287 SECTION("keepers_gc_threshold = -1")
253 { 288 {
254 SECTION("keepers_gc_threshold = <table>") 289 L.requireSuccess("require 'lanes'.configure{keepers_gc_threshold = -1}");
255 { 290 }
256 L.requireFailure("require 'lanes'.configure{keepers_gc_threshold = {}}");
257 }
258 291
259 // ----------------------------------------------------------------------------------------- 292 // ---------------------------------------------------------------------------------------------
260 293
261 SECTION("keepers_gc_threshold = <string>") 294 SECTION("keepers_gc_threshold = 0")
262 { 295 {
263 L.requireFailure("require 'lanes'.configure{keepers_gc_threshold = 'gluh'}"); 296 L.requireSuccess("require 'lanes'.configure{keepers_gc_threshold = 0}");
264 } 297 }
265 298
266 // ----------------------------------------------------------------------------------------- 299 // ---------------------------------------------------------------------------------------------
267 300
268 SECTION("keepers_gc_threshold = -1") 301 SECTION("keepers_gc_threshold = 100")
269 { 302 {
270 L.requireSuccess("require 'lanes'.configure{keepers_gc_threshold = -1}"); 303 L.requireSuccess("require 'lanes'.configure{keepers_gc_threshold = 100}");
271 } 304 }
305}
272 306
273 // ----------------------------------------------------------------------------------------- 307// #################################################################################################
274 308
275 SECTION("keepers_gc_threshold = 0") 309TEST_CASE("lanes.configure.linda_wake_period")
276 { 310{
277 L.requireSuccess("require 'lanes'.configure{keepers_gc_threshold = 0}"); 311 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
278 }
279 312
280 // ----------------------------------------------------------------------------------------- 313 // linda_wake_period should be a number > 0, or 'never'
281 314
282 SECTION("keepers_gc_threshold = 100") 315 SECTION("linda_wake_period = <table>")
283 { 316 {
284 L.requireSuccess("require 'lanes'.configure{keepers_gc_threshold = 100}"); 317 L.requireFailure("require 'lanes'.configure{linda_wake_period = {}}");
285 }
286 } 318 }
287 319
288 // --------------------------------------------------------------------------------------------- 320 // ---------------------------------------------------------------------------------------------
289 // nb_user_keepers should be a number in [0, 100]
290 321
291 SECTION("nb_user_keepers") 322 SECTION("linda_wake_period = <string>")
292 { 323 {
293 SECTION("nb_user_keepers = <table>") 324 L.requireFailure("require 'lanes'.configure{linda_wake_period = 'gluh'}");
294 { 325 }
295 L.requireFailure("require 'lanes'.configure{nb_user_keepers = {}}");
296 }
297 326
298 // ----------------------------------------------------------------------------------------- 327 // ---------------------------------------------------------------------------------------------
299 328
300 SECTION("nb_user_keepers = <string>") 329 SECTION("linda_wake_period = 'never'")
301 { 330 {
302 L.requireFailure("require 'lanes'.configure{nb_user_keepers = 'gluh'}"); 331 L.requireSuccess("require 'lanes'.configure{linda_wake_period = 'never'}");
303 } 332 }
304 333
305 // ----------------------------------------------------------------------------------------- 334 // ---------------------------------------------------------------------------------------------
306 335
307 SECTION("nb_user_keepers = -1") 336 SECTION("linda_wake_period = <negative number>")
308 { 337 {
309 L.requireFailure("require 'lanes'.configure{nb_user_keepers = -1}"); 338 L.requireFailure("require 'lanes'.configure{linda_wake_period = -0.001}");
310 } 339 }
311 340
312 // ----------------------------------------------------------------------------------------- 341 // ---------------------------------------------------------------------------------------------
313 342
314 SECTION("nb_user_keepers = 0") 343 SECTION("linda_wake_period = 0")
315 { 344 {
316 L.requireSuccess("require 'lanes'.configure{nb_user_keepers = 0}"); 345 L.requireFailure("require 'lanes'.configure{linda_wake_period = 0}");
317 } 346 }
347
348 // ---------------------------------------------------------------------------------------------
318 349
319 // ----------------------------------------------------------------------------------------- 350 SECTION("linda_wake_period = 0.0001s")
351 {
352 L.requireSuccess("require 'lanes'.configure{linda_wake_period = 0.0001}");
353 }
320 354
321 SECTION("nb_user_keepers = 100") 355 // ---------------------------------------------------------------------------------------------
322 {
323 L.requireSuccess("require 'lanes'.configure{nb_user_keepers = 100}");
324 }
325 356
326 // ----------------------------------------------------------------------------------------- 357 SECTION("linda_wake_period = 1e30")
358 {
359 L.requireSuccess("require 'lanes'.configure{linda_wake_period = 1e30}");
360 }
361}
327 362
328 SECTION("nb_user_keepers = 101") 363// #################################################################################################
329 { 364
330 L.requireFailure("require 'lanes'.configure{nb_user_keepers = 101}"); 365TEST_CASE("lanes.configure.nb_user_keepers")
331 } 366{
367 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
368
369 // nb_user_keepers should be a number in [0, 100]
370
371 SECTION("nb_user_keepers = <table>")
372 {
373 L.requireFailure("require 'lanes'.configure{nb_user_keepers = {}}");
332 } 374 }
333 375
334 // --------------------------------------------------------------------------------------------- 376 // ---------------------------------------------------------------------------------------------
335 // on_state_create should be a function, either C or Lua, without upvalues
336 377
337 SECTION("on_state_create") 378 SECTION("nb_user_keepers = <string>")
338 { 379 {
339 SECTION("on_state_create = <table>") 380 L.requireFailure("require 'lanes'.configure{nb_user_keepers = 'gluh'}");
340 { 381 }
341 L.requireFailure("require 'lanes'.configure{on_state_create = {}}");
342 }
343 382
344 // ----------------------------------------------------------------------------------------- 383 // ---------------------------------------------------------------------------------------------
345 384
346 SECTION("on_state_create = <string>") 385 SECTION("nb_user_keepers = -1")
347 { 386 {
348 L.requireFailure("require 'lanes'.configure{on_state_create = 'gluh'}"); 387 L.requireFailure("require 'lanes'.configure{nb_user_keepers = -1}");
349 } 388 }
389
390 // ---------------------------------------------------------------------------------------------
350 391
351 // ----------------------------------------------------------------------------------------- 392 SECTION("nb_user_keepers = 0")
393 {
394 L.requireSuccess("require 'lanes'.configure{nb_user_keepers = 0}");
395 }
352 396
353 SECTION("on_state_create = <number>") 397 // ---------------------------------------------------------------------------------------------
354 {
355 L.requireFailure("require 'lanes'.configure{on_state_create = 1}");
356 }
357 398
358 // ----------------------------------------------------------------------------------------- 399 SECTION("nb_user_keepers = 1")
400 {
401 L.requireSuccess("require 'lanes'.configure{nb_user_keepers = 1}");
402 }
359 403
360 SECTION("on_state_create = false") 404 // ---------------------------------------------------------------------------------------------
361 {
362 L.requireFailure("require 'lanes'.configure{on_state_create = false}");
363 }
364 405
365 // ----------------------------------------------------------------------------------------- 406 SECTION("nb_user_keepers = 100")
407 {
408 L.requireSuccess("require 'lanes'.configure{nb_user_keepers = 100}");
409 }
366 410
367 SECTION("on_state_create = true") 411 // -----------------------------------------------------------------------------------------
368 {
369 L.requireFailure("require 'lanes'.configure{on_state_create = true}");
370 }
371 412
372 // ----------------------------------------------------------------------------------------- 413 SECTION("nb_user_keepers = 101")
414 {
415 L.requireFailure("require 'lanes'.configure{nb_user_keepers = 101}");
416 }
417}
373 418
374 SECTION("on_state_create = <Lua function>") 419// #################################################################################################
375 { 420
376 // on_state_create isn't called inside a Keeper state if it's a Lua function (which is good as print() doesn't exist there!) 421TEST_CASE("lanes.configure.on_state_create/configuration")
377 L.requireSuccess("local print = print; require 'lanes'.configure{on_state_create = function() print 'hello' end}"); 422{
378 } 423 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
379 424
380 // ----------------------------------------------------------------------------------------- 425 // on_state_create should be a function, either C or Lua, without upvalues
381 426
382 SECTION("on_state_create = <C function>") 427 SECTION("on_state_create = <table>")
383 { 428 {
384 // funnily enough, in Lua 5.3, print() uses global tostring(), that doesn't exist in a keeper since we didn't open libs -> "attempt to call a nil value" 429 L.requireFailure("require 'lanes'.configure{on_state_create = {}}");
385 // conclusion, don't use print() as a fake on_state_create() callback!
386 // assert() should be fine since we pass a non-false argument to on_state_create
387 L.requireSuccess("require 'lanes'.configure{on_state_create = assert}");
388 }
389 } 430 }
390 431
391 // --------------------------------------------------------------------------------------------- 432 // ---------------------------------------------------------------------------------------------
392 // shutdown_timeout should be a number in [0,3600]
393 433
394 SECTION("shutdown_timeout") 434 SECTION("on_state_create = <string>")
395 { 435 {
396 SECTION("shutdown_timeout = <table>") 436 L.requireFailure("require 'lanes'.configure{on_state_create = 'gluh'}");
397 { 437 }
398 L.requireFailure("require 'lanes'.configure{shutdown_timeout = {}}");
399 }
400 438
401 // ----------------------------------------------------------------------------------------- 439 // ---------------------------------------------------------------------------------------------
402 440
403 SECTION("shutdown_timeout = <string>") 441 SECTION("on_state_create = <number>")
404 { 442 {
405 L.requireFailure("require 'lanes'.configure{shutdown_timeout = 'gluh'}"); 443 L.requireFailure("require 'lanes'.configure{on_state_create = 1}");
406 } 444 }
407 445
408 // ----------------------------------------------------------------------------------------- 446 // ---------------------------------------------------------------------------------------------
409 447
410 SECTION("shutdown_timeout = <negative number>") 448 SECTION("on_state_create = false")
411 { 449 {
412 L.requireFailure("require 'lanes'.configure{shutdown_timeout = -0.001}"); 450 L.requireFailure("require 'lanes'.configure{on_state_create = false}");
413 } 451 }
414 452
415 // ----------------------------------------------------------------------------------------- 453 // ---------------------------------------------------------------------------------------------
416 454
417 SECTION("shutdown_timeout = 0") 455 SECTION("on_state_create = true")
418 { 456 {
419 L.requireSuccess("require 'lanes'.configure{shutdown_timeout = 0}"); 457 L.requireFailure("require 'lanes'.configure{on_state_create = true}");
420 } 458 }
421 459
422 // ----------------------------------------------------------------------------------------- 460 // ---------------------------------------------------------------------------------------------
423 461
424 SECTION("shutdown_timeout = 1s") 462 SECTION("on_state_create = <Lua function>")
425 { 463 {
426 L.requireSuccess("require 'lanes'.configure{shutdown_timeout = 1}"); 464 // on_state_create isn't called inside a Keeper state if it's a Lua function (which is good as print() doesn't exist there!)
427 } 465 L.requireSuccess("local print = print; require 'lanes'.configure{on_state_create = function() print 'hello' end}");
466 }
428 467
429 // ----------------------------------------------------------------------------------------- 468 // ---------------------------------------------------------------------------------------------
430 469
431 SECTION("shutdown_timeout = 3600s") 470 SECTION("on_state_create = <C function>")
432 { 471 {
433 L.requireSuccess("require 'lanes'.configure{shutdown_timeout = 3600}"); 472 // funnily enough, in Lua 5.3, print() uses global tostring(), that doesn't exist in a keeper since we didn't open libs -> "attempt to call a nil value"
434 } 473 // conclusion, don't use print() as a fake on_state_create() callback!
474 // assert() should be fine since we pass a non-false argument to on_state_create
475 L.requireSuccess("require 'lanes'.configure{on_state_create = assert}");
476 }
477}
435 478
436 // ----------------------------------------------------------------------------------------- 479// #################################################################################################
437 480
438 SECTION("shutdown_timeout = <too long>") 481TEST_CASE("lanes.configure.shutdown_timeout")
439 { 482{
440 L.requireFailure("require 'lanes'.configure{shutdown_timeout = 3600.001}"); 483 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
441 } 484
485 // shutdown_timeout should be a number in [0,3600]
486
487 SECTION("shutdown_timeout = <table>")
488 {
489 L.requireFailure("require 'lanes'.configure{shutdown_timeout = {}}");
442 } 490 }
443 491
444 // --------------------------------------------------------------------------------------------- 492 // ---------------------------------------------------------------------------------------------
445 // strip_functions should be a boolean
446 493
447 SECTION("strip_functions") 494 SECTION("shutdown_timeout = <string>")
448 { 495 {
449 SECTION("strip_functions = <table>") 496 L.requireFailure("require 'lanes'.configure{shutdown_timeout = 'gluh'}");
450 { 497 }
451 L.requireFailure("require 'lanes'.configure{strip_functions = {}}");
452 }
453 498
454 // ----------------------------------------------------------------------------------------- 499 // ---------------------------------------------------------------------------------------------
455 500
456 SECTION("strip_functions = <string>") 501 SECTION("shutdown_timeout = <negative number>")
457 { 502 {
458 L.requireFailure("require 'lanes'.configure{strip_functions = 'gluh'}"); 503 L.requireFailure("require 'lanes'.configure{shutdown_timeout = -0.001}");
459 } 504 }
460 505
461 // ----------------------------------------------------------------------------------------- 506 // ---------------------------------------------------------------------------------------------
462 507
463 SECTION("strip_functions = <number>") 508 SECTION("shutdown_timeout = 0")
464 { 509 {
465 L.requireFailure("require 'lanes'.configure{strip_functions = 1}"); 510 L.requireSuccess("require 'lanes'.configure{shutdown_timeout = 0}");
466 } 511 }
467 512
468 // ----------------------------------------------------------------------------------------- 513 // ---------------------------------------------------------------------------------------------
469 514
470 SECTION("strip_functions = <C function>") 515 SECTION("shutdown_timeout = 1s")
471 { 516 {
472 L.requireFailure("require 'lanes'.configure{strip_functions = print}"); 517 L.requireSuccess("require 'lanes'.configure{shutdown_timeout = 1}");
473 } 518 }
519
520 // ---------------------------------------------------------------------------------------------
474 521
475 // ----------------------------------------------------------------------------------------- 522 SECTION("shutdown_timeout = 3600s")
523 {
524 L.requireSuccess("require 'lanes'.configure{shutdown_timeout = 3600}");
525 }
476 526
477 SECTION("strip_functions = false") 527 // ---------------------------------------------------------------------------------------------
478 {
479 L.requireSuccess("require 'lanes'.configure{strip_functions = false}");
480 }
481 528
482 // ----------------------------------------------------------------------------------------- 529 SECTION("shutdown_timeout = <too long>")
530 {
531 L.requireFailure("require 'lanes'.configure{shutdown_timeout = 3600.001}");
532 }
533}
483 534
484 SECTION("strip_functions = true") 535// #################################################################################################
485 { 536
486 L.requireSuccess("require 'lanes'.configure{strip_functions = true}"); 537TEST_CASE("lanes.configure.strip_functions")
487 } 538{
539 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
540
541 // strip_functions should be a boolean
542
543 SECTION("strip_functions = <table>")
544 {
545 L.requireFailure("require 'lanes'.configure{strip_functions = {}}");
488 } 546 }
489 547
490 // --------------------------------------------------------------------------------------------- 548 // ---------------------------------------------------------------------------------------------
491 // track_lanes should be a boolean
492 549
493 SECTION("track_lanes") 550 SECTION("strip_functions = <string>")
494 { 551 {
495 SECTION("track_lanes = <table>") 552 L.requireFailure("require 'lanes'.configure{strip_functions = 'gluh'}");
496 { 553 }
497 L.requireFailure("require 'lanes'.configure{track_lanes = {}}");
498 }
499 554
500 // ----------------------------------------------------------------------------------------- 555 // ---------------------------------------------------------------------------------------------
501 556
502 SECTION("track_lanes = <string>") 557 SECTION("strip_functions = <number>")
503 { 558 {
504 L.requireFailure("require 'lanes'.configure{track_lanes = 'gluh'}"); 559 L.requireFailure("require 'lanes'.configure{strip_functions = 1}");
505 } 560 }
561
562 // ---------------------------------------------------------------------------------------------
506 563
507 // ----------------------------------------------------------------------------------------- 564 SECTION("strip_functions = <C function>")
565 {
566 L.requireFailure("require 'lanes'.configure{strip_functions = print}");
567 }
508 568
509 SECTION("track_lanes = <number>") 569 // ---------------------------------------------------------------------------------------------
510 {
511 L.requireFailure("require 'lanes'.configure{track_lanes = 1}");
512 }
513 570
514 // ----------------------------------------------------------------------------------------- 571 SECTION("strip_functions = false")
572 {
573 L.requireSuccess("require 'lanes'.configure{strip_functions = false}");
574 }
515 575
516 SECTION("track_lanes = <C function>") 576 // ---------------------------------------------------------------------------------------------
517 {
518 L.requireFailure("require 'lanes'.configure{track_lanes = print}");
519 }
520 577
521 // ----------------------------------------------------------------------------------------- 578 SECTION("strip_functions = true")
579 {
580 L.requireSuccess("require 'lanes'.configure{strip_functions = true}");
581 }
582}
522 583
523 SECTION("track_lanes = false") 584// #################################################################################################
524 {
525 L.requireSuccess("require 'lanes'.configure{track_lanes = false}");
526 }
527 585
528 // ----------------------------------------------------------------------------------------- 586TEST_CASE("lanes.configure.track_lanes")
587{
588 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
529 589
530 SECTION("track_lanes = true") 590 // track_lanes should be a boolean
531 { 591
532 L.requireSuccess("require 'lanes'.configure{track_lanes = true}"); 592 SECTION("track_lanes = <table>")
533 } 593 {
594 L.requireFailure("require 'lanes'.configure{track_lanes = {}}");
534 } 595 }
535 596
536 // --------------------------------------------------------------------------------------------- 597 // ---------------------------------------------------------------------------------------------
537 // verbose_errors should be a boolean
538 598
539 SECTION("verbose_errors") 599 SECTION("track_lanes = <string>")
540 { 600 {
541 SECTION("verbose_errors = <table>") 601 L.requireFailure("require 'lanes'.configure{track_lanes = 'gluh'}");
542 { 602 }
543 L.requireFailure("require 'lanes'.configure{verbose_errors = {}}");
544 }
545 603
546 // ----------------------------------------------------------------------------------------- 604 // ---------------------------------------------------------------------------------------------
547 605
548 SECTION("verbose_errors = <string>") 606 SECTION("track_lanes = <number>")
549 { 607 {
550 L.requireFailure("require 'lanes'.configure{verbose_errors = 'gluh'}"); 608 L.requireFailure("require 'lanes'.configure{track_lanes = 1}");
551 } 609 }
552 610
553 // ----------------------------------------------------------------------------------------- 611 // ---------------------------------------------------------------------------------------------
554 612
555 SECTION("verbose_errors = <number>") 613 SECTION("track_lanes = <C function>")
556 { 614 {
557 L.requireFailure("require 'lanes'.configure{verbose_errors = 1}"); 615 L.requireFailure("require 'lanes'.configure{track_lanes = print}");
558 } 616 }
559 617
560 // ----------------------------------------------------------------------------------------- 618 // ---------------------------------------------------------------------------------------------
561 619
562 SECTION("verbose_errors = <C function>") 620 SECTION("track_lanes = false")
563 { 621 {
564 L.requireFailure("require 'lanes'.configure{verbose_errors = print}"); 622 L.requireSuccess("require 'lanes'.configure{track_lanes = false}");
565 } 623 }
566 624
567 // ----------------------------------------------------------------------------------------- 625 // ---------------------------------------------------------------------------------------------
568 626
569 SECTION("verbose_errors = false") 627 SECTION("track_lanes = true")
570 { 628 {
571 L.requireSuccess("require 'lanes'.configure{verbose_errors = false}"); 629 L.requireSuccess("require 'lanes'.configure{track_lanes = true}");
572 } 630 }
631}
573 632
574 // ----------------------------------------------------------------------------------------- 633// #################################################################################################
575 634
576 SECTION("verbose_errors = true") 635TEST_CASE("lanes.configure.verbose_errors")
577 { 636{
578 L.requireSuccess("require 'lanes'.configure{verbose_errors = true}"); 637 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
579 } 638
639 // verbose_errors should be a boolean
640
641 SECTION("verbose_errors = <table>")
642 {
643 L.requireFailure("require 'lanes'.configure{verbose_errors = {}}");
580 } 644 }
581 645
582 // --------------------------------------------------------------------------------------------- 646 // ---------------------------------------------------------------------------------------------
583 // with_timers should be a boolean
584 647
585 SECTION("with_timers") 648 SECTION("verbose_errors = <string>")
586 { 649 {
587 SECTION("with_timers = <table>") 650 L.requireFailure("require 'lanes'.configure{verbose_errors = 'gluh'}");
588 { 651 }
589 L.requireFailure("require 'lanes'.configure{with_timers = {}}");
590 }
591 652
592 // ----------------------------------------------------------------------------------------- 653 // ---------------------------------------------------------------------------------------------
593 654
594 SECTION("with_timers = <string>") 655 SECTION("verbose_errors = <number>")
595 { 656 {
596 L.requireFailure("require 'lanes'.configure{with_timers = 'gluh'}"); 657 L.requireFailure("require 'lanes'.configure{verbose_errors = 1}");
597 } 658 }
598 659
599 // ----------------------------------------------------------------------------------------- 660 // ---------------------------------------------------------------------------------------------
600 661
601 SECTION("with_timers = <number>") 662 SECTION("verbose_errors = <C function>")
602 { 663 {
603 L.requireFailure("require 'lanes'.configure{with_timers = 1}"); 664 L.requireFailure("require 'lanes'.configure{verbose_errors = print}");
604 } 665 }
605 666
606 // ----------------------------------------------------------------------------------------- 667 // ---------------------------------------------------------------------------------------------
607 668
608 SECTION("with_timers = <C function>") 669 SECTION("verbose_errors = false")
609 { 670 {
610 L.requireFailure("require 'lanes'.configure{with_timers = print}"); 671 L.requireSuccess("require 'lanes'.configure{verbose_errors = false}");
611 } 672 }
612 673
613 // ----------------------------------------------------------------------------------------- 674 // ---------------------------------------------------------------------------------------------
614 675
615 SECTION("with_timers = false") 676 SECTION("verbose_errors = true")
616 { 677 {
617 L.requireSuccess("require 'lanes'.configure{with_timers = false}"); 678 L.requireSuccess("require 'lanes'.configure{verbose_errors = true}");
618 } 679 }
680}
619 681
620 // ----------------------------------------------------------------------------------------- 682// #################################################################################################
621 683
622 SECTION("with_timers = true") 684TEST_CASE("lanes.configure.with_timers")
623 { 685{
624 L.requireSuccess("require 'lanes'.configure{with_timers = true}"); 686 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
625 } 687
688 // with_timers should be a boolean
689
690 SECTION("with_timers = <table>")
691 {
692 L.requireFailure("require 'lanes'.configure{with_timers = {}}");
693 }
694
695 // ---------------------------------------------------------------------------------------------
696
697 SECTION("with_timers = <string>")
698 {
699 L.requireFailure("require 'lanes'.configure{with_timers = 'gluh'}");
700 }
701
702 // ---------------------------------------------------------------------------------------------
703
704 SECTION("with_timers = <number>")
705 {
706 L.requireFailure("require 'lanes'.configure{with_timers = 1}");
626 } 707 }
627 708
628 // --------------------------------------------------------------------------------------------- 709 // ---------------------------------------------------------------------------------------------
710
711 SECTION("with_timers = <C function>")
712 {
713 L.requireFailure("require 'lanes'.configure{with_timers = print}");
714 }
715
716 // ---------------------------------------------------------------------------------------------
717
718 SECTION("with_timers = false")
719 {
720 L.requireSuccess("require 'lanes'.configure{with_timers = false}");
721 }
722
723 // ---------------------------------------------------------------------------------------------
724
725 SECTION("with_timers = true")
726 {
727 L.requireSuccess("require 'lanes'.configure{with_timers = true}");
728 }
729}
730
731// #################################################################################################
732
733TEST_CASE("lanes.configure.unknown_setting")
734{
735 LuaState L{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
736
629 // any unknown setting should be rejected 737 // any unknown setting should be rejected
630 738
631 SECTION("unknown_setting") 739 SECTION("table setting")
632 { 740 {
633 SECTION("table setting") 741 L.requireFailure("require 'lanes'.configure{[{}] = {}}");
634 { 742 }
635 L.requireFailure("require 'lanes'.configure{[{}] = {}}");
636 }
637 743
638 // ----------------------------------------------------------------------------------------- 744 // ---------------------------------------------------------------------------------------------
639 745
640 SECTION("boolean setting") 746 SECTION("boolean setting")
641 { 747 {
642 L.requireFailure("require 'lanes'.configure{[true] = 'gluh'}"); 748 L.requireFailure("require 'lanes'.configure{[true] = 'gluh'}");
643 } 749 }
644 750
645 // ----------------------------------------------------------------------------------------- 751 // ---------------------------------------------------------------------------------------------
646 752
647 SECTION("function setting") 753 SECTION("function setting")
648 { 754 {
649 L.requireFailure("require 'lanes'.configure{[function() end] = 1}"); 755 L.requireFailure("require 'lanes'.configure{[function() end] = 1}");
650 } 756 }
651 757
652 // ----------------------------------------------------------------------------------------- 758 // ---------------------------------------------------------------------------------------------
653 759
654 SECTION("number setting") 760 SECTION("number setting")
655 { 761 {
656 L.requireFailure("require 'lanes'.configure{[1] = function() end}"); 762 L.requireFailure("require 'lanes'.configure{[1] = function() end}");
657 } 763 }
658 764
659 // ----------------------------------------------------------------------------------------- 765 // ---------------------------------------------------------------------------------------------
660 766
661 SECTION("unknown string setting") 767 SECTION("unknown string setting")
662 { 768 {
663 L.requireFailure("require 'lanes'.configure{['gluh'] = false}"); 769 L.requireFailure("require 'lanes'.configure{['gluh'] = false}");
664 }
665 } 770 }
666} 771}
667 772
@@ -670,7 +775,7 @@ TEST_CASE("lanes.configure")
670 775
671#if LUAJIT_FLAVOR() == 0 776#if LUAJIT_FLAVOR() == 0
672// TODO: this test crashes inside S.close() against LuaJIT. to be investigated 777// TODO: this test crashes inside S.close() against LuaJIT. to be investigated
673TEST_CASE("lanes.finally.no fixture") 778TEST_CASE("lanes.finally.no_fixture")
674{ 779{
675 LuaState S{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } }; 780 LuaState S{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
676 // we need Lanes to be up. Since we run several 'scripts', we store it as a global 781 // we need Lanes to be up. Since we run several 'scripts', we store it as a global
@@ -691,7 +796,7 @@ TEST_CASE("lanes.finally.no fixture")
691 796
692// ################################################################################################# 797// #################################################################################################
693 798
694TEST_CASE("lanes.finally.with fixture") 799TEST_CASE("lanes.finally.with_fixture")
695{ 800{
696 LuaState S{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ true } }; 801 LuaState S{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ true } };
697 802
@@ -709,7 +814,7 @@ TEST_CASE("lanes.finally.with fixture")
709 814
710// ################################################################################################# 815// #################################################################################################
711 816
712TEST_CASE("lanes.finally.shutdown with an uncooperative lane") 817TEST_CASE("lanes.finally.shutdown_with_an_uncooperative_lane")
713{ 818{
714 LuaState S{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ true } }; 819 LuaState S{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ true } };
715 S.requireSuccess("lanes = require 'lanes'.configure()"); 820 S.requireSuccess("lanes = require 'lanes'.configure()");
@@ -758,7 +863,7 @@ namespace
758 863
759// ################################################################################################# 864// #################################################################################################
760 865
761TEST_CASE("lanes.on_state_create setting") 866TEST_CASE("lanes.configure.on_state_create/details")
762{ 867{
763 LuaState S{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } }; 868 LuaState S{ LuaState::WithBaseLibs{ true }, LuaState::WithFixture{ false } };
764 869
@@ -829,6 +934,7 @@ TEST_CASE("lanes.on_state_create setting")
829 // launch a Lane that requires the module. It should succeed because _on_state_create was called and made it possible 934 // launch a Lane that requires the module. It should succeed because _on_state_create was called and made it possible
830 std::string_view const _script{ 935 std::string_view const _script{
831 " f = lanes.gen('*'," 936 " f = lanes.gen('*',"
937 " { name = 'auto' },"
832 " function()" 938 " function()"
833 " local Stuff = require ('Stuff')" 939 " local Stuff = require ('Stuff')"
834 " Stuff.DoStuffInC()" 940 " Stuff.DoStuffInC()"