start() held mutex_ and then called loadCache(), which re-locks the same
non-recursive mutex. When a schedule cache file exists and parses (the
normal case for a provisioned kiosk), this self-deadlocks and blocks
SDL_AppInit before the first frame, leaving only a black screen and the
compositor cursor.
Narrow the lock to the member setup so loadCache() can take the lock
itself. Add a regression test that starts with a cached payload present.