diff options
| author | Alex Rønne Petersen <alex@alexrp.com> | 2025-10-06 11:10:02 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2025-10-06 11:10:02 +0200 |
| commit | 2962db333f43c8bb10a1e2ad4cdd19dfab26515b (patch) | |
| tree | 1077791d5785d2276053fc3163b5fb6dde21f645 /lib/std/debug | |
| parent | ea9fb3ccfa1caef7f234a791da18fa33b9c292c7 (diff) | |
| parent | a5ff376b8ff6caa857ec2e4da27e5debb716d920 (diff) | |
| download | zig-2962db333f43c8bb10a1e2ad4cdd19dfab26515b.tar.gz zig-2962db333f43c8bb10a1e2ad4cdd19dfab26515b.zip | |
Merge pull request #25480 from alexrp/std-debug-hexagon
`std.debug`: add unwind support for `hexagon-linux`
Diffstat (limited to 'lib/std/debug')
| -rw-r--r-- | lib/std/debug/Dwarf.zig | 3 | ||||
| -rw-r--r-- | lib/std/debug/SelfInfo/Elf.zig | 1 | ||||
| -rw-r--r-- | lib/std/debug/cpu_context.zig | 76 |
3 files changed, 80 insertions, 0 deletions
diff --git a/lib/std/debug/Dwarf.zig b/lib/std/debug/Dwarf.zig index e510c84f15..0134d10e6b 100644 --- a/lib/std/debug/Dwarf.zig +++ b/lib/std/debug/Dwarf.zig @@ -1431,6 +1431,7 @@ pub fn ipRegNum(arch: std.Target.Cpu.Arch) ?u16 { return switch (arch) { .aarch64, .aarch64_be => 32, .arm, .armeb, .thumb, .thumbeb => 15, + .hexagon => 76, .loongarch32, .loongarch64 => 32, .riscv32, .riscv32be, .riscv64, .riscv64be => 32, .s390x => 65, @@ -1444,6 +1445,7 @@ pub fn fpRegNum(arch: std.Target.Cpu.Arch) u16 { return switch (arch) { .aarch64, .aarch64_be => 29, .arm, .armeb, .thumb, .thumbeb => 11, + .hexagon => 30, .loongarch32, .loongarch64 => 22, .riscv32, .riscv32be, .riscv64, .riscv64be => 8, .s390x => 11, @@ -1457,6 +1459,7 @@ pub fn spRegNum(arch: std.Target.Cpu.Arch) u16 { return switch (arch) { .aarch64, .aarch64_be => 31, .arm, .armeb, .thumb, .thumbeb => 13, + .hexagon => 29, .loongarch32, .loongarch64 => 3, .riscv32, .riscv32be, .riscv64, .riscv64be => 2, .s390x => 15, diff --git a/lib/std/debug/SelfInfo/Elf.zig b/lib/std/debug/SelfInfo/Elf.zig index 9a7b12929b..106d2a532f 100644 --- a/lib/std/debug/SelfInfo/Elf.zig +++ b/lib/std/debug/SelfInfo/Elf.zig @@ -97,6 +97,7 @@ pub const can_unwind: bool = s: { .linux => &.{ .aarch64, .aarch64_be, + .hexagon, .loongarch64, .riscv32, .riscv64, diff --git a/lib/std/debug/cpu_context.zig b/lib/std/debug/cpu_context.zig index 121245ac7b..ae0f0d0e38 100644 --- a/lib/std/debug/cpu_context.zig +++ b/lib/std/debug/cpu_context.zig @@ -6,6 +6,7 @@ pub const Native = if (@hasDecl(root, "debug") and @hasDecl(root.debug, "CpuCont else switch (native_arch) { .aarch64, .aarch64_be => Aarch64, .arm, .armeb, .thumb, .thumbeb => Arm, + .hexagon => Hexagon, .loongarch32, .loongarch64 => LoongArch, .riscv32, .riscv32be, .riscv64, .riscv64be => Riscv, .s390x => S390x, @@ -181,6 +182,13 @@ pub fn fromPosixSignalContext(ctx_ptr: ?*const anyopaque) ?Native { }, else => null, }, + .hexagon => switch (builtin.os.tag) { + .linux => .{ + .r = uc.mcontext.gregs, + .pc = uc.mcontext.pc, + }, + else => null, + }, .loongarch64 => switch (builtin.os.tag) { .linux => .{ .r = uc.mcontext.regs, // includes r0 (hardwired zero) @@ -503,6 +511,74 @@ pub const Aarch64 = extern struct { }; /// This is an `extern struct` so that inline assembly in `current` can use field offsets. +pub const Hexagon = extern struct { + /// The numbered general-purpose registers r0 - r31. + r: [32]u32, + pc: u32, + + pub inline fn current() Hexagon { + var ctx: Hexagon = undefined; + asm volatile ( + \\ memw(r0 + #0) = r0 + \\ memw(r0 + #4) = r1 + \\ memw(r0 + #8) = r2 + \\ memw(r0 + #12) = r3 + \\ memw(r0 + #16) = r4 + \\ memw(r0 + #20) = r5 + \\ memw(r0 + #24) = r6 + \\ memw(r0 + #28) = r7 + \\ memw(r0 + #32) = r8 + \\ memw(r0 + #36) = r9 + \\ memw(r0 + #40) = r10 + \\ memw(r0 + #44) = r11 + \\ memw(r0 + #48) = r12 + \\ memw(r0 + #52) = r13 + \\ memw(r0 + #56) = r14 + \\ memw(r0 + #60) = r15 + \\ memw(r0 + #64) = r16 + \\ memw(r0 + #68) = r17 + \\ memw(r0 + #72) = r18 + \\ memw(r0 + #76) = r19 + \\ memw(r0 + #80) = r20 + \\ memw(r0 + #84) = r21 + \\ memw(r0 + #88) = r22 + \\ memw(r0 + #92) = r23 + \\ memw(r0 + #96) = r24 + \\ memw(r0 + #100) = r25 + \\ memw(r0 + #104) = r26 + \\ memw(r0 + #108) = r27 + \\ memw(r0 + #112) = r28 + \\ memw(r0 + #116) = r29 + \\ memw(r0 + #120) = r30 + \\ memw(r0 + #124) = r31 + \\ r1 = pc + \\ memw(r0 + #128) = r1 + \\ r1 = memw(r0 + #4) + : + : [gprs] "{r0}" (&ctx), + : .{ .memory = true }); + return ctx; + } + + pub fn dwarfRegisterBytes(ctx: *Hexagon, register_num: u16) DwarfRegisterError![]u8 { + // Sourced from LLVM's HexagonRegisterInfo.td, which disagrees with LLDB... + switch (register_num) { + 0...31 => return @ptrCast(&ctx.r[register_num]), + 76 => return @ptrCast(&ctx.pc), + + // This is probably covering some numbers that aren't actually mapped, but seriously, + // look at that file. I really can't be bothered to make it more precise. + 32...75 => return error.UnsupportedRegister, + 77...259 => return error.UnsupportedRegister, + // 999999...1000030 => return error.UnsupportedRegister, + // 9999999...10000030 => return error.UnsupportedRegister, + + else => return error.InvalidRegister, + } + } +}; + +/// This is an `extern struct` so that inline assembly in `current` can use field offsets. pub const LoongArch = extern struct { /// The numbered general-purpose registers r0 - r31. r0 must be zero. r: [32]usize, |
