/** @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