1 //===- Tester.cpp ---------------------------------------------------------===// 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 defines the Tester class used in the MLIR Reduce tool. 10 // 11 // A Tester object is passed as an argument to the reduction passes and it is 12 // used to run the interestingness testing script on the different generated 13 // reduced variants of the test case. 14 // 15 //===----------------------------------------------------------------------===// 16 17 #include "mlir/Reducer/Tester.h" 18 19 #include "llvm/Support/ToolOutputFile.h" 20 21 using namespace mlir; 22 23 Tester::Tester(StringRef scriptName, ArrayRef<std::string> scriptArgs) 24 : testScript(scriptName), testScriptArgs(scriptArgs) {} 25 26 std::pair<Tester::Interestingness, size_t> 27 Tester::isInteresting(ModuleOp module) const { 28 SmallString<128> filepath; 29 int fd; 30 31 // Print module to temporary file. 32 std::error_code ec = 33 llvm::sys::fs::createTemporaryFile("mlir-reduce", "mlir", fd, filepath); 34 35 if (ec) 36 llvm::report_fatal_error("Error making unique filename: " + ec.message()); 37 38 llvm::ToolOutputFile out(filepath, fd); 39 module.print(out.os()); 40 out.os().close(); 41 42 if (out.os().has_error()) 43 llvm::report_fatal_error("Error emitting the IR to file '" + filepath); 44 45 size_t size = out.os().tell(); 46 return std::make_pair(isInteresting(filepath), size); 47 } 48 49 /// Runs the interestingness testing script on a MLIR test case file. Returns 50 /// true if the interesting behavior is present in the test case or false 51 /// otherwise. 52 Tester::Interestingness Tester::isInteresting(StringRef testCase) const { 53 54 std::vector<StringRef> testerArgs; 55 testerArgs.push_back(testCase); 56 57 for (const std::string &arg : testScriptArgs) 58 testerArgs.push_back(arg); 59 60 testerArgs.push_back(testCase); 61 62 std::string errMsg; 63 int result = llvm::sys::ExecuteAndWait( 64 testScript, testerArgs, /*Env=*/None, /*Redirects=*/None, 65 /*SecondsToWait=*/0, /*MemoryLimit=*/0, &errMsg); 66 67 if (result < 0) 68 llvm::report_fatal_error("Error running interestingness test: " + errMsg, 69 false); 70 71 if (!result) 72 return Interestingness::False; 73 74 return Interestingness::True; 75 } 76