summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJinWang An <jinwang.an@samsung.com>2021-08-03 16:30:48 +0900
committerJinWang An <jinwang.an@samsung.com>2021-08-03 16:30:48 +0900
commit4cb18bd611457fa47f5ade179f97f839c5e25d79 (patch)
treeb833b3f3f5038292db5ae992325e71652c08179e
parent1d650321e4565184e6f1560a229f9625a85a4daf (diff)
downloadccache-4cb18bd611457fa47f5ade179f97f839c5e25d79.tar.gz
ccache-4cb18bd611457fa47f5ade179f97f839c5e25d79.tar.bz2
ccache-4cb18bd611457fa47f5ade179f97f839c5e25d79.zip
Imported Upstream version 4.3upstream/4.3
-rw-r--r--.clang-format3
-rw-r--r--.github/workflows/build.yaml8
-rw-r--r--.gitignore3
-rw-r--r--.mailmap1
-rw-r--r--CMakeLists.txt41
-rw-r--r--CONTRIBUTING.md12
-rw-r--r--cmake/CIBuildType.cmake16
-rw-r--r--cmake/CcacheVersion.cmake2
-rw-r--r--cmake/GenerateConfigurationFile.cmake4
-rw-r--r--doc/AUTHORS.adoc4
-rw-r--r--doc/MANUAL.adoc4
-rw-r--r--doc/NEWS.adoc55
-rwxr-xr-xmisc/clang-format65
-rwxr-xr-xmisc/format-files2
-rw-r--r--src/Args.hpp6
-rw-r--r--src/CacheEntryWriter.cpp5
-rw-r--r--src/Config.cpp5
-rw-r--r--src/Fd.hpp4
-rw-r--r--src/File.hpp4
-rw-r--r--src/MiniTrace.cpp3
-rw-r--r--src/Result.cpp3
-rw-r--r--src/ResultRetriever.cpp3
-rw-r--r--src/Sloppiness.hpp2
-rw-r--r--src/Stat.cpp7
-rw-r--r--src/Win32Util.cpp28
-rw-r--r--src/Win32Util.hpp4
-rw-r--r--src/ZstdCompressor.cpp3
-rw-r--r--src/argprocessing.cpp34
-rw-r--r--src/ccache.cpp46
-rw-r--r--src/compopt.cpp4
-rw-r--r--src/system.hpp3
-rw-r--r--test/CMakeLists.txt1
-rw-r--r--test/suites/base.bash46
-rw-r--r--test/suites/ivfsoverlay.bash44
-rw-r--r--test/suites/profiling.bash23
-rw-r--r--unittest/test_Config.cpp9
-rw-r--r--unittest/test_Stat.cpp6
37 files changed, 401 insertions, 112 deletions
diff --git a/.clang-format b/.clang-format
index f40eea4..c5ffe56 100644
--- a/.clang-format
+++ b/.clang-format
@@ -1,8 +1,9 @@
-# This configuration should work with Clang-Format 6.0 and higher.
+# This configuration should work with Clang-Format 10 and higher.
---
Language: Cpp
BasedOnStyle: LLVM
+AllowAllConstructorInitializersOnNextLine: false
AllowShortFunctionsOnASingleLine: None
AlwaysBreakAfterReturnType: AllDefinitions
AlwaysBreakBeforeMultilineStrings: true
diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml
index 662f491..07f2904 100644
--- a/.github/workflows/build.yaml
+++ b/.github/workflows/build.yaml
@@ -267,11 +267,11 @@ jobs:
- name: Clang-Tidy
os: ubuntu-18.04
- CC: clang
- CXX: clang++
+ CC: clang-9
+ CXX: clang++-9
RUN_TESTS: none
- CMAKE_PARAMS: -DENABLE_CLANG_TIDY=ON
- apt_get: libzstd-dev clang-tidy
+ CMAKE_PARAMS: -DENABLE_CLANG_TIDY=ON -DCLANGTIDY=/usr/bin/clang-tidy-9
+ apt_get: libzstd-dev clang-9 clang-tidy-9
steps:
- name: Get source
diff --git a/.gitignore b/.gitignore
index 9b69afd..74db15f 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,6 +1,9 @@
# Typical build directories
/build*/
+# Downloaded tools
+misc/.clang-format-exe
+
# Emacs save files
*~
diff --git a/.mailmap b/.mailmap
index cc87e37..7e59d6e 100644
--- a/.mailmap
+++ b/.mailmap
@@ -4,6 +4,7 @@ Anders F Björklund <anders.f.bjorklund@gmail.com> <anders@psqr.se>
Andrew Boie <andrew.p.boie@intel.com>
Arne Hasselbring <arne.hasselbring@googlemail.com>
Bernhard Bauer <bauerb@chromium.org> <bauerb@google.com>
+Bin Li <bin.li@windriver.com>
Chiaki Ishikawa <ishikawa@yk.rim.or.jp>
Clemens Rabe <clemens.rabe@gmail.com> <clemens.rabe@clemensrabe.de>
Clemens Rabe <clemens.rabe@gmail.com> <crabe@gmx.de>
diff --git a/CMakeLists.txt b/CMakeLists.txt
index fc2ff66..e186e81 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -133,7 +133,10 @@ target_link_libraries(ccache PRIVATE standard_settings standard_warnings ccache_
#
# Documentation
#
-add_subdirectory(doc)
+option(ENABLE_DOCUMENTATION "Enable documentation" ON)
+if(ENABLE_DOCUMENTATION)
+ add_subdirectory(doc)
+endif()
#
# Installation
@@ -176,26 +179,16 @@ endif()
#
# Special formatting targets
#
-find_program(
- CLANG_FORMAT_EXE
- NAMES "clang-format"
- DOC "Path to clang-format executable.")
-mark_as_advanced(CLANG_FORMAT_EXE) # Don't show in CMake UIs
-
-if(NOT CLANG_FORMAT_EXE)
- message(STATUS "clang-format not found")
-else()
- add_custom_target(
- format
- COMMAND misc/format-files --all
- COMMENT "Formatting code"
- USES_TERMINAL
- WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
-
- add_custom_target(
- check_format
- COMMAND misc/format-files --all --check
- COMMENT "Checking code formatting"
- USES_TERMINAL
- WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
-endif()
+add_custom_target(
+ format
+ COMMAND misc/format-files --all
+ COMMENT "Formatting code"
+ USES_TERMINAL
+ WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
+
+add_custom_target(
+ check_format
+ COMMAND misc/format-files --all --check
+ COMMENT "Checking code formatting"
+ USES_TERMINAL
+ WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index cb35bc0..ad4b8aa 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -56,12 +56,12 @@ little.
Source code formatting is defined by `.clang-format` in the root directory. The
format is loosely based on [LLVM's code formatting
-style](https://llvm.org/docs/CodingStandards.html) with some exceptions. It's
-highly recommended to install
-[Clang-Format](https://clang.llvm.org/docs/ClangFormat.html) 6.0 or newer and
-run `make format` to format changes according to ccache's code style. Or even
-better: set up your editor to run Clang-Format automatically when saving. If you
-don't run Clang-Format then the ccache authors have to do it for you.
+style](https://llvm.org/docs/CodingStandards.html) with some exceptions. Run
+`make format` (or `ninja format` if you use Ninja) to format changes according
+to ccache's code style. Or even better: set up your editor to run
+`<ccache-top-dir>/misc/clang-format` (or any other Clang-Format version 10
+binary) automatically when saving. Newer Clang-Format versions likely also work
+fine.
Please follow these conventions:
diff --git a/cmake/CIBuildType.cmake b/cmake/CIBuildType.cmake
index e721614..8246ecc 100644
--- a/cmake/CIBuildType.cmake
+++ b/cmake/CIBuildType.cmake
@@ -1,18 +1,18 @@
# Add a build type called "CI" which is like RelWithDebInfo but with assertions
# enabled, i.e. without passing -DNDEBUG to the compiler.
-set(CMAKE_CXX_FLAGS_CI ${CMAKE_CXX_FLAGS_RELWITHDEBINFO} CACHE STRING
+set(CMAKE_CXX_FLAGS_CI "${CMAKE_CXX_FLAGS_RELWITHDEBINFO}" CACHE STRING
"Flags used by the C++ compiler during CI builds."
FORCE)
-set(CMAKE_C_FLAGS_CI ${CMAKE_C_FLAGS_RELWITHDEBINFO} CACHE STRING
+set(CMAKE_C_FLAGS_CI "${CMAKE_C_FLAGS_RELWITHDEBINFO}" CACHE STRING
"Flags used by the C compiler during CI builds."
FORCE)
set(CMAKE_EXE_LINKER_FLAGS_CI
- ${CMAKE_EXE_LINKER_FLAGS_RELWITHDEBINFO} CACHE STRING
+ "${CMAKE_EXE_LINKER_FLAGS_RELWITHDEBINFO}" CACHE STRING
"Flags used for linking binaries during CI builds."
FORCE)
set(CMAKE_SHARED_LINKER_FLAGS_CI
- ${CMAKE_SHARED_LINKER_FLAGS_RELWITHDEBINFO} CACHE STRING
+ "${CMAKE_SHARED_LINKER_FLAGS_RELWITHDEBINFO}" CACHE STRING
"Flags used by the shared libraries linker during CI builds."
FORCE)
mark_as_advanced(
@@ -25,7 +25,7 @@ set(CMAKE_BUILD_TYPE "${CMAKE_BUILD_TYPE}" CACHE STRING
"Choose the type of build, options are: None Debug Release RelWithDebInfo MinSizeRel CI."
FORCE)
-string(REGEX REPLACE "[/-]DNDEBUG" "" CMAKE_CXX_FLAGS_CI ${CMAKE_CXX_FLAGS_CI})
-string(REGEX REPLACE "[/-]DNDEBUG" "" CMAKE_C_FLAGS_CI ${CMAKE_C_FLAGS_CI})
-string(STRIP ${CMAKE_CXX_FLAGS_CI} CMAKE_CXX_FLAGS_CI)
-string(STRIP ${CMAKE_C_FLAGS_CI} CMAKE_C_FLAGS_CI)
+string(REGEX REPLACE "[/-]DNDEBUG" "" CMAKE_CXX_FLAGS_CI "${CMAKE_CXX_FLAGS_CI}")
+string(REGEX REPLACE "[/-]DNDEBUG" "" CMAKE_C_FLAGS_CI "${CMAKE_C_FLAGS_CI}")
+string(STRIP "${CMAKE_CXX_FLAGS_CI}" CMAKE_CXX_FLAGS_CI)
+string(STRIP "${CMAKE_C_FLAGS_CI}" CMAKE_C_FLAGS_CI)
diff --git a/cmake/CcacheVersion.cmake b/cmake/CcacheVersion.cmake
index 2568fd5..c0cbd91 100644
--- a/cmake/CcacheVersion.cmake
+++ b/cmake/CcacheVersion.cmake
@@ -22,7 +22,7 @@
# CCACHE_VERSION_ORIGIN is set to "archive" in scenario 1 and "git" in scenario
# 3.
-set(version_info "1a07c09dcbba202572c5ab1bc4b736183a318aa7 HEAD, tag: v4.2.1, origin/master, origin/HEAD, master")
+set(version_info "2c13bce2609a02b70c92e84cdd177a6072f44d5e HEAD, tag: v4.3, origin/master, origin/HEAD, master")
if(version_info MATCHES "^([0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f])[0-9a-f]* (.*)")
# Scenario 1.
diff --git a/cmake/GenerateConfigurationFile.cmake b/cmake/GenerateConfigurationFile.cmake
index 6e6b604..a460529 100644
--- a/cmake/GenerateConfigurationFile.cmake
+++ b/cmake/GenerateConfigurationFile.cmake
@@ -44,7 +44,7 @@ foreach(func IN ITEMS ${functions})
endforeach()
include(CheckCSourceCompiles)
-set(CMAKE_REQUIRED_LINK_OPTIONS -pthread)
+set(CMAKE_REQUIRED_FLAGS -pthread)
check_c_source_compiles(
[=[
#include <pthread.h>
@@ -57,7 +57,7 @@ check_c_source_compiles(
]=]
HAVE_PTHREAD_MUTEX_ROBUST)
check_function_exists(pthread_mutexattr_setpshared HAVE_PTHREAD_MUTEXATTR_SETPSHARED)
-set(CMAKE_REQUIRED_LINK_OPTIONS)
+set(CMAKE_REQUIRED_FLAGS)
include(CheckStructHasMember)
check_struct_has_member("struct stat" st_ctim sys/stat.h
diff --git a/doc/AUTHORS.adoc b/doc/AUTHORS.adoc
index ce44c8c..2a8363a 100644
--- a/doc/AUTHORS.adoc
+++ b/doc/AUTHORS.adoc
@@ -22,6 +22,7 @@ Ccache is a collective work with contributions from many people, including:
* Arne Hasselbring
* Azat Khuzhin
* Bernhard Bauer
+* Bin Li
* Björn Jacke
* Breno Guimaraes
* Chiaki Ishikawa
@@ -58,6 +59,7 @@ Ccache is a collective work with contributions from many people, including:
* Jon Petrissans
* Jørgen P. Tjernø
* Josh Soref
+* Josh Triplett
* Justin Lebar
* Ka Ho Ng
* Karl Chen
@@ -106,6 +108,8 @@ Ccache is a collective work with contributions from many people, including:
* Pawel Krysiak
* Per Nordlöw
* Peter Budai
+* Peter Steinberger
+* Petr Štetiar
* Philippe Proulx
* Philipp Storz
* Rafael Kitover
diff --git a/doc/MANUAL.adoc b/doc/MANUAL.adoc
index 2b6f001..25c34c0 100644
--- a/doc/MANUAL.adoc
+++ b/doc/MANUAL.adoc
@@ -824,6 +824,10 @@ still has to do _some_ preprocessing (like macros).
mtime is too new. This sloppiness disables that check. See also
_<<_handling_of_newly_created_header_files,Handling of newly created header
files>>_.
+*ivfsoverlay*::
+ Ignore the Clang compiler option *-ivfsoverlay* and its argument. This is
+ useful if you use Xcode, which uses a virtual file system (VFS) for things
+ like combining Objective-C and Swift code.
*locale*::
Ccache includes the environment variables *LANG*, *LC_ALL*, *LC_CTYPE* and
*LC_MESSAGES* in the hash by default since they may affect localization of
diff --git a/doc/NEWS.adoc b/doc/NEWS.adoc
index 040a68e..7d69bd4 100644
--- a/doc/NEWS.adoc
+++ b/doc/NEWS.adoc
@@ -1,6 +1,55 @@
Ccache news
===========
+Ccache 4.3
+----------
+Release date: 2021-05-09
+
+New features
+~~~~~~~~~~~~
+
+- Ccache now ignores the Clang compiler option `-ivfsoverlay` and its argument
+ if you opt in to ``ivfsoverlay sloppiness''. This is useful if you use Xcode,
+ which uses a virtual file system (VFS) for things like combining Objective-C
+ and Swift code.
+
+- When using `-P` in combination with `-E`, ccache now reports this as ``called
+ for preprocessing'' instead of ``unsupported compiler option''.
+
+- Added support for `-specs file.specs` and `--specs file.specs` without an
+ equal sign between the arguments.
+
+
+Bug fixes
+~~~~~~~~~
+
+- "Split dwarf" code paths are now disabled when outputting to `/dev/null`. This
+ avoids an attempt to delete `/dev/null.dwo`.
+
+- Made the `stat`/`lstat` wrapper function for Windows treat pending deletes as
+ missing files.
+
+- Fixed a bug that made ccache process header files redundantly for some
+ relative headers when using Clang.
+
+- The object path in now included in the input hash when using `-fprofile-arcs`
+ (or `--coverage`) since the object file embeds a `.gcda` path based on the
+ object file path.
+
+
+Build improvements
+~~~~~~~~~~~~~~~~~~
+
+- Added an `ENABLE_DOCUMENTATION` build option (default: true) that can be used
+ to disable the build of documentation.
+
+- Fixed detection of pthread features.
+
+- Quote CMake variables expansions to avoid errors when
+ `${CMAKE_C_FLAGS_RELWITHDEBINFO}` or `${CMAKE_CXX_FLAGS_RELWITHDEBINFO}`
+ expands to the empty string.
+
+
Ccache 4.2.1
------------
Release date: 2021-03-27
@@ -8,9 +57,9 @@ Release date: 2021-03-27
Bug fixes
~~~~~~~~~
-- Ccache now only `dup2`s stderr into `$UNCACHED_ERR_FD` for calls to the
- preprocessor/compiler. This works around a complex bug in interaction with GNU
- Make, LTO linking and the Linux PTY driver.
+- Ccache now only duplicates the stderr file descriptor into `$UNCACHED_ERR_FD`
+ for calls to the preprocessor/compiler. This works around a complex bug in
+ interaction with GNU Make, LTO linking and the Linux PTY driver.
- Fixed detection of color diagnostics usage when using `-Xclang
-fcolor-diagnostics` options.
diff --git a/misc/clang-format b/misc/clang-format
new file mode 100755
index 0000000..b198be2
--- /dev/null
+++ b/misc/clang-format
@@ -0,0 +1,65 @@
+#!/bin/sh
+#
+# This script executes clang-format in the following order:
+#
+# 1. If environment variable CLANG_FORMAT is set, execute $CLANG_FORMAT.
+# 2. Otherwise, if <ccache-top-dir>/misc/.clang-format-exe exists, execute that
+# program.
+# 3. Otherwise, download a statically linked clang-format executable, verify its
+# integrity, place it in <ccache-top-dir>/misc/.clang-format-exe and execute
+# it.
+
+set -eu
+
+if [ -n "${CLANG_FORMAT:-}" ]; then
+ exec "$CLANG_FORMAT" "$@"
+fi
+
+top_dir="$(dirname "$0")"
+clang_format_exe="$top_dir/.clang-format-exe"
+clang_format_version=10
+url_prefix="https://github.com/muttleyxd/clang-tools-static-binaries/releases/download/master-22538c65/clang-format-${clang_format_version}_"
+
+if [ ! -x "$clang_format_exe" ]; then
+ case "$(uname -s | tr '[:upper:]' '[:lower:]')" in
+ *mingw*|*cygwin*|*msys*)
+ url_suffix=windows-amd64.exe
+ checksum=0b21dfb9041437eebcc44032096e4dfba9ee7b668ee6867ada71ea3541f7b09657ea592a5b1cf659bc9f8072bdc477dfc9da07b3edacb7834b70e68d7a3fc887
+ ;;
+ *darwin*)
+ url_suffix=macosx-amd64
+ checksum=8458753e13d3cbb7949a302beab812bed6d9dd9001c6e9618e5ba2e438233633ae04704a4e150aa2abfbaf103f1df4bc4a77b306012f44b37e543964bd527951
+ ;;
+ *linux*)
+ url_suffix=linux-amd64
+ checksum=3c4aaa90ad83313a1d7b350b30f9ad62578be73241f00f7d6e92838289e0b734fab80dee9dfcbd1546135bdb4e3601cfb2cf6b47360fba0bfc961e5a7cab2015
+ ;;
+ *)
+ echo "Error: Please set CLANG_FORMAT to clang-format version $clang_format_version" >&2
+ exit 1
+ ;;
+ esac
+
+ url="$url_prefix$url_suffix"
+
+ if command -v wget >/dev/null; then
+ wget -qO "$clang_format_exe.tmp" "$url"
+ elif command -v curl >/dev/null; then
+ curl -so "$clang_format_exe.tmp" -L --retry 20 "$url"
+ else
+ echo "Error: Neither wget nor curl found" >&2
+ exit 1
+ fi
+
+ if ! command -v sha512sum >/dev/null; then
+ echo "Warning: sha512sum not found, not verifying clang-format integrity" >&2
+ elif ! echo "$checksum $clang_format_exe.tmp" | sha512sum --status -c; then
+ echo "Error: Bad checksum of downloaded clang-format" >&2
+ exit 1
+ fi
+
+ chmod +x "$clang_format_exe.tmp"
+ mv "$clang_format_exe.tmp" "$clang_format_exe"
+fi
+
+exec "$clang_format_exe" "$@"
diff --git a/misc/format-files b/misc/format-files
index 111705a..44340b9 100755
--- a/misc/format-files
+++ b/misc/format-files
@@ -27,7 +27,7 @@ if [ -n "$all" ]; then
exec sh "$0" $check $(git ls-files '*.[ch]' '*.[ch]pp' ':!:src/third_party')
fi
-clang_format=${CLANG_FORMAT:-clang-format}
+clang_format="$(dirname "$0")/clang-format"
[ -t 1 ] && cf_color="--color=always" || cf_color=""
if [ -n "${VERBOSE:-}" ]; then
diff --git a/src/Args.hpp b/src/Args.hpp
index ae42809..48fb77d 100644
--- a/src/Args.hpp
+++ b/src/Args.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2020 Joel Rosdahl and other contributors
+// Copyright (C) 2020-2021 Joel Rosdahl and other contributors
//
// See doc/AUTHORS.adoc for a complete list of contributors.
//
@@ -115,18 +115,14 @@ Args::size() const
return m_args.size();
}
-// clang-format off
inline const std::string&
Args::operator[](size_t i) const
-// clang-format on
{
return m_args[i];
}
-// clang-format off
inline std::string&
Args::operator[](size_t i)
-// clang-format on
{
return m_args[i];
}
diff --git a/src/CacheEntryWriter.cpp b/src/CacheEntryWriter.cpp
index 8f45adf..b936947 100644
--- a/src/CacheEntryWriter.cpp
+++ b/src/CacheEntryWriter.cpp
@@ -26,10 +26,9 @@ CacheEntryWriter::CacheEntryWriter(FILE* stream,
uint64_t payload_size)
// clang-format off
: m_compressor(
- Compressor::create_from_type(compression_type, stream, compression_level)
- )
+ Compressor::create_from_type(compression_type, stream, compression_level))
+// clang-format on
{
- // clang-format on
uint8_t header_bytes[15];
memcpy(header_bytes, magic, 4);
header_bytes[4] = version;
diff --git a/src/Config.cpp b/src/Config.cpp
index 68dc3f5..9e70923 100644
--- a/src/Config.cpp
+++ b/src/Config.cpp
@@ -275,6 +275,8 @@ parse_sloppiness(const std::string& value)
result |= SLOPPY_LOCALE;
} else if (token == "modules") {
result |= SLOPPY_MODULES;
+ } else if (token == "ivfsoverlay") {
+ result |= SLOPPY_IVFSOVERLAY;
} // else: ignore unknown value for forward compatibility
start = value.find_first_not_of(", ", end);
}
@@ -315,6 +317,9 @@ format_sloppiness(uint32_t sloppiness)
if (sloppiness & SLOPPY_MODULES) {
result += "modules, ";
}
+ if (sloppiness & SLOPPY_IVFSOVERLAY) {
+ result += "ivfsoverlay, ";
+ }
if (!result.empty()) {
// Strip last ", ".
result.resize(result.size() - 2);
diff --git a/src/Fd.hpp b/src/Fd.hpp
index 80bc77e..6316e45 100644
--- a/src/Fd.hpp
+++ b/src/Fd.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2020 Joel Rosdahl and other contributors
+// Copyright (C) 2020-2021 Joel Rosdahl and other contributors
//
// See doc/AUTHORS.adoc for a complete list of contributors.
//
@@ -72,10 +72,8 @@ Fd::get() const
return m_fd;
}
-// clang-format off
inline int
Fd::operator*() const
-// clang-format on
{
ASSERT(m_fd != -1);
return m_fd;
diff --git a/src/File.hpp b/src/File.hpp
index 6f0dd21..f8f6c0b 100644
--- a/src/File.hpp
+++ b/src/File.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2019-2020 Joel Rosdahl and other contributors
+// Copyright (C) 2019-2021 Joel Rosdahl and other contributors
//
// See doc/AUTHORS.adoc for a complete list of contributors.
//
@@ -89,10 +89,8 @@ inline File::operator bool() const
return m_file;
}
-// clang-format off
inline FILE*
File::operator*() const
-// clang-format on
{
return m_file;
}
diff --git a/src/MiniTrace.cpp b/src/MiniTrace.cpp
index bf17397..0516562 100644
--- a/src/MiniTrace.cpp
+++ b/src/MiniTrace.cpp
@@ -65,7 +65,8 @@ time_seconds()
} // namespace
MiniTrace::MiniTrace(const ArgsInfo& args_info)
- : m_args_info(args_info), m_trace_id(reinterpret_cast<void*>(getpid()))
+ : m_args_info(args_info),
+ m_trace_id(reinterpret_cast<void*>(getpid()))
{
TemporaryFile tmp_file(get_system_tmp_dir() + "/ccache-trace");
m_tmp_trace_file = tmp_file.path;
diff --git a/src/Result.cpp b/src/Result.cpp
index b20aa62..8408d2a 100644
--- a/src/Result.cpp
+++ b/src/Result.cpp
@@ -300,7 +300,8 @@ Reader::read_entry(CacheEntryReader& cache_entry_reader,
}
Writer::Writer(Context& ctx, const std::string& result_path)
- : m_ctx(ctx), m_result_path(result_path)
+ : m_ctx(ctx),
+ m_result_path(result_path)
{
}
diff --git a/src/ResultRetriever.cpp b/src/ResultRetriever.cpp
index 957bbee..0218877 100644
--- a/src/ResultRetriever.cpp
+++ b/src/ResultRetriever.cpp
@@ -25,7 +25,8 @@
using Result::FileType;
ResultRetriever::ResultRetriever(Context& ctx, bool rewrite_dependency_target)
- : m_ctx(ctx), m_rewrite_dependency_target(rewrite_dependency_target)
+ : m_ctx(ctx),
+ m_rewrite_dependency_target(rewrite_dependency_target)
{
}
diff --git a/src/Sloppiness.hpp b/src/Sloppiness.hpp
index bd2078e..62c0508 100644
--- a/src/Sloppiness.hpp
+++ b/src/Sloppiness.hpp
@@ -38,4 +38,6 @@ enum Sloppiness {
SLOPPY_LOCALE = 1 << 8,
// Allow caching even if -fmodules is used.
SLOPPY_MODULES = 1 << 9,
+ // Ignore virtual file system (VFS) overlay file.
+ SLOPPY_IVFSOVERLAY = 1 << 10,
};
diff --git a/src/Stat.cpp b/src/Stat.cpp
index d491682..244fd6f 100644
--- a/src/Stat.cpp
+++ b/src/Stat.cpp
@@ -19,6 +19,8 @@
#include "Stat.hpp"
#ifdef _WIN32
+# include "Win32Util.hpp"
+
# include "third_party/win32/winerror_to_errno.h"
#endif
@@ -124,6 +126,11 @@ win32_stat_impl(const char* path, bool traverse_links, Stat::stat_t* st)
}
if (handle == INVALID_HANDLE_VALUE) {
+ if (GetLastError() == ERROR_ACCESS_DENIED
+ && Win32Util::get_last_ntstatus() == STATUS_DELETE_PENDING) {
+ // Treat a 'pending delete' as a nonexistent file.
+ SetLastError(ERROR_FILE_NOT_FOUND);
+ }
return false;
}
diff --git a/src/Win32Util.cpp b/src/Win32Util.cpp
index b259ed0..1a9de6a 100644
--- a/src/Win32Util.cpp
+++ b/src/Win32Util.cpp
@@ -23,6 +23,26 @@
#include <chrono>
#include <thread>
+namespace {
+
+template<typename Proc>
+Proc*
+get_proc_address(HMODULE module, const char* proc_name)
+{
+#if defined __GNUC__
+# pragma GCC diagnostic push
+# if __GNUC__ >= 8
+# pragma GCC diagnostic ignored "-Wcast-function-type"
+# endif
+#endif
+ return reinterpret_cast<Proc*>(GetProcAddress(module, proc_name));
+#if defined __GNUC__
+# pragma GCC diagnostic pop
+#endif
+}
+
+} // namespace
+
namespace Win32Util {
std::string
@@ -97,6 +117,14 @@ argv_to_string(const char* const* argv,
return result;
}
+NTSTATUS
+get_last_ntstatus()
+{
+ static auto* get_last_ntstatus_fn = get_proc_address<NTSTATUS NTAPI()>(
+ GetModuleHandleA("ntdll.dll"), "RtlGetLastNtStatus");
+ return get_last_ntstatus_fn();
+}
+
} // namespace Win32Util
// From: https://stackoverflow.com/a/58162122/262458
diff --git a/src/Win32Util.hpp b/src/Win32Util.hpp
index d6fc575..0a2f1a1 100644
--- a/src/Win32Util.hpp
+++ b/src/Win32Util.hpp
@@ -39,4 +39,8 @@ std::string argv_to_string(const char* const* argv,
// Return the error message corresponding to `error_code`.
std::string error_message(DWORD error_code);
+// Returns the last NTSTATUS code. (These can be more specific than the
+// corresponding Win32 error code.)
+NTSTATUS get_last_ntstatus();
+
} // namespace Win32Util
diff --git a/src/ZstdCompressor.cpp b/src/ZstdCompressor.cpp
index a53cfa2..39f6bb2 100644
--- a/src/ZstdCompressor.cpp
+++ b/src/ZstdCompressor.cpp
@@ -25,7 +25,8 @@
#include <algorithm>
ZstdCompressor::ZstdCompressor(FILE* stream, int8_t compression_level)
- : m_stream(stream), m_zstd_stream(ZSTD_createCStream())
+ : m_stream(stream),
+ m_zstd_stream(ZSTD_createCStream())
{
if (compression_level == 0) {
compression_level = default_compression_level;
diff --git a/src/argprocessing.cpp b/src/argprocessing.cpp
index e39c4e5..92b929e 100644
--- a/src/argprocessing.cpp
+++ b/src/argprocessing.cpp
@@ -232,6 +232,15 @@ process_arg(Context& ctx,
return nullopt;
}
+ // Ignore clang -ivfsoverlay <arg> to not detect multiple input files.
+ if (args[i] == "-ivfsoverlay"
+ && !(config.sloppiness() & SLOPPY_IVFSOVERLAY)) {
+ LOG_RAW(
+ "You have to specify \"ivfsoverlay\" sloppiness when using"
+ " -ivfsoverlay to get hits");
+ return Statistic::unsupported_compiler_option;
+ }
+
// Special case for -E.
if (args[i] == "-E") {
return Statistic::called_for_preprocessing;
@@ -618,13 +627,19 @@ process_arg(Context& ctx,
return nullopt;
}
+ if (args[i] == "-P" || args[i] == "-Wp,-P") {
+ // Avoid passing -P to the preprocessor since it removes preprocessor
+ // information we need.
+ state.compiler_only_args.push_back(args[i]);
+ LOG("{} used; not compiling preprocessed code", args[i]);
+ config.set_run_second_cpp(true);
+ return nullopt;
+ }
+
if (Util::starts_with(args[i], "-Wp,")) {
- if (args[i] == "-Wp,-P" || args[i].find(",-P,") != std::string::npos
+ if (args[i].find(",-P,") != std::string::npos
|| Util::ends_with(args[i], ",-P")) {
- // -P removes preprocessor information in such a way that the object file
- // from compiling the preprocessed file will not be equal to the object
- // file produced when compiling without ccache.
- LOG_RAW("Too hard option -Wp,-P detected");
+ // -P together with other preprocessor options is just too hard.
return Statistic::unsupported_compiler_option;
} else if (Util::starts_with(args[i], "-Wp,-MD,")
&& args[i].find(',', 8) == std::string::npos) {
@@ -1107,7 +1122,14 @@ process_args(Context& ctx)
}
if (args_info.seen_split_dwarf) {
- args_info.output_dwo = Util::change_extension(args_info.output_obj, ".dwo");
+ if (args_info.output_obj == "/dev/null") {
+ // Outputting to /dev/null -> compiler won't write a .dwo, so just pretend
+ // we haven't seen the -gsplit-dwarf option.
+ args_info.seen_split_dwarf = false;
+ } else {
+ args_info.output_dwo =
+ Util::change_extension(args_info.output_obj, ".dwo");
+ }
}
// Cope with -o /dev/null.
diff --git a/src/ccache.cpp b/src/ccache.cpp
index 7d39e5b..761b9ab 100644
--- a/src/ccache.cpp
+++ b/src/ccache.cpp
@@ -205,7 +205,8 @@ private:
};
inline Failure::Failure(Statistic statistic, nonstd::optional<int> exit_code)
- : m_statistic(statistic), m_exit_code(exit_code)
+ : m_statistic(statistic),
+ m_exit_code(exit_code)
{
}
@@ -398,16 +399,16 @@ do_remember_include_file(Context& ctx,
return true;
}
- if (ctx.included_files.find(path) != ctx.included_files.end()) {
- // Already known include file.
- return true;
- }
-
// Canonicalize path for comparison; Clang uses ./header.h.
if (Util::starts_with(path, "./")) {
path.erase(0, 2);
}
+ if (ctx.included_files.find(path) != ctx.included_files.end()) {
+ // Already known include file.
+ return true;
+ }
+
#ifdef _WIN32
{
// stat fails on directories on win32.
@@ -1425,14 +1426,17 @@ hash_common_info(const Context& ctx,
if ((!should_rewrite_dependency_target(ctx.args_info)
&& ctx.args_info.generating_dependencies)
- || ctx.args_info.seen_split_dwarf) {
- // The output object file name is part of the .d file, so include the path
- // in the hash if generating dependencies.
+ || ctx.args_info.seen_split_dwarf || ctx.args_info.profile_arcs) {
+ // If generating dependencies: The output object file name is part of the .d
+ // file, so include the path in the hash.
//
- // Object files include a link to the corresponding .dwo file based on the
- // target object filename when using -gsplit-dwarf, so hashing the object
- // file path will do it, although just hashing the object file base name
- // would be enough.
+ // When using -gsplit-dwarf: Object files include a link to the
+ // corresponding .dwo file based on the target object filename, so hashing
+ // the object file path will do it, although just hashing the object file
+ // base name would be enough.
+ //
+ // When using -fprofile-arcs (including implicitly via --coverage): the
+ // object file contains a .gcda path based on the object file path.
hash.hash_delimiter("object file");
hash.hash(ctx.args_info.output_obj);
}
@@ -1652,8 +1656,20 @@ calculate_result_name(Context& ctx,
}
if (Util::starts_with(args[i], "-specs=")
- || Util::starts_with(args[i], "--specs=")) {
- std::string path = args[i].substr(args[i].find('=') + 1);
+ || Util::starts_with(args[i], "--specs=")
+ || (args[i] == "-specs" || args[i] == "--specs")) {
+ std::string path;
+ size_t eq_pos = args[i].find('=');
+ if (eq_pos == std::string::npos) {
+ if (i + 1 >= args.size()) {
+ LOG("missing argument for \"{}\"", args[i]);
+ throw Failure(Statistic::bad_compiler_arguments);
+ }
+ path = args[i + 1];
+ i++;
+ } else {
+ path = args[i].substr(eq_pos + 1);
+ }
auto st = Stat::stat(path, Stat::OnError::log);
if (st) {
// If given an explicit specs file, then hash that file, but don't
diff --git a/src/compopt.cpp b/src/compopt.cpp
index d69f74a..3ed4f5b 100644
--- a/src/compopt.cpp
+++ b/src/compopt.cpp
@@ -62,6 +62,7 @@ const CompOpt compopts[] = {
{"--save-temps=cwd", TOO_HARD},
{"--save-temps=obj", TOO_HARD},
{"--serialize-diagnostics", TAKES_ARG | TAKES_PATH},
+ {"--specs", TAKES_ARG},
{"-A", TAKES_ARG},
{"-B", TAKES_ARG | TAKES_CONCAT_ARG | TAKES_PATH},
{"-D", AFFECTS_CPP | TAKES_ARG | TAKES_CONCAT_ARG},
@@ -76,7 +77,6 @@ const CompOpt compopts[] = {
{"-MM", TOO_HARD},
{"-MQ", TAKES_ARG},
{"-MT", TAKES_ARG},
- {"-P", TOO_HARD},
{"-U", AFFECTS_CPP | TAKES_ARG | TAKES_CONCAT_ARG},
{"-V", TAKES_ARG},
{"-Wa,", TAKES_CONCAT_ARG | AFFECTS_COMP},
@@ -116,6 +116,7 @@ const CompOpt compopts[] = {
{"-iquote", AFFECTS_CPP | TAKES_ARG | TAKES_CONCAT_ARG | TAKES_PATH},
{"-isysroot", AFFECTS_CPP | TAKES_ARG | TAKES_CONCAT_ARG | TAKES_PATH},
{"-isystem", AFFECTS_CPP | TAKES_ARG | TAKES_CONCAT_ARG | TAKES_PATH},
+ {"-ivfsoverlay", TAKES_ARG},
{"-iwithprefix", AFFECTS_CPP | TAKES_ARG | TAKES_CONCAT_ARG | TAKES_PATH},
{"-iwithprefixbefore",
AFFECTS_CPP | TAKES_ARG | TAKES_CONCAT_ARG | TAKES_PATH},
@@ -132,6 +133,7 @@ const CompOpt compopts[] = {
{"-save-temps", TOO_HARD},
{"-save-temps=cwd", TOO_HARD},
{"-save-temps=obj", TOO_HARD},
+ {"-specs", TAKES_ARG},
{"-stdlib=", AFFECTS_CPP | TAKES_CONCAT_ARG},
{"-trigraphs", AFFECTS_CPP},
{"-u", TAKES_ARG | TAKES_CONCAT_ARG},
diff --git a/src/system.hpp b/src/system.hpp
index 6115c5b..fa4bbf3 100644
--- a/src/system.hpp
+++ b/src/system.hpp
@@ -158,7 +158,10 @@ const mode_t S_IWUSR = mode_t(_S_IWRITE);
# include <io.h>
# include <process.h>
# define NOMINMAX 1
+# define WIN32_NO_STATUS
# include <windows.h>
+# undef WIN32_NO_STATUS
+# include <ntstatus.h>
# define mkdir(a, b) _mkdir(a)
# define execv(a, b) \
do_not_call_execv_on_windows // to protect against incidental use of MinGW
diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt
index c33befd..ae0df8e 100644
--- a/test/CMakeLists.txt
+++ b/test/CMakeLists.txt
@@ -47,6 +47,7 @@ addtest(fileclone)
addtest(hardlink)
addtest(inode_cache)
addtest(input_charset)
+addtest(ivfsoverlay)
addtest(masquerading)
addtest(modules)
addtest(multi_arch)
diff --git a/test/suites/base.bash b/test/suites/base.bash
index 9629a06..37b7755 100644
--- a/test/suites/base.bash
+++ b/test/suites/base.bash
@@ -1224,43 +1224,59 @@ EOF
expect_stat 'files in cache' 0
# -------------------------------------------------------------------------
- TEST "-P"
+ TEST "-P -c"
- # Check that -P disables ccache. (-P removes preprocessor information in
- # such a way that the object file from compiling the preprocessed file will
- # not be equal to the object file produced when compiling without ccache.)
+ $CCACHE_COMPILE -P -c test1.c
+ expect_stat 'cache hit (direct)' 0
+ expect_stat 'cache hit (preprocessed)' 0
+ expect_stat 'cache miss' 1
- $CCACHE_COMPILE -c -P test1.c
+ $CCACHE_COMPILE -P -c test1.c
+ expect_stat 'cache hit (direct)' 0
+ expect_stat 'cache hit (preprocessed)' 1
+ expect_stat 'cache miss' 1
+
+ # -------------------------------------------------------------------------
+ TEST "-P -E"
+
+ $CCACHE_COMPILE -P -E test1.c
expect_stat 'cache hit (direct)' 0
expect_stat 'cache hit (preprocessed)' 0
expect_stat 'cache miss' 0
- expect_stat 'unsupported compiler option' 1
+ expect_stat 'called for preprocessing' 1
# -------------------------------------------------------------------------
TEST "-Wp,-P"
- # Check that -Wp,-P disables ccache. (-P removes preprocessor information
- # in such a way that the object file from compiling the preprocessed file
- # will not be equal to the object file produced when compiling without
- # ccache.)
-
$CCACHE_COMPILE -c -Wp,-P test1.c
expect_stat 'cache hit (direct)' 0
expect_stat 'cache hit (preprocessed)' 0
- expect_stat 'cache miss' 0
- expect_stat 'unsupported compiler option' 1
+ expect_stat 'cache miss' 1
+
+ $CCACHE_COMPILE -c -Wp,-P test1.c
+ expect_stat 'cache hit (direct)' 0
+ expect_stat 'cache hit (preprocessed)' 1
+ expect_stat 'cache miss' 1
+
+ # -------------------------------------------------------------------------
+ TEST "-Wp,-P,-DFOO"
+
+ # Check that -P disables ccache when used in combination with other -Wp,
+ # options. (-P removes preprocessor information in such a way that the
+ # object file from compiling the preprocessed file will not be equal to the
+ # object file produced when compiling without ccache.)
$CCACHE_COMPILE -c -Wp,-P,-DFOO test1.c
expect_stat 'cache hit (direct)' 0
expect_stat 'cache hit (preprocessed)' 0
expect_stat 'cache miss' 0
- expect_stat 'unsupported compiler option' 2
+ expect_stat 'unsupported compiler option' 1
$CCACHE_COMPILE -c -Wp,-DFOO,-P test1.c
expect_stat 'cache hit (direct)' 0
expect_stat 'cache hit (preprocessed)' 0
expect_stat 'cache miss' 0
- expect_stat 'unsupported compiler option' 3
+ expect_stat 'unsupported compiler option' 2
# -------------------------------------------------------------------------
TEST "-Wp,-D"
diff --git a/test/suites/ivfsoverlay.bash b/test/suites/ivfsoverlay.bash
new file mode 100644
index 0000000..ca88221
--- /dev/null
+++ b/test/suites/ivfsoverlay.bash
@@ -0,0 +1,44 @@
+SUITE_ivfsoverlay_PROBE() {
+ if ! $COMPILER_TYPE_CLANG; then
+ echo "-ivfsoverlay not supported by compiler"
+ else
+ touch test.c
+ cat <<EOF >test.yaml
+{"case-sensitive":"false","roots":[],"version":0}
+EOF
+ $COMPILER -ivfsoverlay test.yaml test.c -S || echo "compiler does not support -ivfsoverlay"
+ fi
+}
+
+SUITE_ivfsoverlay_SETUP() {
+ unset CCACHE_NODIRECT
+
+ cat <<EOF >test.yaml
+{"case-sensitive":"false","roots":[],"version":0}
+EOF
+ cat <<EOF >test.c
+// test.c
+int test;
+EOF
+}
+
+SUITE_ivfsoverlay() {
+ # -------------------------------------------------------------------------
+ TEST "without sloppy ivfsoverlay"
+
+ $CCACHE_COMPILE -ivfsoverlay test.yaml -c test.c
+ expect_stat 'cache hit (direct)' 0
+ expect_stat 'cache miss' 0
+ expect_stat 'unsupported compiler option' 1
+
+ # -------------------------------------------------------------------------
+ TEST "with sloppy ivfsoverlay"
+
+ CCACHE_SLOPPINESS="$DEFAULT_SLOPPINESS ivfsoverlay" $CCACHE_COMPILE -ivfsoverlay test.yaml -c test.c
+ expect_stat 'cache hit (direct)' 0
+ expect_stat 'cache miss' 1
+
+ CCACHE_SLOPPINESS="$DEFAULT_SLOPPINESS ivfsoverlay" $CCACHE_COMPILE -ivfsoverlay test.yaml -c test.c
+ expect_stat 'cache hit (direct)' 1
+ expect_stat 'cache miss' 1
+}
diff --git a/test/suites/profiling.bash b/test/suites/profiling.bash
index b7abaa2..dbe36d4 100644
--- a/test/suites/profiling.bash
+++ b/test/suites/profiling.bash
@@ -128,6 +128,29 @@ SUITE_profiling() {
rm "$gcno_name"
done
done
+
+ # -------------------------------------------------------------------------
+ TEST "-fprofile-arcs for different object file paths"
+
+ mkdir obj1 obj2
+
+ $CCACHE_COMPILE -fprofile-arcs -c test.c -o obj1/test.o
+ expect_stat 'cache hit (direct)' 0
+ expect_stat 'cache miss' 1
+
+ $CCACHE_COMPILE -fprofile-arcs -c test.c -o obj1/test.o
+ expect_stat 'cache hit (direct)' 1
+ expect_stat 'cache miss' 1
+
+ $CCACHE_COMPILE -fprofile-arcs -c test.c -o obj2/test.o
+ expect_different_content obj1/test.o obj2/test.o # different paths to .gcda file
+ expect_stat 'cache hit (direct)' 1
+ expect_stat 'cache miss' 2
+
+ $CCACHE_COMPILE -fprofile-arcs -c test.c -o obj2/test.o
+ expect_different_content obj1/test.o obj2/test.o # different paths to .gcda file
+ expect_stat 'cache hit (direct)' 2
+ expect_stat 'cache miss' 2
}
merge_profiling_data() {
diff --git a/unittest/test_Config.cpp b/unittest/test_Config.cpp
index fad4ff4..e509c9c 100644
--- a/unittest/test_Config.cpp
+++ b/unittest/test_Config.cpp
@@ -128,7 +128,7 @@ TEST_CASE("Config::update_from_file")
"run_second_cpp = false\n"
"sloppiness = time_macros ,include_file_mtime"
" include_file_ctime,file_stat_matches,file_stat_matches_ctime,pch_defines"
- " , no_system_headers,system_headers,clang_index_store\n"
+ " , no_system_headers,system_headers,clang_index_store,ivfsoverlay\n"
"stats = false\n"
"temporary_dir = ${USER}_foo\n"
"umask = 777"); // Note: no newline.
@@ -169,7 +169,8 @@ TEST_CASE("Config::update_from_file")
== (SLOPPY_INCLUDE_FILE_MTIME | SLOPPY_INCLUDE_FILE_CTIME
| SLOPPY_TIME_MACROS | SLOPPY_FILE_STAT_MATCHES
| SLOPPY_FILE_STAT_MATCHES_CTIME | SLOPPY_SYSTEM_HEADERS
- | SLOPPY_PCH_DEFINES | SLOPPY_CLANG_INDEX_STORE));
+ | SLOPPY_PCH_DEFINES | SLOPPY_CLANG_INDEX_STORE
+ | SLOPPY_IVFSOVERLAY));
CHECK_FALSE(config.stats());
CHECK(config.temporary_dir() == FMT("{}_foo", user));
CHECK(config.umask() == 0777);
@@ -402,7 +403,7 @@ TEST_CASE("Config::visit_items")
"run_second_cpp = false\n"
"sloppiness = include_file_mtime, include_file_ctime, time_macros,"
" file_stat_matches, file_stat_matches_ctime, pch_defines, system_headers,"
- " clang_index_store\n"
+ " clang_index_store, ivfsoverlay\n"
"stats = false\n"
"temporary_dir = td\n"
"umask = 022\n");
@@ -459,7 +460,7 @@ TEST_CASE("Config::visit_items")
"(test.conf) run_second_cpp = false",
"(test.conf) sloppiness = include_file_mtime, include_file_ctime,"
" time_macros, pch_defines, file_stat_matches, file_stat_matches_ctime,"
- " system_headers, clang_index_store",
+ " system_headers, clang_index_store, ivfsoverlay",
"(test.conf) stats = false",
"(test.conf) temporary_dir = td",
"(test.conf) umask = 022",
diff --git a/unittest/test_Stat.cpp b/unittest/test_Stat.cpp
index 6f8baa6..e5b6eeb 100644
--- a/unittest/test_Stat.cpp
+++ b/unittest/test_Stat.cpp
@@ -579,7 +579,7 @@ TEST_CASE("Win32 Pending Delete" * doctest::skip(running_under_wine()))
// will persist until the handle is closed. Until the file is closed, new
// handles cannot be created to the file; attempts to do so fail with
// ERROR_ACCESS_DENIED/STATUS_DELETE_PENDING. Our stat implementation maps
- // these to EACCES. (Should this be ENOENT?)
+ // these to ENOENT.
FILE_DISPOSITION_INFO info{};
info.DeleteFile = TRUE;
REQUIRE_MESSAGE(SetFileInformationByHandle(
@@ -590,14 +590,14 @@ TEST_CASE("Win32 Pending Delete" * doctest::skip(running_under_wine()))
{
auto st = Stat::stat("file");
CHECK(!st);
- CHECK(st.error_number() == EACCES);
+ CHECK(st.error_number() == ENOENT);
}
SUBCASE("lstat file pending delete")
{
auto st = Stat::lstat("file");
CHECK(!st);
- CHECK(st.error_number() == EACCES);
+ CHECK(st.error_number() == ENOENT);
}
}