Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

cmd/go: go1.11.4 toolchain3 build fail with "slice bounds out of range" on 32-bit MIPS on Debian buildd #29402

Closed
anthonyfok opened this issue Dec 23, 2018 · 14 comments

Comments

Projects
None yet
5 participants
@anthonyfok
Copy link

commented Dec 23, 2018

go1.11.4 fails to build toolchain3 with a "panic: runtime error: slice bounds out of range" on 32-bit MIPS architectures (mips, mipsel (or mipsle)) on Debian buildd. This seems to be a new problem because go1.11.2 and go1.11.3 built fine.

Here is where it failed:

Building Go cmd/dist using /usr/lib/go-1.10.
go: disabling cache (/sbuild-nonexistent/.cache/go-build) due to initialization failure: mkdir /sbuild-nonexistent: permission denied
Building Go toolchain1 using /usr/lib/go-1.10.
Building Go bootstrap cmd/go (go_bootstrap) using Go toolchain1.
Building Go toolchain2 using go_bootstrap and Go toolchain1.
Building Go toolchain3 using go_bootstrap and Go toolchain2.
# unicode
panic: runtime error: slice bounds out of range

goroutine 1 [running]:
cmd/compile/internal/gc.(*exprSwitch).walkCases(0x1bf39a0, 0x201aec0, 0x4, 0x4, 0x201aec0)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/swt.go:396 +0x918
cmd/compile/internal/gc.(*exprSwitch).walk(0x1bf39a0, 0x16c0b40)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/swt.go:325 +0x380
cmd/compile/internal/gc.walkswitch(0x16c0b40)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/swt.go:234 +0xa8
cmd/compile/internal/gc.walkstmt(0x16c0b40, 0x8)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/walk.go:346 +0xd64
cmd/compile/internal/gc.walkstmtlist(0x165bbd8, 0x2, 0x2)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/walk.go:79 +0x90
cmd/compile/internal/gc.walkstmt(0x16c09b0, 0x4)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/walk.go:286 +0x1208
cmd/compile/internal/gc.walkstmtlist(0x1ae95d0, 0x4, 0x4)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/walk.go:79 +0x90
cmd/compile/internal/gc.walk(0x16b46c0)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/walk.go:63 +0x22c
cmd/compile/internal/gc.compile(0x16b46c0)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/pgen.go:223 +0x80
cmd/compile/internal/gc.funccompile(0x16b46c0)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/pgen.go:209 +0xf4
cmd/compile/internal/gc.Main(0x96654c)
	/usr/lib/go-1.11/src/cmd/compile/internal/gc/main.go:641 +0x290c
main.main()
	/usr/lib/go-1.11/src/cmd/compile/main.go:51 +0xac
# math
panic: runtime error: slice bounds out of range
...
# runtime
panic: runtime error: slice bounds out of range
...

See full build logs here:

Sorry, I haven't had the time to try to study this in depth by logging into Debian's remote 32-bit MIPS machine yet, but thought I should try my luck here first. :-) Many thanks!

@anthonyfok anthonyfok changed the title go1.11.4 toolchain3 build fail with "slice bounds out of range" on Debian buildd go1.11.4 toolchain3 build fail with "slice bounds out of range" on 32-bit MIPS on Debian buildd Dec 23, 2018

@randall77

This comment has been minimized.

Copy link
Contributor

commented Dec 23, 2018

Weird. The code does:

var a []T = ...
half := len(a)/2
_, _ = a[:half], a[half:]

Which should not be able to panic.
Could be a bug in the compiler, though.

I can't seem to gomote a linux-mips or linux-mipsle machine. Someone with access to such a machine care to verify and do a bisect?

@ALTree ALTree changed the title go1.11.4 toolchain3 build fail with "slice bounds out of range" on 32-bit MIPS on Debian buildd cmd/go: go1.11.4 toolchain3 build fail with "slice bounds out of range" on 32-bit MIPS on Debian buildd Dec 23, 2018

@anthonyfok

This comment has been minimized.

Copy link
Author

commented Dec 25, 2018

Hi Randall,

Thank you for the suggestion!

I have finally sat down and got a "schroot" environment set up on the Debian mipsel and mips development machines and got a "git bisect run" going on both machines:

git bisect start go1.11.4 go1.11.3
git bisect run ../build-go.sh

where ../build-go.sh has this:

#!/bin/sh
cd src
./make.bash

I will go back check the result in a few hours. :-)

Have a Happy Christmas! 🎄

@anthonyfok

This comment has been minimized.

Copy link
Author

commented Dec 25, 2018

Here is the result of git bisect test, identical on both mips and mipsel:

...

Bisecting: 0 revisions left to test after this (roughly 0 steps)
[bdc7d5677edd1dab21cdaa1f6498e0c2a6c9d7bf] [release-branch.go1.11] cmd/compile: 
check for negative upper bound to IsSliceInBounds
running ../build-go.sh
Building Go cmd/dist using /usr/lib/go-1.10.
Building Go toolchain1 using /usr/lib/go-1.10.
Building Go bootstrap cmd/go (go_bootstrap) using Go toolchain1.
Building Go toolchain2 using go_bootstrap and Go toolchain1.
Building Go toolchain3 using go_bootstrap and Go toolchain2.
# unicode
panic: runtime error: slice bounds out of range

goroutine 1 [running]:
cmd/compile/internal/gc.(*exprSwitch).walkCases(0x1bb99a0, 0x1fe4ec0, 0x4, 0x4, 0x1fe4ec0)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:396 +0x918
cmd/compile/internal/gc.(*exprSwitch).walk(0x1bb99a0, 0x1694370)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:325 +0x380
cmd/compile/internal/gc.walkswitch(0x1694370)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:234 +0xa8
cmd/compile/internal/gc.walkstmt(0x1694370, 0x8)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:346 +0xd64
cmd/compile/internal/gc.walkstmtlist(0x185f6c8, 0x2, 0x2)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:79 +0x90
cmd/compile/internal/gc.walkstmt(0x16941e0, 0x4)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:286 +0x1208
cmd/compile/internal/gc.walkstmtlist(0x1bbb5c0, 0x4, 0x4)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:79 +0x90
cmd/compile/internal/gc.walk(0x165a780)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:63 +0x22c
cmd/compile/internal/gc.compile(0x165a780)
        /home/foka/git/go/src/cmd/compile/internal/gc/pgen.go:223 +0x80
cmd/compile/internal/gc.funccompile(0x165a780)
        /home/foka/git/go/src/cmd/compile/internal/gc/pgen.go:209 +0xf4
cmd/compile/internal/gc.Main(0x96656c)
        /home/foka/git/go/src/cmd/compile/internal/gc/main.go:641 +0x2910
main.main()
        /home/foka/git/go/src/cmd/compile/main.go:51 +0xac
# math  
panic: runtime error: slice bounds out of range

goroutine 1 [running]:
cmd/compile/internal/gc.(*exprSwitch).walkCases(0x1e798b4, 0x1da1a80, 0x4, 0x4, 0x1da1a80)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:396 +0x918
cmd/compile/internal/gc.(*exprSwitch).walk(0x1e798b4, 0x1c6c8c0)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:325 +0x380
cmd/compile/internal/gc.walkswitch(0x1c6c8c0)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:234 +0xa8
cmd/compile/internal/gc.walkstmt(0x1c6c8c0, 0x1c6c820)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:346 +0xd64
cmd/compile/internal/gc.walkstmtlist(0x1bfe7c0, 0x6, 0x8)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:79 +0x90
cmd/compile/internal/gc.walkstmt(0x1c6c6e0, 0x1c6c230)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:286 +0x1208
cmd/compile/internal/gc.walkstmtlist(0x1c769f8, 0x1, 0x2)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:79 +0x90
cmd/compile/internal/gc.walkstmt(0x1c6c5a0, 0x1c6c500)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:286 +0x1208
cmd/compile/internal/gc.walkstmtlist(0x1da1540, 0xf, 0x10)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:79 +0x90
cmd/compile/internal/gc.walk(0x1c16900)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:63 +0x22c
cmd/compile/internal/gc.compile(0x1c16900) 
        /home/foka/git/go/src/cmd/compile/internal/gc/pgen.go:223 +0x80
cmd/compile/internal/gc.funccompile(0x1c16900)
        /home/foka/git/go/src/cmd/compile/internal/gc/pgen.go:209 +0xf4
cmd/compile/internal/gc.Main(0x96656c)
        /home/foka/git/go/src/cmd/compile/internal/gc/main.go:641 +0x2910
main.main()
        /home/foka/git/go/src/cmd/compile/main.go:51 +0xac
# runtime
panic: runtime error: slice bounds out of range

goroutine 1 [running]:
cmd/compile/internal/gc.(*exprSwitch).walkCases(0x30b9a8c, 0x20ba300, 0xb, 0x10, 0x20ba300)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:396 +0x918
cmd/compile/internal/gc.(*exprSwitch).walk(0x30b9a8c, 0x1c12190)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:325 +0x380
cmd/compile/internal/gc.walkswitch(0x1c12190)
        /home/foka/git/go/src/cmd/compile/internal/gc/swt.go:234 +0xa8
cmd/compile/internal/gc.walkstmt(0x1c12190, 0x1c0bf90)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:346 +0xd64
cmd/compile/internal/gc.walkstmtlist(0x293b180, 0x13, 0x20)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:79 +0x90
cmd/compile/internal/gc.walk(0x1c02180)
        /home/foka/git/go/src/cmd/compile/internal/gc/walk.go:63 +0x22c
cmd/compile/internal/gc.compile(0x1c02180) 
        /home/foka/git/go/src/cmd/compile/internal/gc/pgen.go:223 +0x80
cmd/compile/internal/gc.funccompile(0x1c02180)
        /home/foka/git/go/src/cmd/compile/internal/gc/pgen.go:209 +0xf4
cmd/compile/internal/gc.Main(0x96656c)
        /home/foka/git/go/src/cmd/compile/internal/gc/main.go:641 +0x2910
main.main()
        /home/foka/git/go/src/cmd/compile/main.go:51 +0xac
go tool dist: FAILED: /home/foka/git/go/pkg/tool/linux_mipsle/go_bootstrap install -gcflags=all= -ldflags=all= -a -i cmd/asm cmd/cgo cmd/compile cmd/link: exit status 2
bdc7d5677edd1dab21cdaa1f6498e0c2a6c9d7bf is the first bad commit
commit bdc7d5677edd1dab21cdaa1f6498e0c2a6c9d7bf
Date:   Tue Dec 4 10:00:16 2018 -0500

    [release-branch.go1.11] cmd/compile: check for negative upper bound to IsSliceInBounds

    IsSliceInBounds(x, y) asserts that y is not negative, but
    there were cases where this is not true.  Change code
    generation to ensure that this is true when it's not obviously
    true.  Prove phase cleans a few of these out.

    With this change the compiler text section is 0.06% larger,
    that is, not very much.  Benchmarking still TBD, may need
    to wait for access to a benchmarking box (next week).

    Also corrected run.go to handle '?' in -update_errors output.

    Fixes #28799.

    Change-Id: Ia8af90bc50a91ae6e934ef973def8d3f398fac7b
    Reviewed-on: https://go-review.googlesource.com/c/152477
    Run-TryBot: David Chase <drchase@google.com>
    Reviewed-by: Keith Randall <khr@golang.org>
    TryBot-Result: Gobot Gobot <gobot@golang.org>
    (cherry picked from commit ea6259d5e9d57f247b7d877d4d04602b74ae5155)
    Reviewed-on: https://go-review.googlesource.com/c/153638

:040000 040000 34b03646370c2be9c266fbe248d7424aa466858f ed5ece622de7c63dc9181de93e12126917823c0b M      src
:040000 040000 e2d13d5ad7fa89cdf17e9e209e72b2320bd876c9 5172879f5db0b147c31ae3cfa535f75aba301c87 M      test
bisect run success

Bisect log:

(sid_mipsel-dchroot)foka@eller:~/git/go$ git bisect log
# bad: [4601a4c1b1c00fbe507508f0267ec5a9445bb7e5] [release-branch.go1.11] go1.11.4
# good: [90c896448691b5edb0ab11110f37234f63cd28ed] [release-branch.go1.11-security] go1.11.3
git bisect start 'go1.11.4' 'go1.11.3'
# good: [71b7b4fad3ac6d9ee543b27a9516a9d63ccd9596] [release-branch.go1.11] cmd/link: close input files when copying to temporary directory
git bisect good 71b7b4fad3ac6d9ee543b27a9516a9d63ccd9596
# bad: [928a4b69195f1f408e4cdb6ad4ee41f5f91f4e86] [release-branch.go1.11] cmd/cgo: preserve type information across loadDWARF loop
git bisect bad 928a4b69195f1f408e4cdb6ad4ee41f5f91f4e86
# good: [b86522faa54413930d6e9164973166490babc5de] [release-branch.go1.11] cmd/go/internal/modfetch: skip symlinks in (*coderepo).Zip
git bisect good b86522faa54413930d6e9164973166490babc5de
# bad: [a1d388ebf217d5582c24057cec4ccd053239dfc9] [release-branch.go1.11] doc/go1.11: add note about go run supporting for go run pkg or go run .
git bisect bad a1d388ebf217d5582c24057cec4ccd053239dfc9
# bad: [bdc7d5677edd1dab21cdaa1f6498e0c2a6c9d7bf] [release-branch.go1.11] cmd/compile: check for negative upper bound to IsSliceInBounds
git bisect bad bdc7d5677edd1dab21cdaa1f6498e0c2a6c9d7bf
# first bad commit: [bdc7d5677edd1dab21cdaa1f6498e0c2a6c9d7bf] [release-branch.go1.11] cmd/compile: check for negative upper bound to IsSliceInBounds

See:

@randall77

This comment has been minimized.

Copy link
Contributor

commented Dec 25, 2018

@randall77

This comment has been minimized.

Copy link
Contributor

commented Dec 25, 2018

Thanks for the bisect.

@cherrymui

This comment has been minimized.

Copy link
Contributor

commented Dec 26, 2018

I don't have a MIPS machine on hand, but by visual inspection I think this is mis-compiled. Simple reproducer:

func F(s []int) bool {
	half := len(s)/2
	return half >= 0
}

On tip, I got

"".F STEXT size=12 args=0x10 locals=0x0 leaf
	0x0000 00000 (x.go:3)	TEXT	"".F(SB), LEAF|NOFRAME|ABIInternal, $-4-16
	0x0000 00000 (x.go:3)	FUNCDATA	$0, gclocals·4af967f5c52a6bcdb18ad5576e446d49(SB)
	0x0000 00000 (x.go:3)	FUNCDATA	$1, gclocals·2002e13acf59079a1a5782c918894579(SB)
	0x0000 00000 (x.go:3)	FUNCDATA	$3, gclocals·2002e13acf59079a1a5782c918894579(SB)
	0x0000 00000 (x.go:5)	PCDATA	$2, $0
	0x0000 00000 (x.go:5)	PCDATA	$0, $0
	0x0000 00000 (x.go:5)	MOVB	R0, "".~r1+12(FP)
	0x0004 00004 (x.go:5)	JMP	(R31)
	0x0008 00008 (x.go:5)	NOOP

that is, returning constant false (R0 is the zero register).

In MIPS.rules,

(SGTconst [c] (SRLconst _ [d])) && 0 <= int32(c) && uint32(d) <= 31 && 1<<(32-uint32(d)) <= int32(c) -> (MOVWconst [1])

This rule is problematic. SGTconst is to compare c with the shift _>>d, resulting 1 if c > (_>>d) regardless of the value of _. When c==0 and d==1, 1<<(32-1) <= int32(0) is true when compared as int32, turning to the wrong result. Will send a CL.

@gopherbot

This comment has been minimized.

Copy link

commented Dec 26, 2018

Change https://golang.org/cl/155798 mentions this issue: cmd/compile: fix MIPS SGTconst-with-shift rules

@cherrymui

This comment has been minimized.

Copy link
Contributor

commented Dec 26, 2018

@anthonyfok could you test CL https://go-review.googlesource.com/c/go/+/155798 on a MIPS machine? Thanks!

@anthonyfok

This comment has been minimized.

Copy link
Author

commented Dec 26, 2018

@cherrymui You are totally amazing! I think you have nailed the problem!
On both mips and mipsle, Go toolchain3 builds correctly after applying your CL:

(sid_mipsel-dchroot)foka@eller:~/git/go/src$ ./all.bash 
Building Go cmd/dist using /usr/lib/go-1.10.
Building Go toolchain1 using /usr/lib/go-1.10.
Building Go bootstrap cmd/go (go_bootstrap) using Go toolchain1.
Building Go toolchain2 using go_bootstrap and Go toolchain1.
Building Go toolchain3 using go_bootstrap and Go toolchain2.
Building packages and commands for linux/mipsle.

The tests are still being run. I will report back when all the test results are ready.

Thanks again! And wish you a very Happy Christmas season!

@anthonyfok

This comment has been minimized.

Copy link
Author

commented Dec 26, 2018

@cherrymui The full build logs are in:

@cherrymui

This comment has been minimized.

Copy link
Contributor

commented Dec 26, 2018

@anthonyfok Thank you!

@gopherbot gopherbot closed this in 6a64efc Dec 27, 2018

@anthonyfok

This comment has been minimized.

Copy link
Author

commented Dec 28, 2018

@gopherbot please consider this for backport to 1.11, otherwise release-branch.go1.11 would fail to build on 32-bit MIPS. Thanks!

@gopherbot

This comment has been minimized.

Copy link

commented Dec 28, 2018

Backport issue(s) opened: #29442 (for 1.11).

Remember to create the cherry-pick CL(s) as soon as the patch is submitted to master, according to https://golang.org/wiki/MinorReleases.

@gopherbot

This comment has been minimized.

Copy link

commented Dec 28, 2018

Change https://golang.org/cl/155799 mentions this issue: [release-branch.go1.11] cmd/compile: fix MIPS SGTconst-with-shift rules

gopherbot pushed a commit that referenced this issue Jan 4, 2019

[release-branch.go1.11] cmd/compile: fix MIPS SGTconst-with-shift rules
(SGTconst [c] (SRLconst _ [d])) && 0 <= int32(c) && uint32(d) <= 31 && 1<<(32-uint32(d)) <= int32(c) -> (MOVWconst [1])

This rule is problematic. 1<<(32-uint32(d)) <= int32(c) meant to
say that it is true if c is greater than the largest possible
value of the right shift. But when d==1, 1<<(32-1) is negative
and results in the wrong comparison.

Rewrite the rules in a more direct way.

Updates #29402.
Fixes #29442.

Change-Id: I5940fc9538d9bc3a4bcae8aa34672867540dc60e
Reviewed-on: https://go-review.googlesource.com/c/155798
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Keith Randall <khr@golang.org>
(cherry picked from commit 6a64efc)
Reviewed-on: https://go-review.googlesource.com/c/155799
Reviewed-by: David Chase <drchase@google.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.