Learn C the Hard Way Exercise 2 - makefile

I just started Learn C the Hard Way and I'm on Exercise #2.
link here:
http://c.learncodethehardway.org/book/ex2.html
The instructions are to make a file with only this in it:
CFLAGS=-Wall -g
clean:
rm -f ex1
So I created and saved that as Makefile.c, however, upon running it as specified in my compiler (MINGW), I'm getting this error:
$make clean
cc makefile.c -o makefile
makefile.c:3:1: warning: data definition has no type or storage class [enabled by default]
makefile.c:3:9: error: 'Wall' undeclared here (not in a function)
makefile.c:3:15: error: 'g' undeclared here (not in a function)
makefile.c:5:1: error expected ',' or ';' before 'clean'
cc Makefile.c -o Makefile
Makefile.c:3:1: warning: data definition has no type or storage class [enabled by default]
Makefile.c:3:9: error: 'Wall' undeclared here (not in a function)
Makefile.c:3:15: error: 'g' undeclared here (not in a function)
Makefile.c:5:1: error expected ',' or ';' before 'clean'
make: *** No rule to make target 'clean'. Stop.
Any ideas what I'm doing wrong and/or how I can fix this? Thanks!

Late, but your makefile should just be named "Makefile"
Makefile is not the source code for a C program, but a set of instructions for the Makefile tool, which gets used when you type "make foo".

Makefile can be called "makefile" or "Makefile"
According to man make:
"Normally you should call your makefile either makefile or Makefile. (We recommend Makefile because it appears prominently near the beginning of a directory listing, right near other important files such as README.) The first name checked, GNUmakefile, is not recommended for most makefiles."

Are you using tab characters instead of space? The web page has spaces, but a makefile needs tabs. Note the author's comment after the makefile code.

Related

Calling Octave interpreter from C - Problems compiling and running example

I'm trying to implement calling octave from C, as per the example shown in this answer Call GNU Octave functions in C?
I'm trying this in Nebeans on Linux.
I've created the files calloctave.cc, calloctave.h, main.c and myfunction.m as per the example. Pointed the links and includes to the correct places (in my case /usr/include/octave-5.2.0/octave/ and /usr/lib64/octave/5.2.0 ). I've chosen C++11 as the standard. In the code, there are no errors highlighted and it seems to find everything it needs, and nothing is highlighted as missing.
When I try to compile it, I just get a series of errors as follows....
cd '/home/arwel/NetBeansProjects/callOctave_new'
/bin/gmake -f Makefile CONF=Debug
"/bin/gmake" -f nbproject/Makefile-Debug.mk QMAKE= SUBPROJECTS= .build-conf
gmake[1]: Entering directory `/home/arwel/NetBeansProjects/callOctave_new'
"/bin/gmake" -f nbproject/Makefile-Debug.mk dist/Debug/GNU-Linux/libcallOctave_new.so
gmake[2]: Entering directory `/home/arwel/NetBeansProjects/callOctave_new'
mkdir -p build/Debug/GNU-Linux
rm -f "build/Debug/GNU-Linux/calloctave.o.d"
g++ -c -g -I/usr/include/octave-5.2.0/octave -include /usr/include/octave-5.2.0/octave/mex.h -std=c++11 -fPIC -MMD -MP -MF "build/Debug/GNU-Linux/calloctave.o.d" -o build/Debug/GNU-Linux/calloctave.o calloctave.cc
In file included from /usr/include/octave-5.2.0/octave/Cell.h:33:0,
from /usr/include/octave-5.2.0/octave/gtk-manager.h:32,
from /usr/include/octave-5.2.0/octave/interpreter.h:36,
from calloctave.cc:7:
/usr/include/octave-5.2.0/octave/ov.h:52:7: error: using typedef-name ‘mxArray’ after ‘class’
class mxArray;
^
In file included from <command-line>:0:0:
/usr/include/octave-5.2.0/octave/mex.h:55:14: note: ‘mxArray’ has a previous declaration here
typedef void mxArray;
^
In file included from /usr/include/octave-5.2.0/octave/ov.h:62:0,
from /usr/include/octave-5.2.0/octave/Cell.h:33,
from /usr/include/octave-5.2.0/octave/gtk-manager.h:32,
from /usr/include/octave-5.2.0/octave/interpreter.h:36,
from calloctave.cc:7:
/usr/include/octave-5.2.0/octave/ov-base.h:57:7: error: using typedef-name ‘mxArray’ after ‘class’
class mxArray;
^
In file included from <command-line>:0:0:
/usr/include/octave-5.2.0/octave/mex.h:55:14: note: ‘mxArray’ has a previous declaration here
typedef void mxArray;
^
calloctave.cc: In function ‘int mexCallOctave(int, mxArray**, int, mxArray**, const char*)’:
calloctave.cc:26:15: error: ‘mxArray’ is not a class, namespace, or enumeration
args(i) = mxArray::as_octave_value (argin[i]);
^
calloctave.cc:42:41: error: invalid use of ‘mxArray {aka void}’
argout[i] = new mxArray (retval(i));
^
calloctave.cc: In function ‘void free_arg_list(int, mxArray**)’:
calloctave.cc:56:29: warning: deleting ‘mxArray* {aka void*}’ is undefined [enabled by default]
delete arglist[i];
^
gmake[2]: *** [build/Debug/GNU-Linux/calloctave.o] Error 1
gmake[2]: Leaving directory `/home/arwel/NetBeansProjects/callOctave_new'
gmake[1]: *** [.build-conf] Error 2
gmake[1]: Leaving directory `/home/arwel/NetBeansProjects/callOctave_new'
gmake: *** [.build-impl] Error 2
BUILD FAILED (exit value 2, total time: 1s)
It seems to be not understanding the mex interface in some way. I'm not very knowledgeable about C/C++, so am at a loss as to how to proceed here. What could be causing these errors and how might I resolve them?

Makefile error: missing close parenthesis

I am trying to download the Shakespeare to C compiler, and I have gotten to the point where I am trying to run the Makefile. I have tried nmake -f Makefile, but that returns fatal error U1000 on line 41:
I can't find anything wrong with the Makefile. There is the same number of "(" and ")".Line 41 says MAKESCANNERINCLUDE = $(wildcard $(INCLUDEPATH)/*.{wordlist,metaflex}).
$(wildcard …) is a function call. Function calls are a GNU make extension to the standard make syntax. Nmake expects a variable reference which would be just $(something), so when it sees a space instead of a closing parenthesis, it reports a syntax error.
Use GNU make instead of Nmake.

why is gcc gets executed in this make file?

I have the following makefile when type make i got the following output. why is gcc gets called in this case?
nasm -felf ./source/multiboot.s
gcc multiboot.o -o multiboot
gcc: error: multiboot.o: No such file or directory
gcc: fatal error: no input files
compilation terminated.
make: *** [multiboot] Error 4
makefile:
CC=gcc
ASM=nasm
ASMFLAG=-felf
SOURCE=./source/
all: multiboot
multiboot.o: $(SOURCE)multiboot.s
$(ASM) $(ASMFLAG) $(SOURCE)multiboot.s
The "all" command depends on "multiboot", but there is no explicit rule defining how to produce "multiboot". In this case, Make uses a predefined rule that understands that, if the "$target.o" target exists, then "$target" can be constructed from "$target.o" by running the linker (in this case, GCC).
It seems like the problem in this case is that your instructions for the "multiboot.o" command does not actually produce the file "multiboot.o" as output. Try simply doing:
multiboot.o: multiboot.s
(That is, without specifying the command to run). Simply declaring this dependency should, by a similar mechanism, result in an implicit rule/command to create the "multiboot.o" output from "multiboot.s".

what does Makefile(90) : fatal error U1000 mean?

I'm trying to do this from the command prompt:
C:/>nmake makefile
But I keep getting this error
Makefile(90) : fatal error U1000: syntax error : ')' missing in macro invocation
What does the number 90 refer to?
Any one can help?
If any one would like to see the Makefile it's here Makefile
p.s: I use windows 7
Line 90 of the Makefile is:
LDSHARED = $(CC) -shared $(if $(filter-out -g -g0,$(debugflags)),,-s)
90 is the line-number of the error. I suspect this makefile isn't meant to be used in nmake, since the syntax resembles gnu-make more than nmake.
You will probably have more luck if you run gnumake (gmake or possibly simply make).
Or, you could try to rewrite the makefile using the preprocessor macros, but it will require understanding what they are supposed to do.
http://msdn.microsoft.com/en-US/library/7y32zxwh%28v=vs.80%29.aspx

nmake makefile, linking objects files in a subfolder

My makefile defines a link command:
prod_link = $(LINK) $(LINK_FLAGS) -o$(PROD_OUT) $(PROD_OBJS)
where $(PROD_OBJS) is a list of object files of the form:
PROD_OBJS = objfile1.obj objfile2.obj objfile3.obj ... objfileN.obj
Now the makefile itself is at the root of my project directory.
It gets messy to have object and listing files at the root, I'd like to put them in a subfolder.
Building and outputing the obj files to a subfolder works, I'm doing it with suffixes and inference:
.s.obj:
$(ASSEMBLY) $(FLAGS) $*.s -o Objects\$*.obj
The problem is to pass the Objects folder to the link command.
I tried:
prod_link = $(LINK) $(LINK_FLAGS) -o$(PROD_OUT) Objects\$(PROD_OBJS)
but only the first file in the list of object files gets the folder's name.
How can I pass the Objects subfolder to all files of my list $(PROD_OBJS)?
EDIT
I tried also
PROD_OBJS = $(patsubst %.ss,Object\%.obj, $(PROD_SRC))
but got:
makefile(51) : fatal error U1000: syntax error : ')' missing in macro invocation
Stop.
This is quite strange...
nmake is not GNUMake, and is rather rubbish. See the NMAKE Reference for details.
As far as your problem goes (translating 1.o 2.o 3.o into d/1.o d/2/o d/3.o), try
OBJS= 1.o 2.o 3.o
# Looks wierd I know, but basically change ' ' to ' d/'
# (and it's not very robust!)
OBJS_WITH_PREFIX= d/$(OBJS: = d/)
!ERROR [$(OBJS_WITH_PREFIX)]
By the way, your pattern rule is lying to nmake. You say .s.obj:, which says "here is how to convert a .s file into a .obj," but then the commands you give actually create the object in a subfolder. You should have started the pattern rule with .s{Objects\}.obj:. See the docs for more details (Search Paths in Rules).
Very late to the party, but in case anyone else runs into the same problem:
This error
makefile(51) : fatal error U1000: syntax error : ')' missing in macro invocation
Stop.
is caused by the fact that the patsubst syntax doesn't seem to be supported by nmake. You can get around this by using the alternative syntax
$(var:suffix=replacement)
instead of
$(patsubst %suffix,%replacement,$(var))
(this is also valid in gnumake).

Resources