Add a createUniqueFile function and switch llvm's users of unique_file.
authorRafael Espindola <rafael.espindola@gmail.com>
Fri, 5 Jul 2013 21:01:08 +0000 (21:01 +0000)
committerRafael Espindola <rafael.espindola@gmail.com>
Fri, 5 Jul 2013 21:01:08 +0000 (21:01 +0000)
This function is complementary to createTemporaryFile. It handles the case were
the unique file is *not* temporary: we will rename it in the end. Since we
will rename it, the file has to be in the same filesystem as the final
destination and we don't prepend the system temporary directory.

This has a small semantic difference from unique_file: the default mode is 0666.
This matches the behavior of most unix tools. For example, with this change
lld now produces files with the same permissions as ld. I will add a test
of this change when I port clang over to createUniqueFile (next commit).

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@185726 91177308-0d34-0410-b5e6-96231b3b80d8

include/llvm/Support/FileSystem.h
lib/Support/FileOutputBuffer.cpp
lib/Support/LockFileManager.cpp
lib/Support/Path.cpp
tools/bugpoint/ExecutionDriver.cpp
tools/bugpoint/ExtractFunction.cpp
tools/bugpoint/OptimizerDriver.cpp
tools/bugpoint/ToolRunner.cpp
tools/llvm-ar/ArchiveWriter.cpp

index d8f79ba69d698a548c30be63fc7e41b2e0995666..b729a992c3b6f85432bf5e369dda11fd0fec5bc9 100644 (file)
@@ -575,6 +575,35 @@ error_code unique_file(const Twine &model, int &result_fd,
 error_code unique_file(const Twine &Model, SmallVectorImpl<char> &ResultPath,
                        bool MakeAbsolute = true);
 
+/// @brief Create a uniquely named file.
+///
+/// Generates a unique path suitable for a temporary file and then opens it as a
+/// file. The name is based on \a model with '%' replaced by a random char in
+/// [0-9a-f]. If \a model is not an absolute path, a suitable temporary
+/// directory will be prepended.
+///
+/// Example: clang-%%-%%-%%-%%-%%.s => clang-a0-b1-c2-d3-e4.s
+///
+/// This is an atomic operation. Either the file is created and opened, or the
+/// file system is left untouched.
+///
+/// The intendend use is for files that are to be kept, possibly after
+/// renaming them. For example, when running 'clang -c foo.o', the file can
+/// be first created as foo-abc123.o and then renamed.
+///
+/// @param Model Name to base unique path off of.
+/// @param ResultFD Set to the opened file's file descriptor.
+/// @param ResultPath Set to the opened file's absolute path.
+/// @returns errc::success if Result{FD,Path} have been successfully set,
+///          otherwise a platform specific error_code.
+error_code createUniqueFile(const Twine &Model, int &ResultFD,
+                            SmallVectorImpl<char> &ResultPath,
+                            unsigned Mode = all_read | all_write);
+
+/// @brief Simpler version for clients that don't want an open file.
+error_code createUniqueFile(const Twine &Model,
+                            SmallVectorImpl<char> &ResultPath);
+
 /// @brief Create a file in the system temporary directory.
 ///
 /// The filename is of the form prefix-random_chars.suffix. Since the directory
index 1ee69b60234f6f69c4171ba35db497dd06473ee5..fbfda317e750ee8c5f7d23f56e02a7d8b87e514a 100644 (file)
@@ -65,8 +65,8 @@ error_code FileOutputBuffer::create(StringRef FilePath,
   // Create new file in same directory but with random name.
   SmallString<128> TempFilePath;
   int FD;
-  EC = sys::fs::unique_file(Twine(FilePath) + ".tmp%%%%%%%",
-                            FD, TempFilePath, false, 0644);
+  EC = sys::fs::createUniqueFile(Twine(FilePath) + ".tmp%%%%%%%",
+                                 FD, TempFilePath);
   if (EC)
     return EC;
 
index 2917e273bce7dbf8abcad06969af7610b0288498..21c4d4070d264bb89b789c1572ac3bd8dcc36b49 100644 (file)
@@ -78,10 +78,9 @@ LockFileManager::LockFileManager(StringRef FileName)
   UniqueLockFileName += "-%%%%%%%%";
   int UniqueLockFileID;
   if (error_code EC
-        = sys::fs::unique_file(UniqueLockFileName.str(),
-                                     UniqueLockFileID,
-                                     UniqueLockFileName,
-                                     /*makeAbsolute=*/false)) {
+        = sys::fs::createUniqueFile(UniqueLockFileName.str(),
+                                    UniqueLockFileID,
+                                    UniqueLockFileName)) {
     Error = EC;
     return;
   }
index 36fb9f3a4bf521fdbbd5a018da5de164573b46df..58c7c96c662fe5f5d910f18ed28ccec6dc29f699 100644 (file)
@@ -654,6 +654,17 @@ error_code unique_file(const Twine &Model, SmallVectorImpl<char> &ResultPath,
   return createUniqueEntity(Model, Dummy, ResultPath, MakeAbsolute, 0, FS_Name);
 }
 
+error_code createUniqueFile(const Twine &Model, int &ResultFd,
+                            SmallVectorImpl<char> &ResultPath, unsigned Mode) {
+  return createUniqueEntity(Model, ResultFd, ResultPath, false, Mode, FS_File);
+}
+
+error_code createUniqueFile(const Twine &Model,
+                            SmallVectorImpl<char> &ResultPath) {
+  int Dummy;
+  return createUniqueEntity(Model, Dummy, ResultPath, false, 0, FS_Name);
+}
+
 static error_code createTemporaryFile(const Twine &Model, int &ResultFD,
                                       llvm::SmallVectorImpl<char> &ResultPath,
                                       FSEntity Type) {
index 270dab23171dee7fef534bfbe08e1ba343155e7a..3d3dac3274d151bc5ea9e5bd45b07075fc77f53f 100644 (file)
@@ -267,7 +267,7 @@ void BugDriver::compileProgram(Module *M, std::string *Error) const {
   // Emit the program to a bitcode file...
   SmallString<128> BitcodeFile;
   int BitcodeFD;
-  error_code EC = sys::fs::unique_file(
+  error_code EC = sys::fs::createUniqueFile(
       OutputPrefix + "-test-program-%%%%%%%.bc", BitcodeFD, BitcodeFile);
   if (EC) {
     errs() << ToolName << ": Error making unique filename: " << EC.message()
@@ -306,7 +306,7 @@ std::string BugDriver::executeProgram(const Module *Program,
     // Emit the program to a bitcode file...
     SmallString<128> UniqueFilename;
     int UniqueFD;
-    error_code EC = sys::fs::unique_file(
+    error_code EC = sys::fs::createUniqueFile(
         OutputPrefix + "-test-program-%%%%%%%.bc", UniqueFD, UniqueFilename);
     if (EC) {
       errs() << ToolName << ": Error making unique filename: "
@@ -332,7 +332,7 @@ std::string BugDriver::executeProgram(const Module *Program,
 
   // Check to see if this is a valid output filename...
   SmallString<128> UniqueFile;
-  error_code EC = sys::fs::unique_file(OutputFile, UniqueFile);
+  error_code EC = sys::fs::createUniqueFile(OutputFile, UniqueFile);
   if (EC) {
     errs() << ToolName << ": Error making unique filename: "
            << EC.message() << "\n";
index d50f49b2db27b7df6a25466fcfba1edb7d70bba3..2098928b5c45eeb38a576da42e7336436a911567 100644 (file)
@@ -365,8 +365,8 @@ Module *BugDriver::ExtractMappedBlocksFromModule(const
                                                  Module *M) {
   SmallString<128> Filename;
   int FD;
-  error_code EC = sys::fs::unique_file(OutputPrefix + "-extractblocks%%%%%%%",
-                                       FD, Filename);
+  error_code EC = sys::fs::createUniqueFile(
+      OutputPrefix + "-extractblocks%%%%%%%", FD, Filename);
   if (EC) {
     outs() << "*** Basic Block extraction failed!\n";
     errs() << "Error creating temporary file: " << EC.message() << "\n";
index 43f2d3318ae7c331d971f13120843029e343861d..36d536ab89cf57f5d5519d2c368c946c875a36b6 100644 (file)
@@ -124,8 +124,8 @@ bool BugDriver::runPasses(Module *Program,
   // setup the output file name
   outs().flush();
   SmallString<128> UniqueFilename;
-  error_code EC =
-      sys::fs::unique_file(OutputPrefix + "-output-%%%%%%%.bc", UniqueFilename);
+  error_code EC = sys::fs::createUniqueFile(
+      OutputPrefix + "-output-%%%%%%%.bc", UniqueFilename);
   if (EC) {
     errs() << getToolName() << ": Error making unique filename: "
            << EC.message() << "\n";
@@ -136,8 +136,8 @@ bool BugDriver::runPasses(Module *Program,
   // set up the input file name
   SmallString<128> InputFilename;
   int InputFD;
-  EC = sys::fs::unique_file(OutputPrefix + "-input-%%%%%%%.bc", InputFD,
-                            InputFilename);
+  EC = sys::fs::createUniqueFile(OutputPrefix + "-input-%%%%%%%.bc", InputFD,
+                                 InputFilename);
   if (EC) {
     errs() << getToolName() << ": Error making unique filename: "
            << EC.message() << "\n";
index bec00364d7cfd18c4609e813843390dbc37177d3..107d0dbaeb17fb198021851c5626687df8f812ef 100644 (file)
@@ -478,7 +478,7 @@ GCC::FileType LLC::OutputCode(const std::string &Bitcode,
 
   SmallString<128> UniqueFile;
   error_code EC =
-      sys::fs::unique_file(Bitcode + "-%%%%%%%" + Suffix, UniqueFile);
+      sys::fs::createUniqueFile(Bitcode + "-%%%%%%%" + Suffix, UniqueFile);
   if (EC) {
     errs() << "Error making unique filename: " << EC.message() << "\n";
     exit(1);
@@ -715,7 +715,7 @@ int GCC::ExecuteProgram(const std::string &ProgramFile,
 
   SmallString<128> OutputBinary;
   error_code EC =
-      sys::fs::unique_file(ProgramFile+ "-%%%%%%%.gcc.exe", OutputBinary);
+      sys::fs::createUniqueFile(ProgramFile + "-%%%%%%%.gcc.exe", OutputBinary);
   if (EC) {
     errs() << "Error making unique filename: " << EC.message() << "\n";
     exit(1);
@@ -824,8 +824,8 @@ int GCC::MakeSharedObject(const std::string &InputFile, FileType fileType,
                           const std::vector<std::string> &ArgsForGCC,
                           std::string &Error) {
   SmallString<128> UniqueFilename;
-  error_code EC = sys::fs::unique_file(InputFile + "-%%%%%%%" + LTDL_SHLIB_EXT,
-                                       UniqueFilename);
+  error_code EC = sys::fs::createUniqueFile(
+      InputFile + "-%%%%%%%" + LTDL_SHLIB_EXT, UniqueFilename);
   if (EC) {
     errs() << "Error making unique filename: " << EC.message() << "\n";
     exit(1);
index 048748a3c9ca2bd8dbc75e2781bd5582e6bf04b4..52ce045c16c2acd55ff7de2fc3faab36f6038bfc 100644 (file)
@@ -260,8 +260,8 @@ bool Archive::writeToDisk(bool TruncateNames, std::string *ErrMsg) {
   // Create a temporary file to store the archive in
   int TmpArchiveFD;
   SmallString<128> TmpArchive;
-  error_code EC = sys::fs::unique_file("temp-archive-%%%%%%%.a", TmpArchiveFD,
-                                       TmpArchive, true, sys::fs::all_read | sys::fs::all_write);
+  error_code EC = sys::fs::createUniqueFile("temp-archive-%%%%%%%.a",
+                                            TmpArchiveFD, TmpArchive);
   if (EC)
     return true;