Browse Source

cmSystemTools: Silence CreateLink and CreateSymlink errors

If provided, report errors to a std::string.
This allows "silent" fallback to another flow, like COPY_ON_ERROR.
Tushar Maheshwari 6 years ago
parent
commit
0f08ed8936
3 changed files with 31 additions and 21 deletions
  1. 13 15
      Source/cmFileCommand.cxx
  2. 14 4
      Source/cmSystemTools.cxx
  3. 4 2
      Source/cmSystemTools.h

+ 13 - 15
Source/cmFileCommand.cxx

@@ -3760,34 +3760,32 @@ bool cmFileCommand::HandleCreateLinkCommand(
 
   // Check if the command requires a symbolic link.
   if (symbolicArg.IsEnabled()) {
-    completed = cmSystemTools::CreateSymlink(fileName, newFileName);
+    completed = cmSystemTools::CreateSymlink(fileName, newFileName, &result);
   } else {
-    completed = cmSystemTools::CreateLink(fileName, newFileName);
+    completed = cmSystemTools::CreateLink(fileName, newFileName, &result);
   }
 
-  if (!completed) {
-    // The link method did not succeed. Get the error message.
-    result = "Link failed: " + cmSystemTools::GetLastSystemError();
-
-    // Check if copy-on-error is enabled in the arguments.
-    if (copyOnErrorArg.IsEnabled()) {
-      completed =
-        cmSystemTools::cmCopyFile(fileName.c_str(), newFileName.c_str());
-      if (!completed) {
-        result = "Copy failed: " + cmSystemTools::GetLastSystemError();
-      }
+  // Check if copy-on-error is enabled in the arguments.
+  if (!completed && copyOnErrorArg.IsEnabled()) {
+    completed =
+      cmSystemTools::cmCopyFile(fileName.c_str(), newFileName.c_str());
+    if (!completed) {
+      result = "Copy failed: " + cmSystemTools::GetLastSystemError();
     }
   }
 
   // Check if the operation was successful.
   if (completed) {
     result = "0";
+  } else if (resultVar.empty()) {
+    // The operation failed and the result is not reported in a variable.
+    this->SetError(result);
+    return false;
   }
 
   if (!resultVar.empty()) {
     this->Makefile->AddDefinition(resultVar, result.c_str());
-    return true;
   }
 
-  return completed;
+  return true;
 }

+ 14 - 4
Source/cmSystemTools.cxx

@@ -3114,7 +3114,8 @@ std::string cmSystemTools::EncodeURL(std::string const& in, bool escapeSlashes)
 }
 
 bool cmSystemTools::CreateSymlink(const std::string& origName,
-                                  const std::string& newName)
+                                  const std::string& newName,
+                                  std::string* errorMessage)
 {
   uv_fs_t req;
   int flags = 0;
@@ -3128,7 +3129,11 @@ bool cmSystemTools::CreateSymlink(const std::string& origName,
   if (err) {
     std::string e =
       "failed to create symbolic link '" + newName + "': " + uv_strerror(err);
-    cmSystemTools::Error(e.c_str());
+    if (errorMessage) {
+      *errorMessage = std::move(e);
+    } else {
+      cmSystemTools::Error(e.c_str());
+    }
     return false;
   }
 
@@ -3136,7 +3141,8 @@ bool cmSystemTools::CreateSymlink(const std::string& origName,
 }
 
 bool cmSystemTools::CreateLink(const std::string& origName,
-                               const std::string& newName)
+                               const std::string& newName,
+                               std::string* errorMessage)
 {
   uv_fs_t req;
   int err =
@@ -3144,7 +3150,11 @@ bool cmSystemTools::CreateLink(const std::string& origName,
   if (err) {
     std::string e =
       "failed to create link '" + newName + "': " + uv_strerror(err);
-    cmSystemTools::Error(e.c_str());
+    if (errorMessage) {
+      *errorMessage = std::move(e);
+    } else {
+      cmSystemTools::Error(e.c_str());
+    }
     return false;
   }
 

+ 4 - 2
Source/cmSystemTools.h

@@ -528,12 +528,14 @@ public:
   /** Create a symbolic link if the platform supports it.  Returns whether
       creation succeeded. */
   static bool CreateSymlink(const std::string& origName,
-                            const std::string& newName);
+                            const std::string& newName,
+                            std::string* errorMessage = nullptr);
 
   /** Create a hard link if the platform supports it.  Returns whether
       creation succeeded. */
   static bool CreateLink(const std::string& origName,
-                         const std::string& newName);
+                         const std::string& newName,
+                         std::string* errorMessage = nullptr);
 
 private:
   static bool s_ForceUnixPaths;