From: Than McIntosh Date: Tue, 15 Dec 2020 20:54:25 +0000 (-0500) Subject: cmd/internal/goobj: fix buglet in object file reader X-Git-Tag: go1.16beta1~5 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=f4e7a6b905ce60448e506a3f6578d01b60602cdd;p=gostls13.git cmd/internal/goobj: fix buglet in object file reader The code in the new (introduced in 1.15) Go object file reader was casting a pointer-mmaped-memory into a large array prior to performing a read of the relocations section: return (*[1<<20]Reloc)(unsafe.Pointer(&r.b[off]))[:n:n] For very large object files, this artificial array isn't large enough (that is, there are more than 1048576 relocs to read), so update the code to use a larger artifical array size. Fixes #41621. Change-Id: Ic047c8aef4f8a3839f2e7e3594bce652ebd6bd5b Reviewed-on: https://go-review.googlesource.com/c/go/+/278492 Run-TryBot: Than McIntosh TryBot-Result: Go Bot Reviewed-by: Cherry Zhang Reviewed-by: Jeremy Faller Trust: Than McIntosh --- diff --git a/src/cmd/internal/goobj/objfile.go b/src/cmd/internal/goobj/objfile.go index 6e76bea111..e6447e455d 100644 --- a/src/cmd/internal/goobj/objfile.go +++ b/src/cmd/internal/goobj/objfile.go @@ -483,6 +483,11 @@ func (r *RefFlags) SetFlag2(x uint8) { r[9] = x } func (r *RefFlags) Write(w *Writer) { w.Bytes(r[:]) } +// Used to construct an artifically large array type when reading an +// item from the object file relocs section or aux sym section (needs +// to work on 32-bit as well as 64-bit). See issue 41621. +const huge = (1<<31 - 1) / RelocSize + // Referenced symbol name. // // Serialized format: @@ -792,7 +797,7 @@ func (r *Reader) Reloc(i uint32, j int) *Reloc { func (r *Reader) Relocs(i uint32) []Reloc { off := r.RelocOff(i, 0) n := r.NReloc(i) - return (*[1 << 20]Reloc)(unsafe.Pointer(&r.b[off]))[:n:n] + return (*[huge]Reloc)(unsafe.Pointer(&r.b[off]))[:n:n] } // NAux returns the number of aux symbols of the i-th symbol. @@ -818,7 +823,7 @@ func (r *Reader) Aux(i uint32, j int) *Aux { func (r *Reader) Auxs(i uint32) []Aux { off := r.AuxOff(i, 0) n := r.NAux(i) - return (*[1 << 20]Aux)(unsafe.Pointer(&r.b[off]))[:n:n] + return (*[huge]Aux)(unsafe.Pointer(&r.b[off]))[:n:n] } // DataOff returns the offset of the i-th symbol's data.