From bac02200267495741e85db90607186ce4e0593b3 Mon Sep 17 00:00:00 2001 From: Karen Arutyunov Date: Wed, 29 Jun 2016 21:17:43 +0300 Subject: Port to MSVC --- butl/filesystem | 11 +++++++++-- butl/filesystem.cxx | 40 ++++++++++++++++++++++++++++++++-------- butl/process.cxx | 9 +++++++++ tests/base64/driver.cxx | 7 +++++++ tests/timestamp/driver.cxx | 10 ++++++++++ 5 files changed, 67 insertions(+), 10 deletions(-) diff --git a/butl/filesystem b/butl/filesystem index 565f465..780779f 100644 --- a/butl/filesystem +++ b/butl/filesystem @@ -5,14 +5,21 @@ #ifndef BUTL_FILESYSTEM #define BUTL_FILESYSTEM -#include // mode_t - #ifndef _WIN32 # include // DIR #else # include // intptr_t #endif +// VC's sys/types.h header file doesn't define mode_t type. So let's define it +// ourselves according to the POSIX specification. +// +#ifndef _MSC_VER +# include // mode_t +#else + typedef int mode_t; +#endif + #include // ptrdiff_t #include // uint16_t #include // move() diff --git a/butl/filesystem.cxx b/butl/filesystem.cxx index c3d21cd..0ff0e28 100644 --- a/butl/filesystem.cxx +++ b/butl/filesystem.cxx @@ -5,34 +5,45 @@ #include #ifndef _WIN32 -# include // struct dirent, *dir() -# include // symlink(), link() +# include // struct dirent, *dir() +# include // symlink(), link(), stat(), rmdir(), unlink() +# include // stat +# include // stat(), lstat(), S_IS*, mkdir() #else # include -# include // _find*() -# include // _mkdir() +# include // _find*(), _unlink() +# include // _mkdir(), _rmdir() +# include // _stat +# include // _stat(), S_IF* # include #endif -#include // errno, E* -#include // stat, rmdir(), unlink() -#include // stat -#include // stat(), lstat(), S_IS*, mkdir() +#include // errno, E* #include // unique_ptr #include using namespace std; +#ifdef _MSC_VER // Unlikely to be fixed in newer versions. +# define S_ISREG(m) (((m) & S_IFMT) == S_IFREG) +# define S_ISDIR(m) (((m) & S_IFMT) == S_IFDIR) +#endif + namespace butl { bool dir_exists (const path& p) { +#ifndef _WIN32 struct stat s; if (stat (p.string ().c_str (), &s) != 0) +#else + struct _stat s; + if (_stat (p.string ().c_str (), &s) != 0) +#endif { if (errno == ENOENT || errno == ENOTDIR) return false; @@ -46,8 +57,13 @@ namespace butl bool file_exists (const path& p) { +#ifndef _WIN32 struct stat s; if (stat (p.string ().c_str (), &s) != 0) +#else + struct _stat s; + if (_stat (p.string ().c_str (), &s) != 0) +#endif { if (errno == ENOENT || errno == ENOTDIR) return false; @@ -102,7 +118,11 @@ namespace butl { rmdir_status r (rmdir_status::success); +#ifndef _WIN32 if (rmdir (p.string ().c_str ()) != 0) +#else + if (_rmdir (p.string ().c_str ()) != 0) +#endif { if (errno == ENOENT) r = rmdir_status::not_exist; @@ -146,7 +166,11 @@ namespace butl { rmfile_status r (rmfile_status::success); +#ifndef _WIN32 if (unlink (p.string ().c_str ()) != 0) +#else + if (_unlink (p.string ().c_str ()) != 0) +#endif { if (errno == ENOENT || errno == ENOTDIR) r = rmfile_status::not_exist; diff --git a/butl/process.cxx b/butl/process.cxx index aaab915..e67e12e 100644 --- a/butl/process.cxx +++ b/butl/process.cxx @@ -32,6 +32,15 @@ using namespace std; using namespace butl::win32; #endif +#ifdef _MSC_VER // Unlikely to be fixed in newer versions. +#define S_ISREG(m) (((m) & S_IFMT) == S_IFREG) +# define S_ISDIR(m) (((m) & S_IFMT) == S_IFDIR) + +# define STDIN_FILENO 0 +# define STDOUT_FILENO 1 +# define STDERR_FILENO 2 +#endif // _MSC_VER + namespace butl { class auto_fd diff --git a/tests/base64/driver.cxx b/tests/base64/driver.cxx index e43e04a..a65ddbb 100644 --- a/tests/base64/driver.cxx +++ b/tests/base64/driver.cxx @@ -23,6 +23,13 @@ encode (const string& i, const string& o) if (r) { is.seekg (0); + + // VC 19 seekg() doesn't clear eofbit. + // +#if defined(_MSC_VER) && _MSC_VER <= 1900 + is.clear (); +#endif + ostringstream os; base64_encode (os, is); r = os.str () == o && is.eof (); diff --git a/tests/timestamp/driver.cxx b/tests/timestamp/driver.cxx index f5f30b9..e732629 100644 --- a/tests/timestamp/driver.cxx +++ b/tests/timestamp/driver.cxx @@ -108,7 +108,17 @@ main () // Invalid input (%[] unrelated). // assert (fail ("Apr 08 19:31:10.123456789 ABC", "%b %d %H:%M:%S%[.N] %Y")); + +// This doesn't work in VC 19 because their implementation of std::get_time() +// has a bug. Due to this bug std::get_time() parses the input +// "Apr 19:31:10 2016" for the format "%b %d %H:%M:%S %Y" as if the input were +// "Apr 19 00:31:10 2016". +// +#if !defined(_MSC_VER) || _MSC_VER > 1900 assert (fail ("Apr 19:31:10 2016", "%b %d %H:%M:%S %Y")); + assert (fail (":31 2016", "%H:%M %Y")); +#endif + assert (fail ("Opr 08 19:31:10 2016", "%b %d %H:%M:%S %Y")); // Parse valid input with a valid format. -- cgit v1.1