On Thu, May 29, 2014 at 08:55:42AM +1000, Peter Jeremy wrote:
> As I wrote in my initial mail, I am not certain whether this is a problem
> with Go or FreeBSD.  And having done some poking at corefiles with gdb
> (you need gdb7.6 from ports to grok the Go debug information), I have
> found that all my programs are dying at:
>     mov    %gs:0xfffffff8,%ecx
> but it seems to be timing related as to when the offending instruction
> is executed.  I will do some further investigation into how segment
> wraparound is handled.

Hm, I think I know what is going on.  Try this, please.
At least, your test binary worked for me.

diff --git a/sys/amd64/amd64/exception.S b/sys/amd64/amd64/exception.S
index d4e58b1..d51078d 100644
--- a/sys/amd64/amd64/exception.S
+++ b/sys/amd64/amd64/exception.S
@@ -721,21 +721,38 @@ ld_fsbase:
        pushfq
        cli
        movl    $MSR_GSBASE,%ecx
+       /* Save current kernel %gs base into %r12d:%r13d */
        rdmsr
+       movl    %eax,%r12d
+       movl    %edx,%r13d
        .globl  ld_gs
 ld_gs:
        movw    %si,%gs
+       /* Save user %gs base into %r14d:%r15d */
+       rdmsr
+       movl    %eax,%r14d
+       movl    %edx,%r15d
+       /* Restore kernel %gs base */
+       movl    %r12d,%eax
+       movl    %r13d,%edx
        wrmsr
        popfq
+       /*
+        * Restore user %gs base, either from PCB if used for TLS, or
+        * from the previously saved msr read.
+        */
+       movl    $MSR_KGSBASE,%ecx
        cmpw    $KUG32SEL,%si
        jne     1f
-       movl    $MSR_KGSBASE,%ecx
        movl    PCB_GSBASE(%r8),%eax
        movl    PCB_GSBASE+4(%r8),%edx
+       jmp     ld_gsbase
+1:
+       movl    %r14d,%eax
+       movl    %r15d,%edx
        .globl  ld_gsbase
 ld_gsbase:
-       wrmsr
-1:
+       wrmsr   /* May trap if non-canonical, but only for TLS. */
        .globl  ld_es
 ld_es:
        movw    TF_ES(%rsp),%es

Attachment: pgp3LpzNAPYhQ.pgp
Description: PGP signature

Reply via email to