|
| 1 | +From 98eeeaeaa20279368be0466b24afe44ed24fceb8 Mon Sep 17 00:00:00 2001 |
| 2 | +From: Dmitry Vyukov <dvyukov@google.com> |
| 3 | +Date: Fri, 27 May 2022 18:55:35 +0200 |
| 4 | +Subject: [PATCH] runtime: support riscv64 SV57 mode |
| 5 | + |
| 6 | +Riscv64 has SV57 mode when user-space VA is 56 bits. |
| 7 | +Linux kernel recently got support for this mode and Go binaries started crashing as: |
| 8 | + |
| 9 | +runtime: lfstack.push invalid packing: node=0xffffff5908a940 cnt=0x1 |
| 10 | +packed=0xffff5908a9400001 -> node=0xffff5908a940 |
| 11 | + |
| 12 | +Adjust lfstack code to use only 8 top bits of pointers on riscv64. |
| 13 | + |
| 14 | +For context see: |
| 15 | +https://groups.google.com/g/syzkaller-bugs/c/lU0GQTZoNQQ/m/O_c3vmE3AAAJ |
| 16 | + |
| 17 | +Change-Id: Ib5d3d6a79c0c6eddf11618d73fcc8bc1832a9c25 |
| 18 | + |
| 19 | +Upstream: https://go-review.googlesource.com/c/go/+/409055/3 |
| 20 | +--- |
| 21 | + src/runtime/lfstack_64bit.go | 10 ++++++++++ |
| 22 | + 1 file changed, 10 insertions(+) |
| 23 | + |
| 24 | +diff --git a/src/runtime/lfstack_64bit.go b/src/runtime/lfstack_64bit.go |
| 25 | +index 3f0e480897..9f13e72fa6 100644 |
| 26 | +--- a/src/runtime/lfstack_64bit.go |
| 27 | ++++ b/src/runtime/lfstack_64bit.go |
| 28 | +@@ -36,12 +36,19 @@ const ( |
| 29 | + // We use one bit to distinguish between the two ranges. |
| 30 | + aixAddrBits = 57 |
| 31 | + aixCntBits = 64 - aixAddrBits + 3 |
| 32 | ++ |
| 33 | ++ // Riscv64 SV57 mode gives 56 bits of userspace VA. |
| 34 | ++ riscv64AddrBits = 56 |
| 35 | ++ riscv64CntBits = 64 - riscv64AddrBits + 3 |
| 36 | + ) |
| 37 | + |
| 38 | + func lfstackPack(node *lfnode, cnt uintptr) uint64 { |
| 39 | + if GOARCH == "ppc64" && GOOS == "aix" { |
| 40 | + return uint64(uintptr(unsafe.Pointer(node)))<<(64-aixAddrBits) | uint64(cnt&(1<<aixCntBits-1)) |
| 41 | + } |
| 42 | ++ if GOARCH == "riscv64" { |
| 43 | ++ return uint64(uintptr(unsafe.Pointer(node)))<<(64-riscv64AddrBits) | uint64(cnt&(1<<riscv64CntBits-1)) |
| 44 | ++ } |
| 45 | + return uint64(uintptr(unsafe.Pointer(node)))<<(64-addrBits) | uint64(cnt&(1<<cntBits-1)) |
| 46 | + } |
| 47 | + |
| 48 | +@@ -54,5 +61,8 @@ func lfstackUnpack(val uint64) *lfnode { |
| 49 | + if GOARCH == "ppc64" && GOOS == "aix" { |
| 50 | + return (*lfnode)(unsafe.Pointer(uintptr((val >> aixCntBits << 3) | 0xa<<56))) |
| 51 | + } |
| 52 | ++ if GOARCH == "riscv64" { |
| 53 | ++ return (*lfnode)(unsafe.Pointer(uintptr(val >> riscv64CntBits << 3))) |
| 54 | ++ } |
| 55 | + return (*lfnode)(unsafe.Pointer(uintptr(val >> cntBits << 3))) |
| 56 | + } |
| 57 | +-- |
| 58 | +2.35.1 |
| 59 | + |
0 commit comments