使用Cgo时出现“动态符号意外R_X86_64_64重定位”

I am trying to create binding for a C library using Cgo. I have package which uses Cgo to import the library and make some calls to it. It compiles and installs fine. But when trying to use that package from a Go program, I get the the error "unexpected R_X86_64_64 relocation for dynamic symbol" when linking.

Any ideas?

It appears in the assembly generation routines in the 6g compiler:

case 256 + R_X86_64_64:
        if(targ->dynimpname != nil && !targ->dynexport)
                diag("unexpected R_X86_64_64 relocation for dynamic symbol %s",
                     targ->name);
        r->type = D_ADDR;
        return;

The R_X86_64_64 is a type of a symbol in the library. For more information about relocation in the amd64 architecture consult page ~70 here.

Is it possible that you mix 386 compiled library with amd64 code?

The compiler should report the exact symbol which caused the problem. Can you try linking with a minimal library containing other symbols, and try to locate a minimal example where it fails?

Did you manage to use cgo with any library at all?

I agree with Elazar that it seems plausible that mixing of 32-bit and 64-bit code is involved.

Have you tried gccgo?

Works like a charm :

root@Ubuntu-1304-raring-64-minimal:/etc# uname -a
Linux Ubuntu-1304-raring-64-minimal 3.8.13.4 #2 SMP Mon Jul 8 23:59:05 CEST 2013 x86_64 x86_64 x86_64 GNU/Linux

do this sequence :

cd /usr/local
mkdir /var/go
apt-get install mercurial
hg clone https://code.google.com/p/go/

After that create a /etc/profile.d/go.sh with the follewing contents and make it executable:

export GOPATH=/var/go
export GOROOT=/usr/local/go
export GOBIN=$GOPATH/bin
export PATH=$PATH:$GOBIN
export GOROOT_FINAL=/var/go
export GOHOSTARCH=amd64
export GOARCH=amd64
export CGO_ENABLED=1

And then restart your shell. NO source xxx will be working properly - be warned! In a new shell do this :

cd /usr/local/go/src
./make.bash

do the thing, and then copy all the things from /usr/local/go to /var/go - or there's a way to merge both directories by symlink, whatever you prefer. After that comment GOROOT_FINAL in go.sh script above AND restart your shell again. And you're ok with latest working Go language!

root@Ubuntu-1304-raring-64-minimal:/usr/work/golang/go/src# go version
go version devel +35d5bae6aac8 Fri Oct 18 10:45:19 2013 +0400 linux/amd64

Note bene : Two shell restarts are required - found it myself in a hard way.