aboutsummaryrefslogtreecommitdiff
path: root/lib/std
diff options
context:
space:
mode:
authorAndrew Kelley <andrew@ziglang.org>2021-03-01 19:10:36 -0800
committerGitHub <noreply@github.com>2021-03-01 19:10:36 -0800
commitf9c9b9217551b98a1d25ff6462c035b8d3a99fe1 (patch)
treeb6d6c9254b8f0e3d13e95ec565f6153a8f5c3c52 /lib/std
parenta20169a610b693794756bbc0139f0955c1294b48 (diff)
parent448a28325c7517e6cd62ba7932a4b6c836250757 (diff)
downloadzig-f9c9b9217551b98a1d25ff6462c035b8d3a99fe1.tar.gz
zig-f9c9b9217551b98a1d25ff6462c035b8d3a99fe1.zip
Merge pull request #7946 from koachan/sparc64-framefixes
SPARCv9: Handle various stack frame related quirks.
Diffstat (limited to 'lib/std')
-rw-r--r--lib/std/debug.zig20
1 files changed, 17 insertions, 3 deletions
diff --git a/lib/std/debug.zig b/lib/std/debug.zig
index f32c1a6156..74fb95ffa8 100644
--- a/lib/std/debug.zig
+++ b/lib/std/debug.zig
@@ -360,14 +360,24 @@ pub const StackIterator = struct {
};
}
- // Negative offset of the saved BP wrt the frame pointer.
+ // Offset of the saved BP wrt the frame pointer.
const fp_offset = if (builtin.arch.isRISCV())
// On RISC-V the frame pointer points to the top of the saved register
// area, on pretty much every other architecture it points to the stack
// slot where the previous frame pointer is saved.
2 * @sizeOf(usize)
+ else if (builtin.arch.isSPARC())
+ // On SPARC the previous frame pointer is stored at 14 slots past %fp+BIAS.
+ 14 * @sizeOf(usize)
else
0;
+
+ const fp_bias = if (builtin.arch.isSPARC())
+ // On SPARC frame pointers are biased by a constant.
+ 2047
+ else
+ 0;
+
// Positive offset of the saved PC wrt the frame pointer.
const pc_offset = if (builtin.arch == .powerpc64le)
2 * @sizeOf(usize)
@@ -388,13 +398,17 @@ pub const StackIterator = struct {
}
fn next_internal(self: *StackIterator) ?usize {
- const fp = math.sub(usize, self.fp, fp_offset) catch return null;
+ const fp = if (builtin.arch.isSPARC())
+ // On SPARC the offset is positive. (!)
+ math.add(usize, self.fp, fp_offset) catch return null
+ else
+ math.sub(usize, self.fp, fp_offset) catch return null;
// Sanity check.
if (fp == 0 or !mem.isAligned(fp, @alignOf(usize)))
return null;
- const new_fp = @intToPtr(*const usize, fp).*;
+ const new_fp = math.add(usize, @intToPtr(*const usize, fp).*, fp_bias) catch return null;
// Sanity check: the stack grows down thus all the parent frames must be
// be at addresses that are greater (or equal) than the previous one.