Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions fpga_io.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -427,6 +427,10 @@ static int make_env(const char *name, const char *cfg)

int fpga_load_rbf(const char *name, const char *cfg, const char *xml)
{
// Tear down the launcher frontend (and its HPS framebuffer mmaps) before any
// FPGA reconfiguration. A live frontend scanning out /dev/fb0 over the f2sdram
// bridge deadlocks the AXI bus when do_bridge(0) resets it during load.
alt_launcher_shutdown();
OsdDisable();
static char path[1024];
int ret = 0;
Expand Down
31 changes: 30 additions & 1 deletion support/zaparoo/alt_launcher.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,11 @@
#include <sys/wait.h>
#include "cfg.h"
#include "file_io.h"
#include "fpga_io.h"
#include "hardware.h"
#include "input.h"
#include "menu.h"
#include "scheduler.h"
#include "shmem.h"
#include "user_io.h"
#include "video.h"
Expand Down Expand Up @@ -472,10 +474,37 @@ static void exec_launcher_child(const char *path)
_exit(1);
}

// Bounded replacement for video_chvt(): its VT_WAITACTIVE blocks forever if the
// frontend stalls bringing up video, which would wedge the poll cothread.
static void switch_to_launcher_vt(void)
{
int fd = open("/dev/tty0", O_RDONLY | O_CLOEXEC);
if (fd < 0) return;

if (ioctl(fd, VT_ACTIVATE, s_vt)) printf("alt_launcher: VT_ACTIVATE fails\n");

// Yield to the scheduler rather than usleep() so the poll cothread stays
// cooperative while we wait (bounded) for the VT to become active.
unsigned long deadline = GetTimer(500);
for (;;)
{
struct vt_stat st;
if (!ioctl(fd, VT_GETSTATE, &st) && st.v_active == s_vt) break;
if (CheckTimer(deadline)) break;
scheduler_yield();
}

close(fd);
}

static void finalize_spawn(void)
{
// Defer the VT/fb takeover until the FPGA/HDMI has settled; s_tty_deadline
// stays armed so this retries on a later alt_launcher_poll pass.
if (!is_fpga_ready(1)) return;

s_tty_deadline = 0;
video_chvt(s_vt);
switch_to_launcher_vt();
if (!s_native_crt)
video_fb_enable(1);
else
Expand Down