Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to properly make my makefile to compile and run?

The question is probably not the best one to describe my issue but I couldn't think of a better one. My makefile goes like this:

PROGRAM_NAME = prog

OBJECT_FILES = $(PROGRAM_NAME).o
CFLAGS = -O2 -Wall -g

$(PROGRAM_NAME) : $(OBJECT_FILES)
    gcc $(CFLAGS) -o $@ $(OBJECT_FILES)

$(PROGRAM_NAME).o : $(PROGRAM_NAME).c data.h
    gcc $(CFLAGS) -c $<

clean :
    $(RM) $(PROGRAM_NAME)
    $(RM) $(OBJECT_FILES)
    $(RM) *~ *.bak

run :
    @$(MAKE) && ./$(PROGRAM_NAME) $(ARGS)

When I want to compile and run I just do "make run". The issue with this is that my program handles the signal produced by Ctrl+Z and if I start my program with "make run", the signal will be sent to "make run" and not my program itself.

Basically, calling "make run" is not the same thing as calling directly "make && ./prog" because in the first case, "make run" will not terminate unless "prog" terminates first.

Is there a way around this?

like image 805
rfgamaral Avatar asked May 24 '09 15:05

rfgamaral


People also ask

How do I run an executable file in makefile?

If you run make without specifying any targets, it would execute the first target it finds within the Makefile. By convention all is the name of such a target. If you make run a pre-requisite for all and mark both all and run as PHONY targets, you should be good to go.

What does $() mean in makefile?

The $@ and $< are called automatic variables. The variable $@ represents the name of the target and $< represents the first prerequisite required to create the output file.

How do I run a makefile in Linux?

Also you can just type make if your file name is makefile/Makefile . Suppose you have two files named makefile and Makefile in the same directory then makefile is executed if make alone is given. You can even pass arguments to makefile.


2 Answers

Running from the makefile is a bit unusual. Are you, perhaps, trying to duplicate the "Compile and Run" Menu item that some IDE provide? Make is not well equipped to do that.

All the stuff that happens in the target commands happens in sub-processes that are not attached directly to the terminal, which is why make receives your key stroke.

Another thing to look at: usually the object-file to executable stage (linking) uses a different set of flags (LDFLAGS and LIBS) then the compile stage. In this simple example you can get away with it, but if you copy this makefile for use in a more complicated case you'll run into trouble.

like image 27
dmckee --- ex-moderator kitten Avatar answered Oct 14 '22 14:10

dmckee --- ex-moderator kitten


You can simplify your 'run' target by having it depend on whether your program is up to date, and then simply run the program:

run:    ${PROGRAM_NAME}
        ./${PROGRAM} ${ARGS}

There's not much point in running make when you're already running make - at least, not in this context. Maybe for recursive operations (in different directories), but see 'Recursive Make Considered Harmful'.

Also, your makefile should normally provide a target 'all' and it should normally the first and therefore default target.

like image 163
Jonathan Leffler Avatar answered Oct 14 '22 15:10

Jonathan Leffler