10

I'm grading C and C++ files for a class, and this assignment uses the GSL library. Since I don't have root permission on my computer, my GSL library is installed in my home directory, and thus I need to tell compilers and linkers where to find it.

This isn't a problem when I write a program myself, because I just add the appropriate -L and -I flags to gcc.

But when I'm compiling student's files, I don't want to edit every one of their makefiles. Instead, I want to put the appropriate directories into an environment variable, so that it happens seamlessly.

To this end, I've exported the following variables with the library or include locations: C_INCLUDE_PATH, CPLUS_INCLUDE_PATH, LIBRARY_PATH and LD_LIBRARY_PATH

But when I compile a student's project, with

gcc -Wall -o MC_thread MC_thread.c -lgsl -lgslcblas -lpthread -lm

I get the following error:

/usr/bin/ld: cannot find -lgsl
collect2: ld returned 1 exit status
make: *** [all] Error 1

I'm using gcc v 4.1.2. I actually don't get the error if I use gcc v 4.4, but I have no clue why. My linker is:

ld -V
GNU ld version 2.17.50.0.6-12.el5 20061020.
Stephen
  • 523
  • 1
  • 6
  • 16
  • 1
    Try man ld and man ld.so for environment vars they use. LD_LIBRARY_PATH might work. – Eugene Feb 09 '10 at 05:24
  • 2
    I think LD_LIBRARY_PATH is only used by ld.so, not by ld. Since this is a compile-time error, not a run-time error, I would focus on why LIBRARY_PATH doesn't work. Two things I would verify, does the library file have the correct name and is LIBRARY_PATH actually defined in the gcc execution environment? – Per Knytt Feb 13 '10 at 10:21
  • Try running gcc with the '-v' option and post the complete ld invokation from the output. – Per Knytt Feb 13 '10 at 10:27

4 Answers4

12

You could try using the environment variable LIBRARY_PATH

From man gcc (at least version 4.4)

       LIBRARY_PATH
           The value of LIBRARY_PATH is a colon-separated list of directories,
           much like PATH.  When configured as a native compiler, GCC tries
           the directories thus specified when searching for special linker
           files, if it can't find them using GCC_EXEC_PREFIX.  Linking using
           GCC also uses these directories when searching for ordinary
           libraries for the -l option (but directories specified with -L come
           first).

And then then use LD_LIBRARY_PATH when you run their programs to to let the run-time linker find the libraries.

Kjetil Joergensen
  • 1,595
  • 11
  • 10
3

A lot of the answers above suggest the use of LD_LIBRARY_PATH. But this is incorrect since that is an environmental variable for the dynamic (runtime) linker, not the compile time linker ld.

The correct way to do this is to require the students to append something like:

-L$(EXTRA_LINK_DIRECTORY)

in their Makefile at the point at which they define the build rule. Then, when you compile, do something like:

export EXTRA_LINK_DIRECORY=/home/...

1

If you're on a 64-bit machine, that's probably the problem. OMM, gcc 4.1 doesn't search the paths specified in LIBRARY_PATH, but rather path/../lib64. You'll need to specify -L directly, or symlink the directory to lib64 at the same level, or mess with the gcc specs.

See http://gcc.gnu.org/ml/gcc-help/2010-11/msg00360.html and Why does g++ look in LIBRARY_PATH/../lib64 and where is this documented?

(OMM, this does work with gcc 4.5 without any messing around, so I'm guessing they fixed it later on.)

Community
  • 1
  • 1
jtniehof
  • 581
  • 3
  • 8
  • Playing with the spec file doesn't help much, either, since making it search only lib means gcc doesn't find its internal bits, and making it search both lib and lib64 means gcc spits a bunch of warnings for the incompatible 32-bit versions it finds. – jtniehof Feb 13 '13 at 21:02
  • that was probably it! Since I installed GSL myself I didn't have both the lib/ and lib64/ directories, rather just one location with the (64-bit) libraries but without the expected lib64/ name. That's quite an annoying feature. I guess gcc 4.4 and 4.5 have better behavior – Stephen Feb 14 '13 at 22:05
0

My advice is to require students to support a CFLAGS environment variable in their makefiles, Or else they fail. :) Then you can export CFLAGS="-Lwhatever".

Or you could use LD_LIBRARY_PATH.

Max E.
  • 1,837
  • 13
  • 15
  • You probably mean LDFLAGS, since -l and -L are linker parameters, not compiler-stage parameters. But yes, I agree. Makefiles without these variables are useless. –  Feb 20 '10 at 23:30