I currently have a problem with a C++ project I have. I need some tools provided with C++11 but when I want to compile with a Makefile, I have the error :
error This file requires compiler and library support for the ISO C++ 2011 standard. This support is currently experimental, and must be enabled with the -std=c++11 or -std=gnu++11 compiler options.
Here is my Makefile :
.PHONY: clean, mrproper
# var
CXX = g++
EXEC = tablut
LDFLAGS =
CXXFLAGS = -std=c++11 -Wall -Wextra
SRC= partie.cpp pawn.cpp playground.cpp
OBJ= $(SRC:.c=.o)
# commands
all: $(EXEC)
tablut: $(OBJ)
$(CXX) -o tablut $(OBJ) $(LDFLAGS)
%.o: %.cpp
$(CXX) -o $# -c $< $(CXXFLAGS)
clean:
rm -rf *.o
mrproper: clean
rm -rf tablut
The funny thing is that my code compile if I enter the command g++ -c std=c++11 ...
What did I do wrong ?
NB : I tried with the flags -std=c++11, -std=c++0x and -std=gnu++11
You have the rule:
OBJ= $(SRC:.c=.o)
Which means that $(OBJ) ends up being:
OBJ= partie.cpp pawn.cpp playground.cpp
Because none of them match .c. You probably mean to write:
OBJ= $(SRC:.cpp=.o)
With that fix, running make produces:
$ make
g++ -o partie.o -c partie.cpp -std=c++11 -Wall -Wextra
g++ -o pawn.o -c pawn.cpp -std=c++11 -Wall -Wextra
g++ -o playground.o -c playground.cpp -std=c++11 -Wall -Wextra
g++ -o tablut partie.o pawn.o playground.o
Which is probably what you wanted.
Related
I have trouble creating dependency files while using make re. The %.d pattern rule will be called before fclean, also only the %.o pattern rule were called by all after fclean.
Here is the output when i use make vs make re:
mkdir -p srcs/depends
c++ -Wall -Werror -Wextra -Wshadow -std=c++98 -pedantic -Iincludes -MM srcs/tests.cpp -o srcs/depends/tests.d
c++ -Wall -Werror -Wextra -Wshadow -std=c++98 -pedantic -Iincludes -MM srcs/main.cpp -o srcs/depends/main.d
mkdir -p srcs/obj
c++ -Wall -Werror -Wextra -Wshadow -std=c++98 -pedantic -Iincludes -c srcs/main.cpp -o srcs/obj/main.o
c++ -Wall -Werror -Wextra -Wshadow -std=c++98 -pedantic -Iincludes -c srcs/tests.cpp -o srcs/obj/tests.o
c++ -lstdc++ srcs/obj/main.o srcs/obj/tests.o -o main
vs (make re)
rm -f -rv srcs/obj srcs/depends
srcs/obj/main.o
srcs/obj/tests.o
srcs/obj
srcs/depends/main.d
srcs/depends/tests.d
srcs/depends
rm -f main
mkdir -p srcs/obj
c++ -Wall -Werror -Wextra -Wshadow -std=c++98 -pedantic -Iincludes -c srcs/main.cpp -o srcs/obj/main.o
c++ -Wall -Werror -Wextra -Wshadow -std=c++98 -pedantic -Iincludes -c srcs/tests.cpp -o srcs/obj/tests.o
c++ -lstdc++ srcs/obj/main.o srcs/obj/tests.o -o main
My makefile:
NAME = main
SRCSDIR = srcs
SRCS = $(wildcard $(SRCSDIR)/*.cpp)
OBJSDIR = srcs/obj
OBJS = $(SRCS:$(SRCSDIR)/%.cpp=$(OBJSDIR)/%.o)
DEPENDSDIR = srcs/depends
DEPENDS = $(SRCS:$(SRCSDIR)/%.cpp=$(DEPENDSDIR)/%.d)
CPPFLAGS = -Wall -Werror -Wextra -Wshadow -std=c++98 -pedantic -Iincludes
DEPFLAGS = -MM
LDFLAGS = -lstdc++
all: $(NAME)
$(NAME): $(OBJS)
c++ $(LDFLAGS) $^ -o $#
$(OBJSDIR)/%.o: $(SRCSDIR)/%.cpp | $(OBJSDIR)
c++ $(CPPFLAGS) -c $< -o $#
$(DEPENDSDIR)/%.d: $(SRCSDIR)/%.cpp | $(DEPENDSDIR)
c++ $(CPPFLAGS) $(DEPFLAGS) $< -o $#
$(OBJSDIR) $(DEPENDSDIR):
mkdir -p $#
-include $(DEPENDS)
clean:
$(RM) -rv $(OBJSDIR) $(DEPENDSDIR)
fclean: clean
$(RM) $(NAME)
re: fclean all
.PHONY: all clean fclean re
I have looked up the gnu make documentation and couldn't find any details. (Maybe I don't know where to look it up). Anybody knows why or are there any other cleaner solution to this ? Thanks in advance
You are using the old-style header file generation method where make builds dependency files, then re-execs itself to read in the changed dependencies. So, when you run make first it parses all the .d files that currently exist (due to the include line) then it tries to rebuild the .d files, then if any have changed it re-execs, then it runs the rest of the makefile. Once it loads all the .d files and determines that they're up to date, make is done with them (for that invocation). If they later get deleted, it's not going to try to recreate them. They will be recreated the next time make is run.
In general, it's a bad idea to have a rule that runs clean and all as prerequisites. What if you enable parallel builds? Now make is running the clean and all rules in parallel. If you want to do this, you need to invoke them as sub-makes rather than via prerequisites, like this:
re:
$(MAKE) fclean
$(MAKE) all
This will ensure each target is built serially, even with parallel builds, and that make will be started from scratch to build all.
Another thing you should consider is using a more modern form of dependency generation; for example: https://make.mad-scientist.net/papers/advanced-auto-dependency-generation/
I have installed SDL through homebrew, and it works perfectly with my test program if I enter the following command directly in the terminal:
g++ -O3 -g -Wall -Wextra -std=c++1y hello.cpp hello_main.cpp `sdl2-config --cflags --libs` -o hello
but unfortunately my attempts to write a makefile (I will definitely need one) have yielded unsuccessful/unexplained results.
I am following this, but my configuration is different/I am not specifying Cocoa (I don't need to) so I expect that the issues I am encountering are probably due in part to my different requirements:
Compiling SDL on OS X with makefile
Example:
CC=g++
CFLAGS=-c -Wall
SDLFLAGS=`sdl-config --cflags --libs` -framework Cocoa
SOURCES=main.cpp Game.cpp IO.cpp Board.cpp Pieces.cpp Piece.cpp
OBJECTS=$(SOURCES:.cpp=.o)
EXECUTABLE=tetris
all: $(SOURCES) $(EXECUTABLE)
$(EXECUTABLE): $(OBJECTS)
$(CC) $(OBJECTS) $(SDLFLAGS) -o $#
.cpp.o:
$(CC) $(CFLAGS) $< -o $#
clean:
rm -rf *.o $(EXECUTABLE)
My makefile so far:
CXX = g++
CXXFLAGS = -c -O3 -g -Wall -Wextra -std=c++1y
SDLFLAGS = `sdl2-config --cflags --libs`
SOURCES = hello_main.cpp hello.cpp
OBJECTS = $(SOURCES:.cpp=.o)
EXECNAME = hello
all: $(SOURCES) $(EXECNAME)
$(EXECUTABLE): $(OBJECTS)
$(CXX) $ (OBJECTS) $(SDLFLAGS) -o $#
.cpp.o:
$(CXX) $(CXXFLAGS) $< -o $#
clean :
-rm -f *.o *.core $(EXECNAME)
In my .hpp header file if I #include <SDL.h> and run the one-liner command, everything is successful. If I try my makefile above, cannot be found, but if I then change the directive into #include <SDL2/SDL.h> the library is discovered. Yet the console output is the following:
g++ -c -O3 -g -Wall -Wextra -std=c++1y hello.cpp -o hello
which is odd.
Running ./hello yields a "permission denied" error, which confirms that the linking and compilation were not successful.
Everyone's system is a little bit different and the questions I've found so far don't help in this case.
I am very close to having this working (but then again, how would I start using this in an IDE? I suppose that as long as I can import the fixed makefile or build from the terminal/edit only from the IDE, I am fine.)
What changes in the makefile do I need to make?
Thank you.
EDIT:
Variation 1:
CXX = g++
CXXFLAGS = -O3 -g -Wall -Wextra -std=c++1y -c
SDLCFLAGS = `sdl2-config --cflags`
SDLLIBFLAGS = `sdl2-config --libs`
SOURCES = hello_main.cpp hello.cpp
OBJECTS = $(SOURCES:.cpp=.o)
EXECNAME = hello
all: $(SOURCES) $(EXECNAME)
$(EXECUTABLE): $(OBJECTS)
$(CXX) $ (OBJECTS) $(SDLLIBFLAGS) -o $#
.cpp.o:
$(CXX) $(CXXFLAGS) $(SDLCFLAGS) $< -o $#
clean :
-rm -f *.o *.core $(EXECNAME)
I chatted with a friend and figured what was wrong: a bunch of typos and rule oddities. The following works, for anyone out there who needs a basic makefile:
CXX = g++
CXXFLAGS = -O3 -g -Wall -Wextra -std=c++1y
#LDFLAGS = -lSDL2_image
SDLCFLAGS = $(shell sdl2-config --cflags)
SDLLIBFLAGS = $(shell sdl2-config --libs)
SOURCES = hello_main.cpp hello.cpp
OBJECTS = $(SOURCES:.cpp=.o)
EXECNAME = hello
all: $(EXECNAME)
$(EXECNAME): $(OBJECTS)
$(CXX) $(OBJECTS) $(SDLLIBFLAGS) $(LDFLAGS) -o $#
%.o: %.cpp
$(CXX) -c $(CXXFLAGS) $(SDLCFLAGS) $< -o $#
clean :
-rm -f *.o *.core $(EXECNAME)
You should split your sdl2-config into two - as there are two steps. sdl2-config --cflags should go in the compiler step - thats is the .cpp:.o line in your example. The linking step should be sdl2-config --libs then. The second one seems fine for your case, the additional --cflags there does no harm but is not required.
I'm used to program in IDEs, but switched to vim and plugins recently. Now I try to write a makefile for a c++ project, but somehow if I run make I always get the error
g++ -c -o *.o createOutput.cpp
In file included from /usr/include/c++/4.8/thread:35:0,
from createOutput.cpp:5:
/usr/include/c++/4.8/bits/c++0x_warning.h:32:2: error: #error This file requires compiler and library support for the ISO C++ 2011 standard. This support is currently experimental, and must be enabled with the -std=c++11 or -std=gnu++11 compiler options.
#error This file requires compiler and library support for the \
^
This is my makefile:
CC = clang++
# compiler flags
CFLAGS = -O3 -Wall -Werror -std=c++11
CFLAGS_SFML = -lsfml-graphics -lsfml-window -lsfml-system
all: program.exe clean
program.exe: *.o
$(CC) -o program.exe *.o $(CFLAGS) $(CFLAGS_SFML)
getInput.o: getInput.cpp
$(CC) -c getInput.cpp $(CFLAGS)
createOutput.o: createOutput.cpp
$(CC) -c createOutput.cpp $(CFLAGS)
main.o: main.cpp
$(CC) -c main.cpp $(CFLAGS)
.PHONY: clean
clean:
rm *.o
#echo clean done
Where is my error? Why is it using g++ instead of clang? And why isn't it using the -std=c++11 parameter? Sorry for the beginner questions, I unfortunately can't find a solution with google.
You want to set CXXFLAGS, that gets picked up automatically by make (and sent to your compiler (eg g++, clang++, etc).
make tried to make target '*.o'.
So, instead of that, you can specify sources list explicitly:
CC = clang++
#compiler flags
CFLAGS = -O3 -Wall -Werror -std=c++11
CFLAGS_SFML = -lsfml-graphics -lsfml-window -lsfml-system
SRCS = getInput.cpp createOutput.cpp main.cpp
OBJS = $(SRCS:.cpp=.o)
all: program.exe
program.exe: $(OBJS)
$(CC) -o program.exe *.o $(CFLAGS) $(CFLAGS_SFML)
getInput.o: getInput.cpp
$(CC) -c getInput.cpp $(CFLAGS)
createOutput.o: createOutput.cpp
$(CC) -c createOutput.cpp $(CFLAGS)
main.o: main.cpp
$(CC) -c main.cpp $(CFLAGS)
.PHONY : clean
clean:
rm *.o
#echo clean done
Note definition of variables OBJS and SRCS.
I'm trying to compile my project using a Makefile, but somehow the -fopenmp flag won't work.
Here's the Makefile:
TARGET=isaac
CC=g++
CFLAGS=-Wall -O2 -fopenmp
LDFLAGS=-lm -lpthread -lrt
OBJ=src/main.o src/bhtree.o src/body.o src/configreader.o src/diagnostics.o src/output.o src/quad.o src/timing.o src/vector2.o
isaac: $(OBJ)
$(CC) $(CFLAGS) -o $(TARGET) $(OBJ) $(LDFLAGS)
%.o: src/%.cpp
$(CC) $(CFLAGS) -c $<
clean:
rm src/*.o src/*~ isaac
and here is the output when calling "make"
g++ -c -o src/main.o src/main.cpp
g++ -c -o src/bhtree.o src/bhtree.cpp
g++ -c -o src/body.o src/body.cpp
g++ -c -o src/configreader.o src/configreader.cpp
g++ -c -o src/diagnostics.o src/diagnostics.cpp
g++ -c -o src/output.o src/output.cpp
g++ -c -o src/quad.o src/quad.cpp
g++ -c -o src/timing.o src/timing.cpp
g++ -c -o src/vector2.o src/vector2.cpp
g++ -Wall -O2 -fopenmp -o isaac src/main.o src/bhtree.o src/body.o src/configreader.o src/diagnostics.o src/output.o src/quad.o src/timing.o src/vector2.o -lm -lpthread -lrt
the -fopenmp flag is missing when the source files are compiled, so the finished executable is serial, not parallel.
How can I fix this?
The problem is that your rule does not apply at all. You are free to remove
%.o: src/%.cpp
$(CC) $(CFLAGS) -c $<
and you'll get the same result as before. That's because some predefined rule is used instead of yours (I'm not great makefile expert though).
The core of the problem is that your rule is for ./*.o files, but you need ./src/*.o for isaac. You can change your rule
src/%.o: src/%.cpp
$(CC) $(CFLAGS) -c $<
Or (better) move all autogenerated staff somewhere from src.
I got a C++ program for which someone else made a make file. I want to compile the program with flag -g, but I don't know where to add it. Below is the make file.
CC = g++
LOADLIBES = -lm
CFLAGS = -Wall -O2
SRC1 = Agent.cpp Breeder.cpp CandidateSolution.cpp \
Cupid.cpp FateAgent.cpp Grid.cpp Reaper.cpp \
fitness.cpp
SRC2 = main.cpp
SRC = $(SRC1) $(SRC2)
OBJS = $(SRC1:.cpp = .o)
AUX = $(SRC1:.c = .h)
main: $(OBJS)
# $(CC) $(CFLAGS) -o $(SRC) $(AUX)
.PHONY: clean
clean:
rm -f *.o main
Where should I add that I want to use -g?
$(CC) is used for compiling C programs. $(CXX) is used for compiling C++ programs. Similarly $(CFLAGS) is used for C programs, $(CXXFLAGS) is used for compiling C++.
Change the first few lines to this:
#CC = g++
LOADLIBES = -lm
CXXFLAGS = -Wall -O2 -g
(But see others' notes about incompatibilities between -O2 and -g.)
Get rid of the spaces inside the parentheses in this line:
OBJS = $(SRC1:.cpp=.o)
Change the main lines to this:
main: $(OBJS) $(SRC2)
# Built by implicit rules
The resulting makefile should look like this:
#CC = g++
LOADLIBES = -lm
CXXFLAGS = -Wall -O2 -g
SRC1 = Agent.cpp Breeder.cpp CandidateSolution.cpp \
Cupid.cpp FateAgent.cpp Grid.cpp Reaper.cpp \
fitness.cpp
SRC2 = main.cpp
SRC = $(SRC1) $(SRC2)
OBJS = $(SRC1:.cpp=.o)
AUX = $(SRC1:.c=.h)
main: $(OBJS) $(SRC2)
# Built by implicit rules
.PHONY: clean
clean:
rm -f *.o main
and the output should look like this:
$ make
g++ -Wall -O2 -g -c -o Agent.o Agent.cpp
g++ -Wall -O2 -g -c -o Breeder.o Breeder.cpp
g++ -Wall -O2 -g -c -o CandidateSolution.o CandidateSolution.cpp
g++ -Wall -O2 -g -c -o Cupid.o Cupid.cpp
g++ -Wall -O2 -g -c -o FateAgent.o FateAgent.cpp
g++ -Wall -O2 -g -c -o Grid.o Grid.cpp
g++ -Wall -O2 -g -c -o Reaper.o Reaper.cpp
g++ -Wall -O2 -g -c -o fitness.o fitness.cpp
g++ -Wall -O2 -g main.cpp Agent.o Breeder.o CandidateSolution.o Cupid.o FateAgent.o Grid.o Reaper.o fitness.o -lm -o main
For completeness, this is the version of make I am using on Ubuntu 10.04:
$ make -v
GNU Make 3.81
Copyright (C) 2006 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.
There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A
PARTICULAR PURPOSE.
This program built for i486-pc-linux-gnu
You need to uncomment the line:
# $(CC) $(CFLAGS) -o $(SRC) $(AUX)
(remove the hash sigh):
$(CC) $(CFLAGS) -o $(SRC) $(AUX)
And change
CFLAGS = -Wall -O2
to
CFLAGS = -Wall -O2 -g
But you may find debugging easier if you disable optimization by removing -O2:
CFLAGS = -Wall -g