diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/jni/CMakeLists.txt b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/jni/CMakeLists.txt
index 306bc8d..bca97ce 100644
--- a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/jni/CMakeLists.txt
+++ b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/jni/CMakeLists.txt
@@ -32,7 +32,10 @@ if(HAVE_VICE)
-Wl,--wrap=ui_display_drive_led
-Wl,--wrap=serial_trap_receive
-Wl,--wrap=event_snapshot_write_module
- -Wl,--wrap=event_snapshot_read_module)
+ -Wl,--wrap=event_snapshot_read_module
+ -Wl,--wrap=machine_trigger_reset
+ -Wl,--wrap=machine_reset
+ -Wl,--wrap=maincpu_reset)
target_include_directories(vice_jni PRIVATE
"${CMAKE_CURRENT_SOURCE_DIR}/vice-libs/${ANDROID_ABI}"
"${VICE_SRC}/src"
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/jni/vice_jni.c b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/jni/vice_jni.c
index cadf418..dab8ffa 100644
--- a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/jni/vice_jni.c
+++ b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/jni/vice_jni.c
@@ -77,6 +77,7 @@ extern int __real_console_init(void);
#include "keyboard.h"
#include "autostart.h"
#include "attach.h"
+#include "interrupt.h"
/* Drive LED state.
* g_io_frames: bumped by __wrap_serial_trap_receive; keeps LED lit ~100 ms after
@@ -302,6 +303,69 @@ int __wrap_event_snapshot_read_module(struct snapshot_s *s) {
(void)s; return 0;
}
+/* --wrap=machine_trigger_reset / machine_reset / maincpu_reset: required by the
+ * linker --wrap flags in CMakeLists.txt; kept as simple pass-throughs so the
+ * symbols exist. Previously these suppressed resets during snapshot load, but
+ * the trap-based snapshot load (see load_state_trap below) makes suppression
+ * unnecessary — snapshot load now runs inside DO_INTERRUPT(IK_TRAP) which
+ * provides the EXPORT/IMPORT register sync that makes the CPU resume from the
+ * correct saved PC without any post-load machine reset. */
+void __real_machine_trigger_reset(unsigned int reset_mode);
+void __wrap_machine_trigger_reset(unsigned int reset_mode) {
+ __real_machine_trigger_reset(reset_mode);
+}
+
+void __real_machine_reset(void);
+void __wrap_machine_reset(void) {
+ __real_machine_reset();
+}
+
+void __real_maincpu_reset(void);
+void __wrap_maincpu_reset(void) {
+ __real_maincpu_reset();
+}
+
+/* Snapshot load via VICE CPU trap.
+ *
+ * machine_read_snapshot() restores CPU registers into maincpu_regs (a global
+ * struct), but maincpu_mainloop keeps its own stack-local copies (reg_pc,
+ * reg_a, etc.). If we call machine_read_snapshot() directly from
+ * video_canvas_refresh(), the loop never re-imports maincpu_regs, so the CPU
+ * continues from the *old* reg_pc in the *new* (restored) memory — wrong.
+ *
+ * The fix: schedule a VICE CPU trap. DO_INTERRUPT(IK_TRAP) in 6510core.c
+ * calls EXPORT_REGISTERS() before the trap function and IMPORT_REGISTERS()
+ * after. machine_read_snapshot() inside the trap overwrites maincpu_regs
+ * with the saved state; IMPORT_REGISTERS() then propagates those values
+ * (including the saved PC) back into the CPU loop's stack locals. Result:
+ * the game resumes from exactly the saved execution point. */
+/* Both save and load run inside a CPU trap so DO_INTERRUPT(IK_TRAP) calls
+ * EXPORT_REGISTERS() before the trap function and IMPORT_REGISTERS() after.
+ *
+ * For save: EXPORT_REGISTERS() syncs the CPU loop's stack-local reg_pc into
+ * maincpu_regs before machine_write_snapshot reads it. Without the trap,
+ * maincpu_regs.pc is stale (last synced at the previous DO_INTERRUPT), so the
+ * snapshot would record the wrong PC and restore would resume at the wrong
+ * address — input polling code never reached, buttons appear dead.
+ *
+ * For load: machine_read_snapshot overwrites maincpu_regs with the saved state;
+ * IMPORT_REGISTERS() then propagates the saved PC back into reg_pc so the CPU
+ * resumes from the correct saved execution point. */
+static char g_save_trap_path[512] = {0};
+static char g_load_trap_path[512] = {0};
+
+static void save_state_trap(uint16_t address, void *data) {
+ (void)address;
+ int r = machine_write_snapshot((const char *)data, 0, 0, 0);
+ LOGI("machine_write_snapshot → %d", r);
+}
+
+static void load_state_trap(uint16_t address, void *data) {
+ (void)address;
+ int r = machine_read_snapshot((const char *)data, 0);
+ LOGI("machine_read_snapshot → %d", r);
+}
+
/* All functions below replace arch/headless/video.c (excluded from libvice.a). */
int video_arch_get_active_chip(void) { return 0; /* VIDEO_CHIP_VICII */ }
@@ -425,19 +489,19 @@ void video_canvas_refresh(video_canvas_t *canvas,
}
pthread_mutex_unlock(&g_pending_lock);
if (save_state_path[0] != '\0') {
- /* save_roms=0, save_disks=0: disk management is handled by our UI;
- * skipping the drive module avoids path-resolution failures on restore. */
- int r = machine_write_snapshot(save_state_path, 0, 0, 0);
- LOGI("machine_write_snapshot → %d", r);
+ strncpy(g_save_trap_path, save_state_path, sizeof(g_save_trap_path) - 1);
+ g_save_trap_path[sizeof(g_save_trap_path) - 1] = '\0';
+ interrupt_maincpu_trigger_trap(save_state_trap, g_save_trap_path);
}
if (load_state_path[0] != '\0') {
- int r = machine_read_snapshot(load_state_path, 0);
- LOGI("machine_read_snapshot → %d", r);
- /* After snapshot restore the virtual device loses its D64 attachment
- * and falls back to host-filesystem mode. Re-attach the same disk so
- * the C64 program can continue reading from the image it expected. */
- if (r == 0 && g_current_disk_path[0] != '\0')
- file_system_attach_disk(8, 0, g_current_disk_path);
+ /* Schedule a VICE CPU trap so machine_read_snapshot runs inside
+ * DO_INTERRUPT(IK_TRAP). That macro calls EXPORT_REGISTERS() before
+ * the trap and IMPORT_REGISTERS() after, so the saved PC written into
+ * maincpu_regs by machine_read_snapshot is picked up by the CPU loop
+ * immediately — the game resumes from the correct saved execution point. */
+ strncpy(g_load_trap_path, load_state_path, sizeof(g_load_trap_path) - 1);
+ g_load_trap_path[sizeof(g_load_trap_path) - 1] = '\0';
+ interrupt_maincpu_trigger_trap(load_state_trap, g_load_trap_path);
}
/* Drive LED.
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/drawable/ic_launcher_background.xml b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/drawable/ic_launcher_background.xml
deleted file mode 100644
index 07d5da9..0000000
--- a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/drawable/ic_launcher_background.xml
+++ /dev/null
@@ -1,170 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/drawable/ic_launcher_foreground.xml b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/drawable/ic_launcher_foreground.xml
deleted file mode 100644
index 2b068d1..0000000
--- a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/drawable/ic_launcher_foreground.xml
+++ /dev/null
@@ -1,30 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml
index 6f3b755..c164fd9 100644
--- a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml
+++ b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml
@@ -1,6 +1,5 @@
-
-
-
-
\ No newline at end of file
+
+
+
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml
index 6f3b755..c164fd9 100644
--- a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml
+++ b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml
@@ -1,6 +1,5 @@
-
-
-
-
\ No newline at end of file
+
+
+
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher.png
new file mode 100644
index 0000000..2872de7
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher.webp
deleted file mode 100644
index c209e78..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_foreground.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_foreground.png
new file mode 100644
index 0000000..9253a74
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_foreground.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_round.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_round.png
new file mode 100644
index 0000000..2872de7
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_round.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_round.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_round.webp
deleted file mode 100644
index b2dfe3d..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-hdpi/ic_launcher_round.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher.png
new file mode 100644
index 0000000..8da4574
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher.webp
deleted file mode 100644
index 4f0f1d6..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_foreground.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_foreground.png
new file mode 100644
index 0000000..43f1563
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_foreground.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_round.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_round.png
new file mode 100644
index 0000000..8da4574
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_round.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_round.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_round.webp
deleted file mode 100644
index 62b611d..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-mdpi/ic_launcher_round.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher.png
new file mode 100644
index 0000000..a8a4ef4
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher.webp
deleted file mode 100644
index 948a307..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_foreground.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_foreground.png
new file mode 100644
index 0000000..957ee35
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_foreground.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png
new file mode 100644
index 0000000..a8a4ef4
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_round.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_round.webp
deleted file mode 100644
index 1b9a695..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xhdpi/ic_launcher_round.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
new file mode 100644
index 0000000..0f3b11e
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher.webp
deleted file mode 100644
index 28d4b77..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_foreground.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_foreground.png
new file mode 100644
index 0000000..d3689db
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_foreground.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png
new file mode 100644
index 0000000..0f3b11e
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.webp
deleted file mode 100644
index 9287f50..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
new file mode 100644
index 0000000..ce17835
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher.webp
deleted file mode 100644
index aa7d642..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_foreground.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_foreground.png
new file mode 100644
index 0000000..f3f0e1e
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_foreground.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png
new file mode 100644
index 0000000..ce17835
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.webp b/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.webp
deleted file mode 100644
index 9126ae3..0000000
Binary files a/SchwertUndMagieOnPebbleCompanionApp/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.webp and /dev/null differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/res/app-icon-round.png b/SchwertUndMagieOnPebbleCompanionApp/res/app-icon-round.png
new file mode 100644
index 0000000..7af0209
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/res/app-icon-round.png differ
diff --git a/SchwertUndMagieOnPebbleCompanionApp/res/app-icon.png b/SchwertUndMagieOnPebbleCompanionApp/res/app-icon.png
new file mode 100644
index 0000000..f45d83c
Binary files /dev/null and b/SchwertUndMagieOnPebbleCompanionApp/res/app-icon.png differ