aboutsummaryrefslogtreecommitdiff
path: root/butl/filesystem.cxx
diff options
context:
space:
mode:
authorKaren Arutyunov <karen@codesynthesis.com>2016-06-22 23:00:36 +0300
committerKaren Arutyunov <karen@codesynthesis.com>2016-06-23 15:13:25 +0300
commite0b126d8c7f691856ec4d80bb57cb1ba5c71fd69 (patch)
tree20613b639d81a08dd1189ef4db37f41f3de54a68 /butl/filesystem.cxx
parent748eab79085d7c8a3b3da90316a90a892db884ae (diff)
Add mkslink(), mkhlink()
Diffstat (limited to 'butl/filesystem.cxx')
-rw-r--r--butl/filesystem.cxx61
1 files changed, 54 insertions, 7 deletions
diff --git a/butl/filesystem.cxx b/butl/filesystem.cxx
index a2d6434..c3d21cd 100644
--- a/butl/filesystem.cxx
+++ b/butl/filesystem.cxx
@@ -4,18 +4,23 @@
#include <butl/filesystem>
-#include <errno.h> // errno, E*
-#include <unistd.h> // stat, rmdir(), unlink()
-#include <sys/types.h> // stat
-#include <sys/stat.h> // stat(), lstat(), S_IS*, mkdir()
-
#ifndef _WIN32
# include <dirent.h> // struct dirent, *dir()
+# include <unistd.h> // symlink(), link()
#else
-# include <io.h> // _find*()
-# include <direct.h> // _mkdir()
+# include <butl/win32-utility>
+
+# include <io.h> // _find*()
+# include <direct.h> // _mkdir()
+
+# include <cassert>
#endif
+#include <errno.h> // errno, E*
+#include <unistd.h> // stat, rmdir(), unlink()
+#include <sys/types.h> // stat
+#include <sys/stat.h> // stat(), lstat(), S_IS*, mkdir()
+
#include <memory> // unique_ptr
#include <system_error>
@@ -152,6 +157,48 @@ namespace butl
return r;
}
+#ifndef _WIN32
+ void
+ mksymlink (const path& target, const path& link, bool)
+ {
+ if (symlink (target.string ().c_str (), link.string ().c_str ()) == -1)
+ throw system_error (errno, system_category ());
+ }
+
+ void
+ mkhardlink (const path& target, const path& link, bool)
+ {
+ if (::link (target.string ().c_str (), link.string ().c_str ()) == -1)
+ throw system_error (errno, system_category ());
+ }
+
+#else
+
+ void
+ mksymlink (const path&, const path&, bool)
+ {
+ throw system_error (ENOSYS, system_category (), "symlinks not supported");
+ }
+
+ void
+ mkhardlink (const path& target, const path& link, bool dir)
+ {
+ if (!dir)
+ {
+ if (!CreateHardLinkA (link.string ().c_str (),
+ target.string ().c_str (),
+ nullptr))
+ {
+ string e (win32::last_error_msg ());
+ throw system_error (EIO, system_category (), e);
+ }
+ }
+ else
+ throw system_error (
+ ENOSYS, system_category (), "directory hard links not supported");
+ }
+#endif
+
// Figuring out whether we have the nanoseconds in struct stat. Some
// platforms (e.g., FreeBSD), may provide some "compatibility" #define's,
// so use the second argument to not end up with the same signatures.