TL;DR:
How do I get from having the source for DerelictGL3 et al, to linking to it, with GDC?
Detailed complaints:
I have a small program written in D. (http://dlang.org)
module controller;
import std.stdio;
import std.conv;
import std.exception;
import derelict.opengl3.gl3;
import derelict.glfw3.glfw3;
void main()
{
DerelictGL3.load();
DerelictGLFW3.load();
if(!glfwInit())
throw new Exception("Failure");
scope(exit) glfwTerminate();
}
I'm trying to build this program with the following command. (I'm on linux.)
gdc -o "${BLD}controller" \
"/home/user/Source/d/controller.d" \
"-I/home/user/Source/DerelictOrg/DerelictUtil/source/" \
"-I/home/user/Source/DerelictOrg/DerelictGL3/source/" \
"-I/home/user/Source/DerelictOrg/DerelictGLFW3/source/" \
-I/usr/include/d2 \
-L -lDerelictUtil \
-L -lDerelictGL3 \
-L -lDerelictGLFW3 \
-L -ldl
I get the following error messages.
controller.d:(.text+0x3b): undefined reference to
`_D8derelict7opengl33gl311DerelictGL3C8derelict7opengl33gl317DerelictGL3Loader'
controller.d:(.text+0x4c): undefined reference to
`_D8derelict7opengl33gl311DerelictGL3C8derelict7opengl33gl317DerelictGL3Loader'
controller.d:(.text+0x58): undefined reference to
`_D8derelict5glfw35glfw313DerelictGLFW3C8derelict5glfw35glfw319DerelictGLFW3Loader'
controller.d:(.text+0x69): undefined reference to
`_D8derelict5glfw35glfw313DerelictGLFW3C8derelict5glfw35glfw319DerelictGLFW3Loader'
controller.d:(.text+0x75): undefined reference to
`_D8derelict5glfw35glfw38glfwInitPUNbZi'
controller.d:(.text+0xf7): undefined reference to
`_D8derelict5glfw35glfw313glfwTerminatePUNbZv'
/tmp/ccTqE9NN.o:(.data+0x28): undefined reference to
`_D8derelict7opengl33gl312__ModuleInfoZ'
/tmp/ccTqE9NN.o:(.data+0x30): undefined reference to
`_D8derelict5glfw35glfw312__ModuleInfoZ'
collect2: error: ld returned 1 exit status
I'm fairly certain that none of the arguments I'm passing to GDC are correct, past the name of my source file. The behavior is identical if I comment out all the -L lines. If I comment out the -I lines, I get the following.
controller.d:6: error: module gl3 is in file 'derelict/opengl3/gl3.d'
which cannot be read
However, I expect that could be resolved with a well placed library.
How do I get from having the source for DerelictGL3 et al, to linking to it, with GDC?
Edit: I'm confident I've installed libDerelictGL3.a, libDerelictGLFW3.a, and libDerelictUtil.a in /usr/bin/.
More thoughts: I'm really quite confused as to why I need to compile against the source. This isn't C++ and there are no header files. When I forego the -I lines, the compiler doesn't know how to open the gl3 module. Shouldn't it just infer that the functions I used exist, and then have linker errors if/when it cannot find them? Given as I have the libraries compiled and in the search path, why can't GDC figure the rest out?
More thoughts: I recently found Can't link GLFW3: undefined references In that case, the OP found that they needed their libraries in .so form, rather than .a form, since they were attempting a dynamic link. I'm currently investigating that.
Another piece of the puzzle: I've changed the relevant portion of my gdc call to
-I/usr/include/d2 \
-L -ldl \
-L/usr/bin \
-lDerelictUtil \
-lDerelictGL3 \
-lDerelictGLFW3
Now, rather than having trouble linking to Derelict, I appear to be having trouble linking to the _d_runtime itself.
Output is hundreds of lines similar to these:
/usr/bin/libDerelictGL3.a(libDerelictGL3.o): In function
`_D3std5array18__T8AppenderTAPxaZ8Appender13ensureAddableMFNaNbNfmZv':
/home/user/Source/ldc-developers/ldc/runtime/phobos/std/array.d:2231:
undefined reference to `_d_allocmemoryT'
Thus, I believe that my problem is that _d_runtime (forgive me if that's the wrong name) is somewhere other than /usr/bin, and when I override my -L path to /usr/bin (since that's where I put the libs) I have problems finding it. Either that, or I simply installed D wrong in the first place. But in either case, it is actually finding libDerelictGL3.a in the aforementioned example! =)
Edit: I suppose I left out the actual line to build Derelict with gdc.
dub --compiler=gdc
I executed this in the source directory of each of the derelict packages, and copied the contents of lib/ to /usr/bin.
I've figured it out. Time for a thorough post-mordem "for the next guy".
I started this project some time ago, and I forgot that I had started off using ldc, an llvm based D compiler. For some reason, I symlinked /usr/bin/dmd2 to a local build of ldmd2, sitting as a fresh binary in a source directory. My build of the various DerelictOrg projects used dub, which then used ldmd2, and thus a local, probably forked, copy of the d runtime.
Basically, the rest of the project was setup correctly. For the sake of the next guy, here's what my script ended up as:
gdc -o "/home/user/Build/controller" \
"/home/user/Source/d/controller.d" \
-I/usr/include/d \
"-I/home/user/Source/DerelictOrg/DerelictUtil/source/" \
"-I/home/user/Source/DerelictOrg/DerelictGL3/source/" \
"-I/home/user/Source/DerelictOrg/DerelictGLFW3/source/" \
-lDerelictUtil \
-lDerelictGL3 \
-lDerelictGLFW3 \
-ldl
Humorously enough, the ldc vs gdc mistake made it all the way to the log I posted here. Too bad I didn't read my own log closely enough.