Error when linking libv8_base.a into a shared object on x64 linux

1,191 views
Skip to first unread message

Charles Lowell

unread,
Jul 1, 2012, 8:33:02 PM7/1/12
to v8-u...@googlegroups.com
Hi,

I'm trying to build a shared object and link in the static v8 library. This works fine for me on OSX, but on Linux I get the following error:

    /usr/bin/ld: /tmp/build_321giz8disep/vendor/v8/out/x64.release/obj.target/v8_base/src/api.o: relocation R_X86_64_32S against `vtable for v8::ScriptData' can not be used when making a shared object; recompile with -fPIC
       /tmp/build_321giz8disep/vendor/v8/out/x64.release/obj.target/tools/gyp/libv8_base.a: could not read symbols: Bad value
       collect2: ld returned 1 exit status

Is there a way to tell GYP to build a static v8 library with -fPIC? Is there a way to do this without patching one of the gypfiles?

cheers,
Charles

Michael Schwartz

unread,
Jul 1, 2012, 10:39:55 PM7/1/12
to v8-u...@googlegroups.com
make GYPFLAGS="-Dcomponent=shared_library"

I think the default is static library for OSX (x64).

Mixing static and shared libraries is really difficult with the GNU tools.  OSX uses the LLVM tool chain, which is similar but has significant differences.

If you're building a 64-bit version on a 32-bit system, it could be that v8 is so big that 32-bit relocations in the code segments of the library are not enough bits.


Charles Lowell

unread,
Jul 2, 2012, 1:38:06 AM7/2/12
to v8-u...@googlegroups.com


On Sunday, July 1, 2012 9:39:55 PM UTC-5, mschwartz wrote:
make GYPFLAGS="-Dcomponent=shared_library"

Unfortunately, I need to build a static library. If I monkey patch standalone.gypi to put in the -fPIC flag then it works fine, but it would be nice if there were a way to specify this from the command line.

Michael Schwartz

unread,
Jul 2, 2012, 6:50:47 AM7/2/12
to v8-u...@googlegroups.com
Try make GYPFLAGS="-Dcomponent=static_library"

Jakob Kummerow

unread,
Jul 2, 2012, 6:57:12 AM7/2/12
to v8-u...@googlegroups.com

On Mon, Jul 2, 2012 at 12:50 PM, Michael Schwartz <myk...@gmail.com> wrote:
Try make GYPFLAGS="-Dcomponent=static_library"

That is the default and doesn't change anything.
 
On Jul 1, 2012, at 10:38 PM, Charles Lowell wrote:

On Sunday, July 1, 2012 9:39:55 PM UTC-5, mschwartz wrote:
make GYPFLAGS="-Dcomponent=shared_library"

Unfortunately, I need to build a static library. If I monkey patch standalone.gypi to put in the -fPIC flag then it works fine, but it would be nice if there were a way to specify this from the command line.

Adding a line to either standalone.gypi or common.gypi sounds like an easy enough solution, no?
Alternatively, you could try setting environment variables. I'm not sure if regular g++ invocations honor CXXFLAGS, but setting CXX="g++ -fPIC" should do the trick either way. (You might need to set LDFLAGS and/or LINK too.)

Michael Schwartz

unread,
Jul 2, 2012, 7:13:13 AM7/2/12
to v8-u...@googlegroups.com
On OSX Lion, make without the -Dcomponent=shared_library built shared, dynamic, and debug versions.

The more interesting question is why he thinks he needs -fPIC for a static library.  The error message indicates the elf file contains a 32-bit relocation and it needs to be a 64-bit one.  

Position Independent Code (PIC) is typically (almost always) used in shared libraries.  

Statically linked libraries can have their code loaded at any address, and are loaded  as part of the executable at run time so they don't need to be position independent.  

Shared libraries can be loaded at any address and in any order, so they must be position independent.  Their code segments can be mapped with the MMU into several process' address space, so you don't have the overhead of loading that code into memory twice if you run the program twice at the same time.



On Jul 1, 2012, at 10:38 PM, Charles Lowell wrote:

Stephan Beal

unread,
Jul 2, 2012, 7:39:11 AM7/2/12
to v8-u...@googlegroups.com
On Mon, Jul 2, 2012 at 1:13 PM, Michael Schwartz <myk...@gmail.com> wrote:
The more interesting question is why he thinks he needs -fPIC for a static library.  The error message indicates the elf file contains a 32-bit relocation and it needs to be a 64-bit one.  

FWIW: i had the same problem with libsqlite4.a (yes, 4) until i added -fPIC to its build options.
 
Position Independent Code (PIC) is typically (almost always) used in shared libraries.  

Ubuntu likes it to always be set :/.

--
----- stephan beal
http://wanderinghorse.net/home/stephan/

mschwartz

unread,
Jul 2, 2012, 7:54:19 AM7/2/12
to v8-u...@googlegroups.com
I'm not so familiar with the 64 bit versions of Linux, but the 32 bit ones used the MMU to map each process identically.  All programs were loaded at the same logical address in each process.  If I remember right, it was loaded toward high memory, leaving low memory available for shared memory, shared libraries, etc.

So a statically linked program would be loaded at that high address, including all the .o files extracted from the .a libraries and physically included in the binary file.  The shared libraries would be loaded at arbitrary addresses in the lower address space.  The "arbitrary" making relocatable binary format all but required (for shared libraries).

At least that's my understanding.

Anyhow, I ran into this issue (the relocation error) when trying to mix static and shared libraries and using dlopen() to load .so files at run time on top of that.  The only solution I found after 10+ hours of trial and error (and reading lots of googled www pages) was to make as much of the linking against dynamic libraries as possible.  Though for some of those dlopen() .so files, linking in entire static libraries worked in some cases.

You can link with static libraries two ways:
-Lpath/to/static/libraries -llibrary
or
liblibrary.a (just like any .o)

The former pulls in the .o's referenced in the .a only.  The latter includes the entire .a (all its .o files) in the resulting binary.

Trevor

unread,
Aug 11, 2012, 9:53:31 PM8/11/12
to v8-u...@googlegroups.com
Michael Schwartz <mykesx <at> gmail.com> writes:

> The more interesting question is why he thinks he needs -fPIC for a static
library.  The error message indicates the elf file contains a 32-bit relocation
and it needs to be a 64-bit one.  
>


I also would like to generate a static lib with pic. I will be linking the
static lib when building a dynamic lib which is loaded via dlopen in a plug-in
system thus the need for pic. Using a dynamic v8 lib means another level of
dynamic libs loaded (2-deep) which makes it more difficult to find missing
symbols, etc. since they don't resolve until runtime.

Marat Abdullin

unread,
Apr 15, 2014, 7:45:45 PM4/15/14
to v8-u...@googlegroups.com
This thing is pretty old but I still have the same problem.
Is there any fix?

I'm building a dynamic library and I'm statically linking V8 (version 3.24.40) in it. On OSX everything is linking just fine, but on Linux I get:

/usr/bin/ld: out/Release/obj.target/deps/v8/tools/gyp/../../../../v8_base.x64/deps/v8/src/accessors.o: relocation R_X86_64_32S against `vtable for v8::internal::StackFrame' can not be used when making a shared object; recompile with -fPIC

out/Release/obj.target/deps/v8/tools/gyp/../../../../v8_base.x64/deps/v8/src/accessors.o: could not read symbols: Bad value

collect2: ld returned 1 exit status


So, I need a way to tell V8 to build static library with -fPIC. Or is there any other fix for this?

--
Marat

Jakob Kummerow

unread,
Apr 16, 2014, 4:23:29 AM4/16/14
to v8-u...@googlegroups.com
If you use GYP for your entire project, things should "just work". Otherwise you'll probably have to modify V8's .gyp files. I'm not sure how, you'll have to find that out for yourself. Try adding -fPIC to the 'cflags' lists in build/toolchain.gypi.


--
---
You received this message because you are subscribed to the Google Groups "v8-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to v8-users+u...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Marat Abdullin

unread,
Apr 16, 2014, 6:29:54 AM4/16/14
to v8-u...@googlegroups.com
I use GYP for my entire project and it doesn't work.

I add V8 using:
    "dependencies": [
        "deps/v8/tools/gyp/v8.gyp:v8",
    ]

with `component` set to `static_library` (and my library's target type is `shared_library`).

Here is an example of compiler call (I use `make V=1` to get this) when it builds V8:

g++ '-DV8_TARGET_ARCH_X64' '-DENABLE_DEBUGGER_SUPPORT' '-DV8_USE_DEFAULT_PLATFORM' '-DENABLE_HANDLE_ZAPPING' -Ideps/v8/src  -fno-strict-aliasing -m64 -fdata-sections -ffunction-sections -O3  -MMD -MF out/Release/.deps/out/Release/obj.host/v8_base.x64/deps/v8/src/accessors.o.d.raw  -c -o out/Release/obj.host/v8_base.x64/deps/v8/src/accessors.o deps/v8/src/accessors.cc

No -fPIC (and quick V8's gyp-files examination shows that -fPIC is being added only in case `component` is set to `shared_library`).

--
Marat

Jakob Kummerow

unread,
Apr 16, 2014, 1:35:13 PM4/16/14
to v8-u...@googlegroups.com
Try depending on 'v8_base.<(v8_target_arch)' and 'v8_snapshot' instead. The 'v8' target is just a meta target, you can probably fold everything it does into your own custom shared library (those dependencies being the most important bits).

Marat Abdullin

unread,
Apr 16, 2014, 5:56:38 PM4/16/14
to v8-u...@googlegroups.com
No positive result.

I've found a dirty hack to enable PIC.
And I've submitted a patch that allows to force PIC to V8. I really hope it will be accepted.

--
Marat

Peter Olsson

unread,
Apr 17, 2014, 8:57:23 AM4/17/14
to v8-u...@googlegroups.com
You can also specify flags when building, I'm doing it like this in one project. It works as expected.

CFLAGS="-fPIC" CXXFLAGS="-fPIC" make native

Jakob Kummerow

unread,
Apr 17, 2014, 9:06:27 AM4/17/14
to v8-u...@googlegroups.com
On Thu, Apr 17, 2014 at 2:57 PM, Peter Olsson <pe...@olssononline.se> wrote:

You can also specify flags when building, I'm doing it like this in one project. It works as expected.

CFLAGS="-fPIC" CXXFLAGS="-fPIC" make native
I think this is easy enough that we don't need to add a GYP option. 

Marat Abdullin

unread,
Apr 17, 2014, 9:36:09 AM4/17/14
to v8-u...@googlegroups.com
No, because of two things:

1. This is an additional requirement to run make with (nobody wants to know these requirements when they build your library).
2. It doesn't work either.

I have my library's gyp-file. It depends on V8's gyp-file. I generate my library's Makefiles with GYP (I use configure script similar to Node.JS). And when I type `CFLAGS="-fPIC" CXXFLAGS="-fPIC" make` in my library to build everything, these cflags are not being passed to V8 compile commands.

--
Marat

Marat Abdullin

unread,
Apr 17, 2014, 10:12:14 AM4/17/14
to v8-u...@googlegroups.com
And, by the way, here is my patch: https://codereview.chromium.org/240473003/patch/1/10001
It is rather simple and works the same way `v8_no_strict_aliasing` works.

In conclusion, I don't build V8 from V8 folder, GYP builds it as my library's dependency, and in this case there is no way to pass cflags for V8 saying CFLAGS="" before make command.

--
Marat

Pete

unread,
Jun 25, 2015, 2:25:48 AM6/25/15
to v8-u...@googlegroups.com
Anyone know what the solution to this is? I am experiencing the same issues statically linking v8 into a shared object and then consuming it. I'm getting a segmentation fault.

Marat Dakota

unread,
Jun 25, 2015, 8:43:35 AM6/25/15
to v8-u...@googlegroups.com
Pete,

I doubt you have the same problem. On Linux, the linkage will fail without -fPIC compiler option (and it could be passed with build command or from GYP-file). You are saying that you're getting segfault, that implies that the linkage was successful.

--
Marat

--
--
v8-users mailing list
v8-u...@googlegroups.com
http://groups.google.com/group/v8-users
---
You received this message because you are subscribed to a topic in the Google Groups "v8-users" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/v8-users/1vva9qjvstE/unsubscribe.
To unsubscribe from this group and all its topics, send an email to v8-users+u...@googlegroups.com.
Reply all
Reply to author
Forward
0 new messages