When setting up benchmarks for Nim and Lua, @Nino found that calling setImage
many times with no pauses from Nim (the same from C) crashed both the simulator and device.
Later we discovered that the crash only happens when the Lua environment has been initialized.
That means, the native C/Nim update callback is set during the kEventInitLua
.
This is the crash log I got on macOS:
Thread 0 Crashed:: Dispatch queue: com.apple.main-thread
0 libsystem_kernel.dylib 0x19057d11c __pthread_kill + 8
1 libsystem_pthread.dylib 0x1905b4cc0 pthread_kill + 288
2 libsystem_c.dylib 0x1904c4a40 abort + 180
3 Playdate Simulator 0x104aa44c8 luaD_throw + 84
4 Playdate Simulator 0x104ad18a0 luaG_errormsg + 168
5 Playdate Simulator 0x104ab55a0 lua_error + 160
6 Playdate Simulator 0x104a9de4c luaL_error + 76
7 Playdate Simulator 0x104afaf0c pc_luaError + 80
8 Playdate Simulator 0x104ab350c auxgetstr + 224
9 Playdate Simulator 0x104a9e368 luaL_testudata + 76
10 Playdate Simulator 0x104a9e3c8 luaL_checkudata + 32
11 Playdate Simulator 0x104af65b0 luasprite_setImage + 108
12 Playdate Simulator 0x104af6508 pc_sprite_setImage + 140
13 pdex.dylib 0x10c976de8 setImage__OOZOOZOOZOOZOnimbleZpkgsZplaydate4548O4949O50ZplaydateZsprite_781 + 208 (sprite.nim:120)
14 pdex.dylib 0x10c97d510 colonanonymous___bench_225 + 104 (bench.nim:124)
15 pdex.dylib 0x10c97ee54 update__bench_550 + 1368 (bench.nim:242)
16 pdex.dylib 0x10c984050 update__screen_9 + 392 (screen.nim:6)
17 pdex.dylib 0x10c98379c catchingUpdate__nim95snake_10 + 368 (nim_snake.nim:19)
18 pdex.dylib 0x10c97303c privateUpdate__OOZOOZOOZOOZOnimbleZpkgsZplaydate4548O4949O50ZplaydateZsystem_75 + 312 (system.nim:38)
19 Playdate Simulator 0x104b03064 pd_update + 468
20 Playdate Simulator 0x104b55850 -[PCPlaydateSimulator update] + 508
21 Foundation 0x1917b62d8 __NSThreadPerformPerform + 264
22 CoreFoundation 0x190691cfc __CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE0_PERFORM_FUNCTION__ + 28
23 CoreFoundation 0x190691c90 __CFRunLoopDoSource0 + 176
24 CoreFoundation 0x190691a00 __CFRunLoopDoSources0 + 244
25 CoreFoundation 0x1906905f0 __CFRunLoopRun + 828
26 CoreFoundation 0x19068fc5c CFRunLoopRunSpecific + 608
27 HIToolbox 0x19ac0c448 RunCurrentEventLoopInMode + 292
28 HIToolbox 0x19ac0c0d8 ReceiveNextEventCommon + 220
29 HIToolbox 0x19ac0bfdc _BlockUntilNextEventMatchingListInModeWithFilter + 76
30 AppKit 0x193e6ac54 _DPSNextEvent + 660
31 AppKit 0x194640ebc -[NSApplication(NSEventRouting) _nextEventMatchingEventMask:untilDate:inMode:dequeue:] + 716
32 AppKit 0x193e5e100 -[NSApplication run] + 476
33 AppKit 0x193e353cc NSApplicationMain + 880
34 dyld 0x1902390e0 start + 2360
Having Lua enabled, seems like a C call to setImage
goes through quite a few Lua related stuff under the hood, and in our scenario it causes a crash.
Here's a minimal reproduction project in C:
c-sprite-game.zip (8.8 KB)
In this project, calling setImage
more than 15 times in the for loop in main.c
crashes the simulator.
Here's also the GitHub issue of the report: LCD:Sprite.setImage crashes when invoked multiple times · Issue #27 · samdze/playdate-nim · GitHub