diff mbox series

[v1,1/1] package/go: fix go on riscv64 in sv57 mode

Message ID 20220724235058.677911-1-christian@paral.in
State Superseded, archived
Headers show
Series [v1,1/1] package/go: fix go on riscv64 in sv57 mode | expand

Commit Message

Christian Stewart July 24, 2022, 11:50 p.m. UTC
On machines supporting Riscv SV57 mode like Qemu, Go programs currently crash
with the following type of error:

runtime: lfstack.push invalid packing: node=0xffffff5908a940 cnt=0x1
packed=0xffff5908a9400001 -> node=0xffff5908a940

The upstream PR fixes this error, but has not yet been merged.

Upstream: https://go-review.googlesource.com/c/go/+/409055/3

Signed-off-by: Christian Stewart <christian@paral.in>
---
 ...03-runtime-support-riscv64-SV57-mode.patch | 59 +++++++++++++++++++
 1 file changed, 59 insertions(+)
 create mode 100644 package/go/0003-runtime-support-riscv64-SV57-mode.patch
diff mbox series

Patch

diff --git a/package/go/0003-runtime-support-riscv64-SV57-mode.patch b/package/go/0003-runtime-support-riscv64-SV57-mode.patch
new file mode 100644
index 0000000000..04811dd3ba
--- /dev/null
+++ b/package/go/0003-runtime-support-riscv64-SV57-mode.patch
@@ -0,0 +1,59 @@ 
+From 98eeeaeaa20279368be0466b24afe44ed24fceb8 Mon Sep 17 00:00:00 2001
+From: Dmitry Vyukov <dvyukov@google.com>
+Date: Fri, 27 May 2022 18:55:35 +0200
+Subject: [PATCH] runtime: support riscv64 SV57 mode
+
+Riscv64 has SV57 mode when user-space VA is 56 bits.
+Linux kernel recently got support for this mode and Go binaries started crashing as:
+
+runtime: lfstack.push invalid packing: node=0xffffff5908a940 cnt=0x1
+packed=0xffff5908a9400001 -> node=0xffff5908a940
+
+Adjust lfstack code to use only 8 top bits of pointers on riscv64.
+
+For context see:
+https://groups.google.com/g/syzkaller-bugs/c/lU0GQTZoNQQ/m/O_c3vmE3AAAJ
+
+Change-Id: Ib5d3d6a79c0c6eddf11618d73fcc8bc1832a9c25
+
+Upstream: https://go-review.googlesource.com/c/go/+/409055/3
+---
+ src/runtime/lfstack_64bit.go | 10 ++++++++++
+ 1 file changed, 10 insertions(+)
+
+diff --git a/src/runtime/lfstack_64bit.go b/src/runtime/lfstack_64bit.go
+index 3f0e480897..9f13e72fa6 100644
+--- a/src/runtime/lfstack_64bit.go
++++ b/src/runtime/lfstack_64bit.go
+@@ -36,12 +36,19 @@ const (
+ 	// We use one bit to distinguish between the two ranges.
+ 	aixAddrBits = 57
+ 	aixCntBits  = 64 - aixAddrBits + 3
++
++	// Riscv64 SV57 mode gives 56 bits of userspace VA.
++	riscv64AddrBits = 56
++	riscv64CntBits  = 64 - riscv64AddrBits + 3
+ )
+ 
+ func lfstackPack(node *lfnode, cnt uintptr) uint64 {
+ 	if GOARCH == "ppc64" && GOOS == "aix" {
+ 		return uint64(uintptr(unsafe.Pointer(node)))<<(64-aixAddrBits) | uint64(cnt&(1<<aixCntBits-1))
+ 	}
++	if GOARCH == "riscv64" {
++		return uint64(uintptr(unsafe.Pointer(node)))<<(64-riscv64AddrBits) | uint64(cnt&(1<<riscv64CntBits-1))
++	}
+ 	return uint64(uintptr(unsafe.Pointer(node)))<<(64-addrBits) | uint64(cnt&(1<<cntBits-1))
+ }
+ 
+@@ -54,5 +61,8 @@ func lfstackUnpack(val uint64) *lfnode {
+ 	if GOARCH == "ppc64" && GOOS == "aix" {
+ 		return (*lfnode)(unsafe.Pointer(uintptr((val >> aixCntBits << 3) | 0xa<<56)))
+ 	}
++	if GOARCH == "riscv64" {
++		return (*lfnode)(unsafe.Pointer(uintptr(val >> riscv64CntBits << 3)))
++	}
+ 	return (*lfnode)(unsafe.Pointer(uintptr(val >> cntBits << 3)))
+ }
+-- 
+2.35.1
+