Search code examples
windowsmakefileescapingbackslash

How can I escape the Backslash character in a makefile?


There are several posts about trying to escape characters in a Makefile. I am interested in escaping the backslash \. I need to dynamically build a path according to the OS. So, I wrote a condition for that:

OperatingSystem :=
ifeq ($(OS),Windows_NT)
  Separator := \
else
  Separator := /
endif

Path := c:$(Separator)

This code fails when the OS is Windows since the backslash is not escaped and it expects to have more data on the next line. Does anyone have an idea how can I overcome this? I thought about a workaround which in case it is Windows, I will read the environment variable called ProgramFiles and will take the 3rd character out of it. But how can I get a specific character from it?

Thanks,


Solution

  • The meta-answer to your question is you should never use backslashes in makefiles; make is a POSIX-based program and it expects the paths that it parses to use forward-slashes.

    99% of Windows programs will accept forward slashes as directory separators, as well as backslashes. So for 99% of the recipes in makefiles, forward slashes will work. For those few that don't work (typically only cmd.exe programs like rmdir or copy or the like), you can do the replacement in the recipe itself.

    The simplest direct answer is to use an empty variable to separate the newline from the backslash so make doesn't do anything special with it. For example:

    EMPTY :=
    BACKSLASH := \$(EMPTY)
    

    The second thing to note is that make doesn't treat backslashes separately in MOST situations. The end of the line is really the only place where it matters.

    So in a recipe where you need backslashes, you can do this:

    sometarget:
            copy $(subst /,\,$<) $(subst /,\,$@)
    

    without doing anything special to "quote" backslashes.