1 //===-- Program.cpp - Implement OS Program Concept --------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file implements the operating system Program concept. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #include "llvm/Support/Program.h" 14 #include "llvm/ADT/StringRef.h" 15 #include "llvm/Config/llvm-config.h" 16 #include <system_error> 17 using namespace llvm; 18 using namespace sys; 19 20 //===----------------------------------------------------------------------===// 21 //=== WARNING: Implementation here must contain only TRULY operating system 22 //=== independent code. 23 //===----------------------------------------------------------------------===// 24 25 static bool Execute(ProcessInfo &PI, StringRef Program, 26 ArrayRef<StringRef> Args, Optional<ArrayRef<StringRef>> Env, 27 ArrayRef<Optional<StringRef>> Redirects, 28 unsigned MemoryLimit, std::string *ErrMsg); 29 30 int sys::ExecuteAndWait(StringRef Program, ArrayRef<StringRef> Args, 31 Optional<ArrayRef<StringRef>> Env, 32 ArrayRef<Optional<StringRef>> Redirects, 33 unsigned SecondsToWait, unsigned MemoryLimit, 34 std::string *ErrMsg, bool *ExecutionFailed, 35 Optional<ProcessStatistics> *ProcStat) { 36 assert(Redirects.empty() || Redirects.size() == 3); 37 ProcessInfo PI; 38 if (Execute(PI, Program, Args, Env, Redirects, MemoryLimit, ErrMsg)) { 39 if (ExecutionFailed) 40 *ExecutionFailed = false; 41 ProcessInfo Result = 42 Wait(PI, SecondsToWait, /*WaitUntilTerminates=*/SecondsToWait == 0, 43 ErrMsg, ProcStat); 44 return Result.ReturnCode; 45 } 46 47 if (ExecutionFailed) 48 *ExecutionFailed = true; 49 50 return -1; 51 } 52 53 ProcessInfo sys::ExecuteNoWait(StringRef Program, ArrayRef<StringRef> Args, 54 Optional<ArrayRef<StringRef>> Env, 55 ArrayRef<Optional<StringRef>> Redirects, 56 unsigned MemoryLimit, std::string *ErrMsg, 57 bool *ExecutionFailed) { 58 assert(Redirects.empty() || Redirects.size() == 3); 59 ProcessInfo PI; 60 if (ExecutionFailed) 61 *ExecutionFailed = false; 62 if (!Execute(PI, Program, Args, Env, Redirects, MemoryLimit, ErrMsg)) 63 if (ExecutionFailed) 64 *ExecutionFailed = true; 65 66 return PI; 67 } 68 69 bool sys::commandLineFitsWithinSystemLimits(StringRef Program, 70 ArrayRef<const char *> Args) { 71 SmallVector<StringRef, 8> StringRefArgs; 72 StringRefArgs.reserve(Args.size()); 73 for (const char *A : Args) 74 StringRefArgs.emplace_back(A); 75 return commandLineFitsWithinSystemLimits(Program, StringRefArgs); 76 } 77 78 // Include the platform-specific parts of this class. 79 #ifdef LLVM_ON_UNIX 80 #include "Unix/Program.inc" 81 #endif 82 #ifdef _WIN32 83 #include "Windows/Program.inc" 84 #endif 85