I’ve started working with my first makefile. I’m writing a roguelike in C++ using the libtcod library, and have the following hello world program to test if my environment’s up and running:
#include "libtcod.hpp"
int main()
{
TCODConsole::initRoot(80, 50, "PartyHack");
TCODConsole::root->printCenter(40, 25, TCOD_BKGND_NONE, "Hello World");
TCODConsole::flush();
TCODConsole::waitForKeypress(true);
}
My project directory structure looks like this:
/CppPartyHack
----/libtcod-1.5.1 # this is the libtcod root folder
--------/include
------------libtcod.hpp
----/PartyHack
--------makefile
--------partyhack.cpp # the above code
(while we’re here, how do I do proper indentation? Using those dashes is silly.)
and here’s my makefile:
SRCDIR = .
INCDIR = ../libtcod-1.5.1/include
CFLAGS = $(FLAGS) -I$(INCDIR) -I$(SRCDIR) -Wall
CC = gcc
CPP = g++
.SUFFIXES: .o .h .c .hpp .cpp
$(TEMP)/%.o : $(SRCDIR)/%.cpp
$(CPP) $(CFLAGS) -o $@ -c $<
$(TEMP)/%.o : $(SRCDIR)/%.c
$(CC) $(CFLAGS) -o $@ -c $<
CPP_OBJS = $(TEMP)partyhack.o
all : partyhack
partyhack : $(CPP_OBJS)
$(CPP) $(CPP_OBJS) -o $@ -L../libtcod-1.5.1 -ltcod -ltcod++ -Wl,-rpath,.
clean :
\rm -f $(CPP_OBJS) partyhack
I'm using Ubuntu, and my terminal gives me the following errors:
max@max-desktop:~/Desktop/Development/CppPartyhack/PartyHack$ make
g++ -c -o partyhack.o partyhack.cpp
partyhack.cpp:1:23: error: libtcod.hpp: No such file or directory
partyhack.cpp: In function ‘int main()’:
partyhack.cpp:5: error: ‘TCODConsole’ has not been declared
partyhack.cpp:6: error: ‘TCODConsole’ has not been declared
partyhack.cpp:6: error: ‘TCOD_BKGND_NONE’ was not declared in this scope
partyhack.cpp:7: error: ‘TCODConsole’ has not been declared
partyhack.cpp:8: error: ‘TCODConsole’ has not been declared
make: *** [partyhack.o] Error 1
So obviously, the makefile can't find libtcod.hpp. I've double checked and I'm sure the relative path to libtcod.hpp in INCDIR is correct, but as I'm just starting out with makefiles, I'm uncertain what else could be wrong. My makefile is based off a template that the libtcod designers provided along with the library itself, and while I've looked at a few online makefile tutorials, the code in this makefile is a good bit more complicated than any of the examples the tutorials showed, so I'm assuming I screwed up something basic in the conversion. Thanks for any help.
What happens here, is that
1) make evaluates the target
all, which resolves topartyhack.2) make evaluates the target
partyhack, which resolves to$(CPP_OBJS)3) make evaluates the target
$(CPP_OBJS), which resolves to$(TMP)partyhack.o4) make evaluates the target
$(TMP)partyhack.owhich resolves topartyhack.oThis is because TMP is not defined. Also note that the slash is missing after
$(TMP).5) make evaluates the target
partyhack.o, and applies the implicit ruleg++ -c -o partyhack.o partyhack.cppIt does not apply the rule you specified, namely
$(TEMP)/%.o : $(SRCDIR)/%.cppbecause TEMP is not defined, so this evaluates to/partyhack.o : ./partyhack.cpp, and we are not building/partyhack.obecause we are not in the root directory.6) g++ does not find the include file, because the include directories were not passed to it, because your rule was not applied.
To fix this:
First, you need to define TEMP (see Nick Meyers answer).
Second, you need to change the definition of CPP_OBJS (as Paul R suggested).
This will work if you invoke make inside the directory CppPartyHack/PartyHack.