1

I have tried searching around other questions here on SO, but have still been unable to get my newly created C++ and .h linked to my main C file correctly. My implementation of my loader.cpp and loader.h are based off of this SO question.

My loader.cpp has no main function as I just want to use the C++ functions there. My shift.c file is where my int main() is located. Here is the basic structure of my loader.cpp file.

loader.cpp

#include "loader.h"
...
// Class Declaration
...
// Class implementation

I have been trying to compile with the following.

g++ loader.cpp -o obj -lGLU -lGL -lglut

The error I am getting here is...

(.text+0x20): undefined reference `to main'

So my two questions are, how do I get my cpp file to compile properly, and then what do I need to add to my Makefile to link them properly?

Makefile (for reference)

CC = gcc
CXX = g++

EXE = shift gears

# Main target
all: $(EXE)

CFLG=-O3 -Wall
LIBS=-lglut -lGLU -lGL -lm

CLEAN=rm -f $(EXE) *.o *.a


# Dependencies
gears.o: gears.c
shift.o: shift.c CSCIx229.h
fatal.o: fatal.c CSCIx229.h
loadtexbmp.o: loadtexbmp.c CSCIx229.h
print.o: print.c CSCIx229.h
project.o: project.c CSCIx229.h
errcheck.o: errcheck.c CSCIx229.h
object.o: object.c CSCIx229.h

#  Create archive
CSCIx229.a:fatal.o loadtexbmp.o print.o project.o errcheck.o object.o
    ar -rcs $@ $^

# Compile rules
.c.o:
    gcc -c $(CFLG) $<
.cpp.o:
    g++ -c $(CFLG) $<

#  Link
shift:shift.o CSCIx229.a
    gcc -O3 -o $@ $^   $(LIBS)

gears:gears.o
    gcc -O3 -o $@ $^   $(LIBS)

#  Clean
clean:
    $(CLEAN)
Community
  • 1
  • 1
Scalahansolo
  • 2,615
  • 6
  • 26
  • 43

2 Answers2

2

If you want g++ to compile an object module without linking it into a complete program then you must give it the -c option:

g++ -c loader.cpp -o loader.o

Note that that compilation command also assigns a conventional name to the generated object file, and that if you're not linking it into an executable then you don't need to specify libraries to link it to. Your Makefile is already set up for this.

If you add loader.o to the dependencies of CSCIx229.a then that should be enough to persuade make to build it from loader.cpp and to include the object file in your library (which will make it available for linking into your executables). You may also need to add some or all of -lGLU -lGL -lglut to your LIBS variable. It might also be appropriate to add loader.o's dependencies to the makefile if they include more than just loader.cpp itself (e.g. if they include CSCIx229.h).

John Bollinger
  • 160,171
  • 8
  • 81
  • 157
  • Right. The tl;dr version here is "treat `loader.o` the way you treat the other `.o` files you are using in that library and it should Just Work". – Etan Reisner Dec 04 '14 at 17:20
0

Add the -c option to compile only. When you are ready to link the final application, then include all the object files and the list of libraries.

g++ -c loader.cpp -o loader.o
g++ loader.o (and the rest of your object files)  -lGLU -lGL -lglut

Try adding this to your makefile:

shift:shift.o CSCIx229.a loader.o
    gcc -O3 -o $@ $^   $(LIBS)
George Houpis
  • 1,729
  • 1
  • 9
  • 5