e438cff79d
[SVN r63448]
109 lines
3.1 KiB
C++
109 lines
3.1 KiB
C++
// (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
|