I'm getting a Make error when I run the mingw32-make command:
PS D:\> mingw32-make
cd src; mingw32-make
The system cannot find the path specified.
mingw32-make: *** [Makefile:4: all] Error 1
But when I list the actual command listed in the Makefile i.e. cd src; mingw32-make, the build is finished successfully.
PS D:\> cd src; mingw32-make
g++ -std=c++17 -Wall -Wextra -Wpedantic -Wformat -Wchkp -I../include -c account.cpp
g++ -std=c++17 -Wall -Wextra -Wpedantic -Wformat -Wchkp -I../include -c customer.cpp
g++ -std=c++17 -Wall -Wextra -Wpedantic -Wformat -Wchkp -I../include -c display.cpp
g++ -std=c++17 -Wall -Wextra -Wpedantic -Wformat -Wchkp -I../include -c main.cpp
g++ -std=c++17 -Wall -Wextra -Wpedantic -Wformat -Wchkp -I../include -c passbook.cpp
g++ -std=c++17 -Wall -Wextra -Wpedantic -Wformat -Wchkp -I../include -c security.cpp
g++ -std=c++17 -Wall -Wextra -Wpedantic -Wformat -Wchkp -I../include -c staff.cpp
g++ -o Bank account.o customer.o display.o main.o passbook.o security.o staff.o
However this issue is not present when I build using Make on Ubuntu.
This is the Makefile in my root directory:
DIR = src
all:
cd $(DIR); mingw32-make
clean:
cd $(DIR); mingw32-make clean
This is the Makefile in my src subdirectory:
# Compiler options
# -std=c++17 enables ISO C++ 17 standard
CC = g++
CCFLAGS = -std=c++17 -Wall -Wextra -Wpedantic -
Wformat -Wchkp
i = ../include
# LOCFLAGS used to set tell the compiler where to find a
# header that is not in the same directory as the source
file itself
# LOCFLAGS will be set in directory level makefiles as
needed
LOCFLAGS = -I../include
# The list of object files that can be made in this
subdirectory
# is assigned to the make macro named $OBJECTS
OBJECTS = account.o customer.o display.o main.o
passbook.o \
security.o staff.o
# This rule says that the target named "all" depends on
those
# files. Executing "make all" in this subdirectory will cause
# make to build the object files (.o) listed in the macro
$OBJECTS
# and create an executable named "Bank" by linking them
all: $(OBJECTS)
$(CC) -o Bank $(OBJECTS)
# rule that says how to make a .o object file from a .cpp
source file
# for a given source file in a given directory you could
compile it
# into an object file by executing "make filename.o"
# $< and $# are macros defined by make
# $< refers to the file being processed (i.e., compiled or
linked )
# $# refers to the generated file
%.o: %.cpp
$(CC) $(CCFLAGS) $(LOCFLAGS) -c $<
# target to clean up the object files, core files and
executables
# executing "make clean" in this subdirectory will remove
all
# files named core, "Bank" or any file ending in .o or
.stackdump
clean:
del $(OBJECTS) core *.stackdump Bank
On Windows you're running in a command.com shell, not a POSIX shell. In command.com, the syntax cd src; mingw32-make is not legal. For example if I open a command.com terminal on a Windows system I see:
C:\Users\build> cd src; echo hi
The system cannot find the path specified.
In Windows command.com the command separator is a single & not a semicolon.
If you want to change directories portably you can use the -C option to GNU make. Also you should always use the $(MAKE) variable, not write out the make command by hand:
all:
$(MAKE) -C $(DIR)
Related
I'm trying to compile a large C++ project with source files in several subdirectories of src.
My Makefile looks like this:
# ---------- Compiler and linker directives ----------
CXX = g++-11
CXXFLAGS = -std=c++17 -fopenmp -MD -g -Wall -pedantic
# LDFLAGS = -Wl,--gc-sections
# Output directory after linking
BIN_PATH = ../bin
BUILD_PATH = ../build
# ------- System Include --------------
# Change ~/include as necessary for your architecture
INC_FLAGS = -I../include -I/opt/homebrew/include
# -------- Establishing objects and sources ------
RATE_SRC = $(wildcard hartreefock/*.cpp) $(wildcard struct_hartreefock/*.cpp) $(wildcard numerical/*.cpp)
RATE_OBJ = $(addprefix $(BUILD_PATH)/,$(RATE_SRC:.cpp=.o)))
# ------------- Specific Include -----------
# RATE_HEADERS = $(wildcard hartreefock/*.hpp) $(wildcard struct_hartreefock/*.hpp) $(wildcard numerical/*.hpp)
RATE_DIR = hartreefock struct_hartreefock numerical
RATE_INC = $(addprefix -I,$(RATE_DIR))
# ---------- Libraries needed for linking ----------
# Change or remove ~/lib as necessary for your architecture
LIB_PATH = -L/opt/homebrew/lib
# Generic .cc -> .o rule
$(BUILD_PATH)/%.o: %.cpp
#mkdir -p $(#D)
$(CXX) $(CXXFLAGS) $(INC_FLAGS) $(RATE_INC) $< -c -o $#
# ---------- Linking rules ----------
# Generic .o -> exec rule: uses all prerequisites (meant to be .o files)
ratecalc: $(RATE_OBJ)
$(CXX) $(CXXFLAGS) $(INC_PATH) $(A_RATE_INC) $(LDFLAGS) $^ \
$(LIB_PATH) -o $(BIN_PATH)/$#
# TODO
# simulate:
echo:
echo "$(RATE_OBJ)"
echo "$(BUILD_PATH)"
# Cleanup:
.PHONY: clean build_directories
clean:
-rm -r $(BUILD_PATH)/**
Bizarrely, this seems to do the right thing until I get to one specific file:
make clean
make ratecalc
g++-11 -std=c++17 -fopenmp -MD -g -Wall -pedantic -I../include -I/opt/homebrew/include -Ihartreefock -Istruct_hartreefock -Inumerical struct_hartreefock/RateData.cpp -c -o ../build/struct_hartreefock/RateData.o
g++-11 -std=c++17 -fopenmp -MD -g -Wall -pedantic -I../include -I/opt/homebrew/include -Ihartreefock -Istruct_hartreefock -Inumerical numerical/Constant.cpp -c -o ../build/numerical/Constant.o
make: *** No rule to make target `../build/numerical/wignerSymbols.o)', needed by `ratecalc'. Stop.
This is especially strange because Constant.cpp and wignerSymbols.cpp are in the same directory. Manually running with this target compiles the object file as needed,
make ../build/numerical/wignerSymbols.o
g++-11 -std=c++17 -fopenmp -MD -g -Wall -pedantic -I../include -I/opt/homebrew/include -Ihartreefock -Istruct_hartreefock -Inumerical numerical/wignerSymbols.cpp -c -o ../build/numerical/wignerSymbols.o
but this is not recognised as satisfying the dependency for the ratecalc rule.
It might be significant that wignerSymbols.cpp is the very last entry in RATE_OBJ, but to be honest I can't understand what's happening here.
For completeness: I'm using GNU make 3.81 on an M1 macbook air.
Typo:
RATE_OBJ = $(addprefix $(BUILD_PATH)/,$(RATE_SRC:.cpp=.o)))
There is an extra close paren here, which you can see in your error message:
make: *** No rule to make target `../build/numerical/wignerSymbols.o)', ...
when running a makefile, which includes a usage of
a script-file, I receive an error saying the linker doesn't find the script file.
When running the make file the output is as follows:
arm-none-eabi-gcc -g -Wall -Werror -c -o main.o main.c
arm-none-eabi-gcc -g -Wall -Werror -c -o misc.o misc.c
arm-none-eabi-gcc main.o misc.o misc.h -g -Wall -Werror -Wl,-Map=HOST.map -T=msp432p401r.lds -o HOST
/usr/lib/gcc/arm-none-eabi/9.2.1/../../../arm-none-eabi/bin/ld: cannot open linker script file =msp432p401r.lds: No such file or directory
collect2: error: ld returned 1 exit status
make: *** [Makefile:11: HOST] Error 1
The makefile content is:
#---- Variables (machine depending) --------
TARGET = HOST
CC = arm-none-eabi-gcc #gcc
CFLAGS = -g -Wall -Werror # compiler flags
LDFLAGS = -Wl,-Map=$(TARGET).map -T=msp432p401r.lds # linker flag
SOURCE = main.c misc.c misc.h
OBJS = $(SOURCE:.c=.o) # replace all c with o
#---- Targets -----------
$(TARGET): $(OBJS)
$(CC) $(OBJS) $(CFLAGS) $(LDFLAGS) -o $#
I have searched a lot for a solution for this issue, and tried various fixes, with no success.
The script file is located at the same location as the source files.
What can be the reason for not finding the file?
Thanks
So here's my question: Why is the following makefile failing to build the only .c file in the directory? I have a fairly simple makefile for building my operating system kernel, and for some reason, it's not building the .c files required for the kernel rule to build.
The directory only contains a single .c file and the following Makefile:
GCCPARAMS = -m32 -ffreestanding -Wall -Wextra -nostdinc -nostdlib
GPPPARAMS = -m32 -ffreestanding -O2 -Wall -Wextra -fno-exceptions -fno-rtti -nostdinc -nostdlib
ASPARAMS = --32
LDPARAMS = -m32 -ffreestanding -O2 -nostdlib
C_FILES := $(wildcard *.c)
CPP_FILES := $(wildcard *.cpp)
S_FILES := $(wildcard *.s)
OBJ_FILES := $(C_FILES:.c=.o) $(CPP_FILES:.cpp=.o) $(S_FILES:.s=.o)
all: kernel
%.o: %.cpp
g++ $(GPPPARAMS) -c $< -o $#
%.o: %.c
gcc $(GCCPARAMS) -c $< -o $#
%.o: %.s
as $(ASPARAMS) $< -o $#
kernel: $(C_FILES) $(CPP_FILES) $(A_FILES)
ld -r $(OBJ_FILES) -o ../kernel.o
As you can see, I clearly have $(C_FILES) in the list. However, running make all or make kernel yields the following output:
ld -r core.o -o ../kernel.o
ld: cannot find core.o: No such file or directory
Makefile:23: recipe for target 'kernel' failed
make: *** [kernel] Error 1
Now, I've called even added to the kernel rule a print routine to test the C_FILES variable which does, in fact, print core.c (The one .c file in the directory), and the linker clearly received the OBJ_FILES list, so why is it not building core.c?
You need to define your object files as prerequisite to the kernel rule, because the kernel rule depends on them. It only depends indirectly from the source files.
kernel: $(C_FILES) $(CPP_FILES) $(A_FILES) $(OBJ_FILES)
ld -r $(OBJ_FILES) -o ../kernel.o
I've been trying to compile some language (CISC) that my professor created which is pseudo assembly. He wanted us to make a makefile and compile the file with .asm extension using gcc.
This is the makefile:
.SUFFIXES: .asm
all:schemeCompiler
schemeCompiler:target.o
gcc -g -m32 -Wall -o schemeCompiler target.o
target.o: target.asm
gcc -m32 -g -Wall -ansi -c -o target.o target.asm
.PHONY: clean
clean:
rm -f *.o schemeCompiler
And this is the error I get:
gcc -m32 -g -Wall -ansi -c -o target.o target.asm
gcc: warning: target.asm: linker input file unused because linking not done
gcc -g -m32 -Wall -o schemeCompiler target.o
gcc: error: target.o: No such file or directory
gcc: fatal error: no input files
compilation terminated.
I've put the makefile with the asm file in the same directory
Thanks !
***We've figured out the problem , we weren't running the make command right. Also the makefile wasn't right:
.SUFFIXES: .asm
all:schemeCompiler
schemeCompiler:$#
gcc -g -m32 -Wall -o schemeCompiler $#
%: %.asm
gcc -x c -o $# $<
.PHONY: clean
clean:
rm -f *.o schemeCompiler
I want to add the shared library path to my Makefile. I have put in the export command in the makefile, it even gets called, but I still have to manually export it again.
What is the correct approach?
Makefile:
SOURCES = kwest_main.c fusefunc.c dbfuse.c logging.c dbbasic.c dbinit.c dbkey.c metadata_extract.c plugins_extraction.c import.c
LIBS = -L$(LIB) -lfuse -lsqlite3 -lkw_taglib -ltag_c -ltag -Wl,-rpath=.
INCLUDE = ../include
LIB = ../lib
EXE = kwest
CC = gcc
CCFLAGS = -g -Wall -Wextra -std=gnu99 -pedantic-errors -I$(INCLUDE)
OFLAGS = -c
ARCH = $(shell getconf LONG_BIT)
X = -D_FILE_OFFSET_BITS=$(ARCH)
OBJECTS = $(SOURCES:.c=.o)
$(EXE) : $(OBJECTS)
$(CC) -o $(EXE) $(OBJECTS) $(LIBS)
%.o: %.c
$(CC) $(OFLAGS) $(CCFLAGS) $<
fusefunc.o: fusefunc.c
$(CC) $(OFLAGS) $(CCFLAGS) $< $X
kwest_libs: kw_taglib
--->export LD_LIBRARY_PATH=$(LIB):$LD_LIBRARY_PATH
kw_taglib: plugin_taglib
plugin_taglib: plugin_taglib.o kwt_upd_meta.o
gcc -g -shared -I$(INCLUDE) -Wl,-soname,libkw_taglib.so -o $(LIB)/libkw_taglib.so -ltag -ltag_c plugin_taglib.o kwt_upd_meta.o
plugin_taglib.o:
gcc -c -g -I$(INCLUDE) -Wall -Wextra -pedantic-errors -std=gnu99 -fPIC -ltag_c -c plugin_taglib.c
kwt_upd_meta.o:
g++ -c -g -I$(INCLUDE) -Wall -Wextra -pedantic-errors -fPIC -ltag kwt_upd_meta.cpp
c: clean
clean:
rm -rf *.o
rm -rf *.db
ca: cleanall
cleanall: clean
rm -rf $(EXE)
ob: cleanall
rm -rf ~/.config/$(EXE)/
Execution:
$ ./kwest mnt
./kwest: error while loading shared libraries: libkw_taglib.so: cannot open shared object file: No such file or directory
$ export LD_LIBRARY_PATH=../lib:D_LIBRARY_PATH
$ ./kwest mnt
"executes correctly"
The usual way is to copy the dynamic library during the default make and to one of the standard library path
/usr/local/bin
or one of your project library path and add the library to executable using
-L/project/specific/path
during make install.
As already mentioned here, the thing you probably want is the linker option -rpath.
Like that, you can set a default search path for the binary. Looks like you even already use -rpath in your makefile, but you specify the wrong path:
LIBS = -L$(LIB) -lfuse -lsqlite3 -lkw_taglib -ltag_c -ltag -Wl,-rpath=.
So the binary will search in the current directory for dyn-libraries.
However, you add ../lib to your LD_LIBRARY_PATH later, for execution of the binary, so the given path . seems to be wrong.
Please take a try for the following fix:
LIBS = -L$(LIB) -lfuse -lsqlite3 -lkw_taglib -ltag_c -ltag -Wl,-rpath=../lib
Like that you should not need to specify a LD_LIBRARY_PATH for execution.