From ce9707f0de5ef749500a627f42657ebb92627a04 Mon Sep 17 00:00:00 2001 From: Oleg Ranevskyy Date: Tue, 5 Jan 2016 19:54:39 +0000 Subject: [PATCH] [Clang/Support/Windows/Unix] Command lines created by clang may exceed the command length limit set by the OS Summary: LLVM part of the patch is D15831. When clang runs an external tool such as a linker it may create a command line that exceeds the length limit. Clang uses the llvm::sys::argumentsFitWithinSystemLimits function to check if command line length fits the OS limitation. There are two problems in this function that may cause exceeding of the limit: 1. It ignores the length of the program path in its calculations. On the other hand, clang adds the program path to the command line when it runs the program. 2. It assumes no space character is inserted after the last argument, which is not true for Windows. The flattenArgs function adds the trailing space for *each* argument. The result of this is that the terminating NULL character is not counted and may be placed beyond the length limit if the command line is exactly 32768 characters long. The WinAPI's CreateProcess does not find the NULL character and fails. Reviewers: rafael, asl Subscribers: asl, llvm-commits Differential Revision: http://reviews.llvm.org/D15832 git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@256865 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Driver/Driver.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/Driver/Driver.cpp b/lib/Driver/Driver.cpp index 4f8481c0be..85bbcb4113 100644 --- a/lib/Driver/Driver.cpp +++ b/lib/Driver/Driver.cpp @@ -699,11 +699,11 @@ void Driver::generateCompilationDiagnostics(Compilation &C, } void Driver::setUpResponseFiles(Compilation &C, Command &Cmd) { - // Since argumentsFitWithinSystemLimits() may underestimate system's capacity + // Since commandLineFitsWithinSystemLimits() may underestimate system's capacity // if the tool does not support response files, there is a chance/ that things // will just work without a response file, so we silently just skip it. if (Cmd.getCreator().getResponseFilesSupport() == Tool::RF_None || - llvm::sys::argumentsFitWithinSystemLimits(Cmd.getArguments())) + llvm::sys::commandLineFitsWithinSystemLimits(Cmd.getExecutable(), Cmd.getArguments())) return; std::string TmpName = GetTemporaryPath("response", "txt"); -- 2.40.0