how to prevent "directory already exists error" in a makefile when using mkdir

I need to generate a directory in my makefile and I would like to not get the "directory already exists error" over and over even though I can easily ignore it.

I mainly use mingw/msys but would like something that works across other shells/systems too.

I tried this but it didn't work, any ideas?

ifeq (,$(findstring $(OBJDIR),$(wildcard $(OBJDIR) )))
-mkdir $(OBJDIR)
endif

Solution 1:

Looking at the official make documentation, here is a good way to do it:

OBJDIR := objdir
OBJS := $(addprefix $(OBJDIR)/,foo.o bar.o baz.o)

$(OBJDIR)/%.o : %.c
    $(COMPILE.c) $(OUTPUT_OPTION) $<

all: $(OBJS)

$(OBJS): | $(OBJDIR)

$(OBJDIR):
    mkdir -p $(OBJDIR)

You should see here the usage of the | pipe operator, defining an order only prerequisite. Meaning that the $(OBJDIR) target should be existent (instead of more recent) in order to build the current target.

Note that I used mkdir -p. The -p flag was added compared to the example of the docs. See other answers for another alternative.

Solution 2:

On UNIX Just use this:

mkdir -p $(OBJDIR)

The -p option to mkdir prevents the error message if the directory exists.

Solution 3:

You can use the test command:

test -d $(OBJDIR) || mkdir $(OBJDIR)

Solution 4:

Here is a trick I use with GNU make for creating compiler-output directories. First define this rule:

  %/.d:
          mkdir -p $(@D)
          touch $@

Then make all files that go into the directory dependent on the .d file in that directory:

 obj/%.o: %.c obj/.d
    $(CC) $(CFLAGS) -c -o $@ $<

Note use of $< instead of $^.

Finally prevent the .d files from being removed automatically:

 .PRECIOUS: %/.d

Skipping the .d file, and depending directly on the directory, will not work, as the directory modification time is updated every time a file is written in that directory, which would force rebuild at every invocation of make.