2014-06-12 17:00:00

by Kui Zhang

[permalink] [raw]
Subject: Segmentation fault on all golang executables

Hello,

This commit seem to cause Segmentation fault on any of my golang executables.

commit 6f121e548f83674ab4920a4e60afb58d4f61b829
Author: Andy Lutomirski <[email protected]>
Date: Mon May 5 12:19:34 2014 -0700

x86, vdso: Reimplement vdso.so preparation in build-time C

golang-go 2:1.2.1-2ubuntu1
amd64
golang-go-linux-amd64 2:1.2.1-2ubuntu1
amd64


/tmp]> go
Segmentation fault

go_seg]> cat a.go
package main

func main(){
println("test")

}

################

(gdb) run
Starting program: go_seg/a

Program received signal SIGSEGV, Segmentation fault.
vdso_parse_symbols (vdso_info=<error reading variable: Attempt to
dereference a generic pointer.>,
version=<error reading variable: Attempt to dereference a generic pointer.>)
at /usr/lib/go/src/pkg/runtime/vdso_linux_amd64.c:279
279 if(ELF64_ST_TYPE(sym->st_info) != STT_FUNC)
(gdb) bt
#0 vdso_parse_symbols (vdso_info=<error reading variable: Attempt to
dereference a generic pointer.>,
version=<error reading variable: Attempt to dereference a generic pointer.>)
at /usr/lib/go/src/pkg/runtime/vdso_linux_amd64.c:279
#1 0x0000000000417228 in runtime.linux_setup_vdso (
argc=<error reading variable: Attempt to dereference a generic pointer.>,
argv=<error reading variable: Attempt to dereference a generic pointer.>)
at /usr/lib/go/src/pkg/runtime/vdso_linux_amd64.c:326
#2 0x000000000041358c in runtime.args (c=<error reading variable:
Attempt to dereference a generic pointer.>,
v=<error reading variable: Attempt to dereference a generic
pointer.>) at /usr/lib/go/src/pkg/runtime/runtime.c:86
#3 0x000000000041a01b in _rt0_go () at
/usr/lib/go/src/pkg/runtime/asm_amd64.s:85
#4 0x0000000000000001 in ?? ()
#5 0x00007fffffffe7b8 in ?? ()
#6 0x0000000000000001 in ?? ()
#7 0x00007fffffffe7b8 in ?? ()
#8 0x0000000000000000 in ?? ()

###########################################

Starting program: /usr/bin/go
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".

Program received signal SIGSEGV, Segmentation fault.
vdso_parse_symbols (vdso_info=<error reading variable: Attempt to
dereference a generic pointer.>,
version=<error reading variable: Attempt to dereference a generic pointer.>)
at /usr/lib/go/src/pkg/runtime/vdso_linux_amd64.c:279
279 if(ELF64_ST_TYPE(sym->st_info) != STT_FUNC)
(gdb) bt
#0 vdso_parse_symbols (vdso_info=<error reading variable: Attempt to
dereference a generic pointer.>,
version=<error reading variable: Attempt to dereference a generic pointer.>)
at /usr/lib/go/src/pkg/runtime/vdso_linux_amd64.c:279
#1 0x0000000000470288 in runtime.linux_setup_vdso (
argc=<error reading variable: Attempt to dereference a generic pointer.>,
argv=<error reading variable: Attempt to dereference a generic pointer.>)
at /usr/lib/go/src/pkg/runtime/vdso_linux_amd64.c:326
#2 0x000000000046bf6c in runtime.args (c=<error reading variable:
Attempt to dereference a generic pointer.>,
v=<error reading variable: Attempt to dereference a generic
pointer.>) at /usr/lib/go/src/pkg/runtime/runtime.c:86
#3 0x000000000047558b in _rt0_go () at
/usr/lib/go/src/pkg/runtime/asm_amd64.s:85
#4 0x0000000000000001 in ?? ()
#5 0x00007fffffffe7d8 in ?? ()
#6 0x0000000000000001 in ?? ()
#7 0x00007fffffffe7d8 in ?? ()
#8 0x0000000000000000 in ?? ()



thanks
Kui.Z


2014-06-12 17:21:00

by Andy Lutomirski

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On Thu, Jun 12, 2014 at 9:59 AM, Kui Zhang <[email protected]> wrote:
> Hello,
>
> This commit seem to cause Segmentation fault on any of my golang executables.

Well, crap. It looks like the Go people took my sample vDSO parser...
and broke it. WTF were they thinking? I should have noticed that
they screwed it up when I was cc'd on this thing:

https://code.google.com/p/go/source/detail?r=56ea40aac72b

but I didn't. Sorry, everyone. And the issue isn't even something
sensibly broken like trying to find vdso symbols in the symbol table.
No, they're using the size of the SHT_DYNSYM section to deduce the
number of entries *in the dynamic table*. This is just completely
wrong.

But even that's not all. They borrowed by error handling, so they
should have silently failed to parse the vdso instead of crashing.
But then they broke it completely by failing to zero the state, so
they're just reading from initialized memory. Grr.

The current offending code is here:

https://code.google.com/p/go/source/browse/src/pkg/runtime/vdso_linux_amd64.c

Since we don't get to break all Go executables, here are two options:

1. Try to keep the whole symbol table intact. This is annoying:
there's a reason I removed it. The linker script doesn't know how big
it is, so it's hard to make it compatible with the vvar table.

2. Write a dummy section table that contains a single empty section of
type SHT_DYNSYM. Hopefully the Go runtime will then get far enough to
fail cleanly. And they can go and write a real ELF parser or copy my
reference parser correctly. (hpa, can you apply my patches to make
the reference parser 32-bit clean?)

--Andy

2014-06-12 17:27:12

by Andy Lutomirski

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On Thu, Jun 12, 2014 at 10:20 AM, Andy Lutomirski <[email protected]> wrote:
> On Thu, Jun 12, 2014 at 9:59 AM, Kui Zhang <[email protected]> wrote:
>> Hello,
>>
>> This commit seem to cause Segmentation fault on any of my golang executables.

Can you send me a golang executable that doesn't work. I just build
the "hello world" example and it works fine -- my copy seems to be
getting lucky and reading zeros in the uninitialized memory :-/

--Andy

2014-06-12 17:37:35

by Andy Lutomirski

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On Thu, Jun 12, 2014 at 10:26 AM, Andy Lutomirski <[email protected]> wrote:
> On Thu, Jun 12, 2014 at 10:20 AM, Andy Lutomirski <[email protected]> wrote:
>> On Thu, Jun 12, 2014 at 9:59 AM, Kui Zhang <[email protected]> wrote:
>>> Hello,
>>>
>>> This commit seem to cause Segmentation fault on any of my golang executables.
>
> Can you send me a golang executable that doesn't work. I just build
> the "hello world" example and it works fine -- my copy seems to be
> getting lucky and reading zeros in the uninitialized memory :-/
>

I filed this:

https://code.google.com/p/go/issues/detail?id=8197

--Andy

2014-06-12 18:38:51

by Andy Lutomirski

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On Thu, Jun 12, 2014 at 10:20 AM, Andy Lutomirski <[email protected]> wrote:
> On Thu, Jun 12, 2014 at 9:59 AM, Kui Zhang <[email protected]> wrote:
>> Hello,
>>
>> This commit seem to cause Segmentation fault on any of my golang executables.
>
> Well, crap. It looks like the Go people took my sample vDSO parser...
> and broke it. WTF were they thinking? I should have noticed that
> they screwed it up when I was cc'd on this thing:
>
> https://code.google.com/p/go/source/detail?r=56ea40aac72b
>
> but I didn't. Sorry, everyone. And the issue isn't even something
> sensibly broken like trying to find vdso symbols in the symbol table.
> No, they're using the size of the SHT_DYNSYM section to deduce the
> number of entries *in the dynamic table*. This is just completely
> wrong.
>
> But even that's not all. They borrowed by error handling, so they
> should have silently failed to parse the vdso instead of crashing.
> But then they broke it completely by failing to zero the state, so
> they're just reading from initialized memory. Grr.
>
> The current offending code is here:
>
> https://code.google.com/p/go/source/browse/src/pkg/runtime/vdso_linux_amd64.c
>
> Since we don't get to break all Go executables, here are two options:
>
> 1. Try to keep the whole symbol table intact. This is annoying:
> there's a reason I removed it. The linker script doesn't know how big
> it is, so it's hard to make it compatible with the vvar table.
>
> 2. Write a dummy section table that contains a single empty section of
> type SHT_DYNSYM. Hopefully the Go runtime will then get far enough to
> fail cleanly. And they can go and write a real ELF parser or copy my
> reference parser correctly. (hpa, can you apply my patches to make
> the reference parser 32-bit clean?)

Sigh.

See attached. It seems to work for me. Can you test it? It'll hurt
performance for Go programs, but I don't feel too bad about that.

--Andy


Attachments:
0001-x86-vdso-Hack-to-keep-64-bit-Go-programs-working.patch (3.87 kB)

2014-06-12 18:41:15

by H. Peter Anvin

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On 06/12/2014 11:38 AM, Andy Lutomirski wrote:
>>
>> 2. Write a dummy section table that contains a single empty section of
>> type SHT_DYNSYM. Hopefully the Go runtime will then get far enough to
>> fail cleanly. And they can go and write a real ELF parser or copy my
>> reference parser correctly. (hpa, can you apply my patches to make
>> the reference parser 32-bit clean?)
>

Could you resend it please?

> Sigh.
>
> See attached. It seems to work for me. Can you test it? It'll hurt
> performance for Go programs, but I don't feel too bad about that.
>

If Google fixes Go, will that address the performance problem?

-hpa

2014-06-12 18:42:55

by Andy Lutomirski

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On Thu, Jun 12, 2014 at 11:41 AM, H. Peter Anvin <[email protected]> wrote:
> On 06/12/2014 11:38 AM, Andy Lutomirski wrote:
>>>
>>> 2. Write a dummy section table that contains a single empty section of
>>> type SHT_DYNSYM. Hopefully the Go runtime will then get far enough to
>>> fail cleanly. And they can go and write a real ELF parser or copy my
>>> reference parser correctly. (hpa, can you apply my patches to make
>>> the reference parser 32-bit clean?)
>>
>
> Could you resend it please?

Yes. I'll send the whole series.

>
>> Sigh.
>>
>> See attached. It seems to work for me. Can you test it? It'll hurt
>> performance for Go programs, but I don't feel too bad about that.
>>
>
> If Google fixes Go, will that address the performance problem?

Yes.

Note that my hack will build a buggy vdso on big-endian hosts. Is
there a way to convert host -> BE yet?

--Andy

2014-06-12 18:49:27

by H. Peter Anvin

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On 06/12/2014 11:42 AM, Andy Lutomirski wrote:
>
> Note that my hack will build a buggy vdso on big-endian hosts. Is
> there a way to convert host -> BE yet?
>

Yes, use <tools/be_byteshift.h>.

-hpa

2014-06-12 18:51:22

by Andy Lutomirski

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On Thu, Jun 12, 2014 at 11:48 AM, H. Peter Anvin <[email protected]> wrote:
> On 06/12/2014 11:42 AM, Andy Lutomirski wrote:
>>
>> Note that my hack will build a buggy vdso on big-endian hosts. Is
>> there a way to convert host -> BE yet?
>>
>
> Yes, use <tools/be_byteshift.h>.

What should I rebase on for that? And wasn't there some header that
was supposed to choose the right include file given the host runtime?

Also, I meant host -> LE, of course, but that should be trivial.

--Andy

>
> -hpa
>
>



--
Andy Lutomirski
AMA Capital Management, LLC

2014-06-12 19:11:52

by H. Peter Anvin

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On 06/12/2014 11:51 AM, Andy Lutomirski wrote:
> On Thu, Jun 12, 2014 at 11:48 AM, H. Peter Anvin <[email protected]> wrote:
>> On 06/12/2014 11:42 AM, Andy Lutomirski wrote:
>>>
>>> Note that my hack will build a buggy vdso on big-endian hosts. Is
>>> there a way to convert host -> BE yet?
>>>
>>
>> Yes, use <tools/be_byteshift.h>.
>
> What should I rebase on for that? And wasn't there some header that
> was supposed to choose the right include file given the host runtime?
>
> Also, I meant host -> LE, of course, but that should be trivial.
>

No need to rebase. My patchset proposes replacing
<tools/be_byteshift.h> and <tools/le_byteshift.h> by a unified
<tools/unaligned.h> but that is not important for this purpose.

host -> LE uses <tools/le_byteshift.h> which is already in use by
vdso2c. Use put_unaligned_leXX().

-hpa

2014-06-13 05:48:00

by Kui Zhang

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

Thanks for the patches. The workaround works.

Stupid idea, maybe something in dmesg to help spark conversions, when
this workaround is hit?

Looks like golang people are close.


Thanks
Kuiz

2014-06-13 05:51:18

by H. Peter Anvin

[permalink] [raw]
Subject: Re: Segmentation fault on all golang executables

On 06/12/2014 10:47 PM, Kui Zhang wrote:
> Thanks for the patches. The workaround works.
>
> Stupid idea, maybe something in dmesg to help spark conversions, when
> this workaround is hit?
>
> Looks like golang people are close.
>

The kernel won't even know.

-hpa