A Bluesky Playdate client
1const std = @import("std");
2const pdapi = @import("playdate_api_definitions.zig");
3const builtin = @import("builtin");
4
5var global_playdate: *pdapi.PlaydateAPI = undefined;
6pub fn init(playdate: *pdapi.PlaydateAPI) void {
7 global_playdate = playdate;
8}
9
10pub fn panic(
11 msg: []const u8,
12 error_return_trace: ?*std.builtin.StackTrace,
13 return_address: ?usize,
14) noreturn {
15 _ = error_return_trace;
16 _ = return_address;
17
18 switch (comptime builtin.os.tag) {
19 .freestanding => {
20 //Playdate hardware
21
22 //TODO: The Zig std library does not yet support stacktraces on Playdate hardware.
23 //We will need to do this manually. Some notes on trying to get it working:
24 //Frame pointer is R7
25 //Next Frame pointer is *R7
26 //Return address is *(R7+4)
27 //To print out the trace corrently,
28 //We need to know the load address and it doesn't seem to be exactly
29 //0x6000_0000 as originally thought
30
31 global_playdate.system.logToConsole("PANIC: %s", msg.ptr);
32 global_playdate.system.@"error"("PANIC: %s", msg.ptr);
33 },
34 else => {
35 //playdate simulator
36 var stack_trace_buffer = [_]u8{0} ** 4096;
37 var buffer = [_]u8{0} ** 4096;
38 var stream = std.io.fixedBufferStream(&stack_trace_buffer);
39
40 const stack_trace_string = b: {
41 if (builtin.strip_debug_info) {
42 break :b "Unable to dump stack trace: Debug info stripped";
43 }
44 const debug_info = std.debug.getSelfDebugInfo() catch |err| {
45 const to_print = std.fmt.bufPrintZ(
46 &buffer,
47 "Unable to dump stack trace: Unable to open debug info: {s}\n",
48 .{@errorName(err)},
49 ) catch break :b "Unable to dump stack trace: Unable to open debug info due unknown error";
50 break :b to_print;
51 };
52 std.debug.writeCurrentStackTrace(
53 stream.writer(),
54 debug_info,
55 .no_color,
56 null,
57 ) catch break :b "Unable to dump stack trace: Unknown error writng stack trace";
58
59 //NOTE: playdate.system.error (and all Playdate APIs that deal with strings) require a null termination
60 const null_char_index = @min(stream.pos, stack_trace_buffer.len - 1);
61 stack_trace_buffer[null_char_index] = 0;
62
63 break :b &stack_trace_buffer;
64 };
65 global_playdate.system.@"error"(
66 "PANIC: %s\n\n%s",
67 msg.ptr,
68 stack_trace_string.ptr,
69 );
70 },
71 }
72
73 while (true) {}
74}