/** @file
$Id$
$Date$
$Author$
@copy © Marc Wäckerlin
@license LGPL, see file COPYING
$Log$
Revision 1.5 2005/03/02 22:03:08 marc
some fixes for solaris
Revision 1.4 2005/02/28 07:17:24 marc
Dir is now usable and compilable, also added fixes for Solaris
Revision 1.3 2005/02/18 15:52:20 marc
correection in documentation
Revision 1.2 2005/01/28 07:49:32 marc
Save configuration using file.hpp
Revision 1.1 2005/01/07 00:31:38 marc
initial version
1 2 3 4 5 6 7 8
5678901234567890123456789012345678901234567890123456789012345678901234567890
*/
#ifndef __MRW_FILE_HPP__
#define __MRW_FILE_HPP__
#include
#include
#include
#include
#include
#include
#include // offsetof
#include // abort
namespace mrw {
/** @defgroup sysFile File and System Utilities
@brief By now, some utilies for file handling, i.e. a copy command.
Some file and system specific utilities are missing in C++ and
often there is even no good alternative in C libraries.
*/
//@{
//============================================================================
/** @brief File handling utilities.
Utilities for file access in C++.
*/
class File {
//................................................................ methods
public:
/** @brief Copy a file.
Copy a file to a new location.
First the source file is fully read into memory, then written
to the destination. If the source file cannot be fully read,
the destination is left untouched.
@throw mrw::invalid_argument if read or write fails
@param from the source file name
@param to the destination file name
@note If the destination file already exists, it will be overwritten.
*/
static void copy(const std::string& from,
const std::string& to) throw(std::exception) {
std::ofstream os(to.c_str());
os<(), sz); // hack to get the buffer
if (!is.good() && is.eof())
throw mrw::invalid_argument("Cannot read file: '"+filename+"'");
return contents;
};
/** @brief Save a string to a file.
A string is stored in a file, the whole file is overwritten by
the contents of the string. This is the counterpart of
read(const std::string&).
@throw mrw::invalid_argument if write fails
@param filename the name of the output file
@param contents the text to be written to the file
*/
static void save(const std::string& filename, const std::string& contents)
throw(std::exception) {
std::ofstream file(filename.c_str());
if (!(file<. and
..
(self anf top)
*/
Dir(const std::string& dir, bool ignoreDots=true) throw(std::exception):
_ignoreDots(ignoreDots), _dir(opendir(dir.c_str())) {
if (!_dir)
throw mrw::invalid_argument("Cannot read directory: '"+dir+'\'');
}
/// Directory is closed automatically in the destructor.
~Dir() throw() {
closedir(_dir);
}
/** @brief Advance to the next directory entry.
Advance to the next directory entry.
@code
mrw::Dir dir("/home");
while (dir) ...
@endcode
@return
- @c true if an entry has been found
- @c false if there are no more entries left
@warning If you call this method again after @c false was
returned, behaviour is unspecified, but a crash
is probable.
*/
operator bool() throw() {
static const std::string D("."), DD("..");
static dirent* fake;
if (readdir_r(_dir, &_entry.entry(), &fake) || !fake) return false;
if (_ignoreDots
&& (_entry.type()==Entry::UNKNOWN || _entry.type()==Entry::DIR)
&& (D==_entry() || DD==_entry()))
return operator bool();
return true;
}
/** @brief Get the actual directory entry.
Returns the actual directory entry.
@code
mrw::Dir dir("/home");
while (dir) {
mrw::Dir::Entry entry(dir());
...
}
@endcode
@return the actual directory entry
@warning You must first call operator bool(), otherwise the
behaviour is undefined, but a crash is probable.
*/
const Entry& operator()() {
return _entry;
}
//.............................................................. variables
private:
bool _ignoreDots;
DIR* _dir;
Entry _entry;
};
//@}
}
#endif