Skip to content

clang-cl does not respect /I include directores if they are also in the INCLUDE environment variable #162115

@davidritter

Description

@davidritter

I am observing an issue with clang-cl and how it resolves include paths. It appears the front end is ignoring values passed in to the compiler via -I IF that path is also part of the INCLUDE environment variable.

This causes a problem as the value passed in via -I should be considered a higher precedence regardless of whether it occurs in the INCLUDE environment variable or not. The MSVC cl compiler front end does not treat the value special and respects the ordering defined below.

The MSVC cl documentation notes (https://learn.microsoft.com/en-us/cpp/build/reference/i-additional-include-directories)

The compiler searches directories in the following order:

  1. If the #include directive is specified using double-quote form, it first searches local directories. The search begins in the same directory as the file that contains the #include directive. If it fails to find the file, it searches next in the directories of the currently opened include files, in the reverse order in which they were opened. The search begins in the directory of the parent include file and continues upward through the directories of any grandparent include files.
  2. If the #include directive is specified in angle-bracket form, or if the local directory search has failed, it searches directories specified by using the /I option, in the order they're specified on the command line.
  3. Directories specified in the INCLUDE environment variable.
C:\Workspace\tmp\t42>dir /s /b /a-d
C:\Workspace\tmp\t42\main.cpp
C:\Workspace\tmp\t42\env\foo.h
C:\Workspace\tmp\t42\include\foo.h

C:\Workspace\tmp\t42\env>set INCLUDE=%CD%;%INCLUDE%

C:\Workspace\tmp\t42\env>cd ..

C:\Workspace\tmp\t42>clang-cl main.cpp && main.exe
C:\Workspace\tmp\t42\env\foo.h

C:\Workspace\tmp\t42>clang-cl -Iinclude main.cpp && main.exe
include\foo.h

C:\Workspace\tmp\t42>set INCLUDE=%INCLUDE%;C:\Workspace\tmp\t42\include

C:\Workspace\tmp\t42>clang-cl -Iinclude main.cpp && main.exe
C:\Workspace\tmp\t42\env\foo.h

C:\Workspace\tmp\t42>

The files foo.h are identical (just in different locations to illustrate the behavior):
foo.h

#include <cstdio>

void foo()
{
    std::printf("%s\n", __FILE__);
}

main.cpp

#include <foo.h>

int main(void)
{
    foo();
    return 0;
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    clang-cl`clang-cl` driver. Don't use for other compiler parts

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions