summaryrefslogtreecommitdiffstats
path: root/src/boost/libs/iostreams/test/detail/file_handle.hpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/boost/libs/iostreams/test/detail/file_handle.hpp')
-rw-r--r--src/boost/libs/iostreams/test/detail/file_handle.hpp108
1 files changed, 108 insertions, 0 deletions
diff --git a/src/boost/libs/iostreams/test/detail/file_handle.hpp b/src/boost/libs/iostreams/test/detail/file_handle.hpp
new file mode 100644
index 00000000..a9bfed52
--- /dev/null
+++ b/src/boost/libs/iostreams/test/detail/file_handle.hpp
@@ -0,0 +1,108 @@
+// (C) Copyright 2010 Daniel James
+// (C) Copyright 2008 CodeRage, LLC (turkanis at coderage dot com)
+// (C) Copyright 2003-2007 Jonathan Turkanis
+// Distributed under the Boost Software License, Version 1.0. (See accompanying
+// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt.)
+
+// A few methods for getting and manipulating file handles.
+
+#ifndef BOOST_IOSTREAMS_FILE_HANDLE_HPP_INCLUDED
+#define BOOST_IOSTREAMS_FILE_HANDLE_HPP_INCLUDED
+
+#include <boost/iostreams/detail/file_handle.hpp>
+#include <boost/iostreams/detail/config/rtl.hpp>
+#include <boost/test/test_tools.hpp>
+#include <string>
+
+#ifdef BOOST_IOSTREAMS_WINDOWS
+# include <io.h> // low-level file i/o.
+# define WINDOWS_LEAN_AND_MEAN
+# include <windows.h>
+#else
+# include <sys/stat.h>
+# include <fcntl.h>
+#endif
+
+namespace boost { namespace iostreams { namespace test {
+
+#ifdef BOOST_IOSTREAMS_WINDOWS
+
+// Windows implementation
+
+boost::iostreams::detail::file_handle open_file_handle(std::string const& name)
+{
+ HANDLE handle =
+ ::CreateFileA( name.c_str(),
+ GENERIC_READ | GENERIC_WRITE,
+ FILE_SHARE_READ | FILE_SHARE_WRITE,
+ NULL, // lpSecurityAttributes
+ OPEN_EXISTING,
+ FILE_ATTRIBUTE_NORMAL,
+ NULL ); // hTemplateFile
+
+ BOOST_REQUIRE (handle != INVALID_HANDLE_VALUE);
+ return handle;
+}
+
+void close_file_handle(boost::iostreams::detail::file_handle handle)
+{
+ BOOST_REQUIRE(::CloseHandle(handle) == 1);
+}
+
+#define BOOST_CHECK_HANDLE_CLOSED(handle)
+#define BOOST_CHECK_HANDLE_OPEN(handle)
+
+#else // BOOST_IOSTREAMS_WINDOWS
+
+// Non-windows implementation
+
+boost::iostreams::detail::file_handle open_file_handle(std::string const& name)
+{
+ int oflag = O_RDWR;
+
+ #ifdef _LARGEFILE64_SOURCE
+ oflag |= O_LARGEFILE;
+ #endif
+
+ // Calculate pmode argument to open.
+
+ mode_t pmode = S_IRUSR | S_IWUSR |
+ S_IRGRP | S_IWGRP |
+ S_IROTH | S_IWOTH;
+
+ // Open file.
+
+ int fd = BOOST_IOSTREAMS_FD_OPEN(name.c_str(), oflag, pmode);
+ BOOST_REQUIRE (fd != -1);
+
+ return fd;
+}
+
+void close_file_handle(boost::iostreams::detail::file_handle handle)
+{
+ BOOST_REQUIRE(BOOST_IOSTREAMS_FD_CLOSE(handle) != -1);
+}
+
+// This is pretty dubious. First you must make sure that no other
+// operations that could open a descriptor are called before this
+// check, otherwise it's quite likely that a closed descriptor
+// could be used. Secondly, I'm not sure if it's guaranteed that
+// fcntl will know that the descriptor is closed but this seems
+// to work okay, and I can't see any other convenient way to check
+// that a descripter has been closed.
+bool is_handle_open(boost::iostreams::detail::file_handle handle)
+{
+ return ::fcntl(handle, F_GETFD) != -1;
+}
+
+#define BOOST_CHECK_HANDLE_CLOSED(handle) \
+ BOOST_CHECK(!::boost::iostreams::test::is_handle_open(handle))
+#define BOOST_CHECK_HANDLE_OPEN(handle) \
+ BOOST_CHECK(::boost::iostreams::test::is_handle_open(handle))
+
+
+#endif // BOOST_IOSTREAMS_WINDOWS
+
+}}}
+
+#endif // BOOST_IOSTREAMS_FILE_HANDLE_HPP_INCLUDED