#ifndef __SITECING_SITECING_UTIL_H #define __SITECING_SITECING_UTIL_H #include #include #include /** * @file * @brief utility classes and functions. */ namespace sitecing { using namespace std; /** * Base class for utility exceptions. */ class utility_error : public konforka::exception { public: utility_error(const string& fi,const string& fu,int l,const string& w) : konforka::exception(fi,fu,l,w) { } }; /** * Restricted sequence encountered. */ class utility_restricted_sequence : public utility_error { public: utility_restricted_sequence(const string& fi,const string& fu,int l,const string& w) : utility_error(fi,fu,l,w) { } }; /** * No prefix or suffix found to strip out. */ class utility_no_affix : public utility_error { public: utility_no_affix(const string& fi,const string& fu,int l,const string& w) : utility_error(fi,fu,l,w) { } }; /** * No prefix to strip found. */ class utility_no_prefix : public utility_no_affix { public: utility_no_prefix(const string& fi,const string& fu,int l,const string& w) : utility_no_affix(fi,fu,l,w) { } }; /** * No suffix to strip found. */ class utility_no_suffix : public utility_no_affix { public: utility_no_suffix(const string& fi,const string& fu,int l,const string& w) : utility_no_affix(fi,fu,l,w) { } }; /** * Went up beyond root. * @todo TODO: wish I could remember the details -- document me. */ class utility_beyond_root : public utility_error { public: utility_beyond_root(const string& fi,const string& fu,int l,const string& w) : utility_error(fi,fu,l,w) { } }; /** * The file lock object. Released at the object destruction. */ class file_lock { public: /** * The file descriptor. */ int fd; file_lock() : fd(-1) { } /** * @param f file name. */ file_lock(const string& f) : fd(-1) { lock(f); } ~file_lock() { unlock(); } /** * Do lock. * @param f file name. */ void lock(const string& f); /** * @todo TODO: wish I could remember the details -- document me. */ void lock(); /** * Release the lock obtained. */ void unlock(); }; /** * The pid file. Removed at object destruction. */ class pid_file { public: /** * The file name. */ string file_name; /** * Do we unlink the file after we're done? */ bool unlink_pid; pid_file() : unlink_pid(false) { } ~pid_file() { unlink(); } /** * @param f file name. * @param u whether we want to unlink the file. */ void set(const string& f,bool u=true); /** * Unlink the file if we wanted to in the first place. */ void unlink(); }; /** * The semaphore object. */ class semaphore { public: /** * The semaphore id. */ int semid; semaphore() : semid(-1) { } /** * @param sid semaphore id. */ semaphore(int sid) : semid(sid) { } ~semaphore() { deinit(); } /** * Init semaphore. */ void init(); /** * Undo the init. */ void deinit(); /** * Semaphore on. */ void on(); /** * Semaphore off. */ void off(); }; /** * The semaphor lock object, released at object destruction. */ class semaphore_lock { public: /** * Pointer to the semaphore we're operating on. */ semaphore* sem; /** * Whether it is locked. */ bool locked; semaphore_lock() : sem(NULL), locked(false) {} /** * @param s pointer to the semaphore. * @param l lock at creation? */ semaphore_lock(semaphore* s,bool l=true) : sem(s), locked(false) { if(l) lock(); } /** * @param s reference to the semaphore. * @param l lock at creation? */ semaphore_lock(semaphore& s,bool l=true) : sem(&s), locked(false) { if(l) lock(); } ~semaphore_lock() { unlock(); } /** * Lock it. */ void lock(); /** * Unlock it. */ void unlock(); }; /** * normalize_path options enumeration. * @see normalize_path() */ enum normalize_path_options { /** * Restrict the /../ sequence. */ restrict_dotdot = 1, /** * Strip out the leading slash. */ strip_leading_slash = 2, /** * Strip out the trailing slash. */ strip_trailing_slash = 4 }; /** * combine_path options enumeration. * @see combine_path() */ enum combine_path_options { /** * The origin is file. Otherwise it is directory. */ origin_is_file = 1, /** * Fail if we've gone up beyond root. */ fail_beyond_root = 2 }; /** * Normalize pathname by stripping duplicate slashes, etc. * @param path the path name. * @param opts options. * @return the normalized path. * @see normalize_path_options * @todo TODO: document exceptions. */ string normalize_path(const string& path,int opts=(restrict_dotdot|strip_trailing_slash)); /** * Strip prefix from the string. * @param str the string. * @param prefix prefix to strip. * @return the string without prefix. * @todo TODO: document exceptions. */ string strip_prefix(const string& str,const string& prefix); /** * Strip suffix from the string. * @param str the string. * @param suffix suffix to strip. * @return the string without suffix. * @todo TODO: document exceptions. */ string strip_suffix(const string& str,const string& suffix); /** * Get the directory part of the filename. * @param filename the full file name. * @return the directory part. */ string dir_name(const string& filename); /** * Combine path with the relative path. * @param origin the origin. * @param relative relative path to combine origin with. * @param opts options. * @return the pathc combined. * @see combine_path_options * @todo TODO: document exceptions. */ string combine_path(const string& origin,const string& relative,int opts=origin_is_file); /** * Create directory and parent directories if needed. * @param path the pathname. * @param mode the mode for newly created directories. */ void make_path(const string& path,mode_t mode); /** * Change to the directory and pop back at object's destruction (e.g. when * the object goes out of scope). */ class auto_chdir { public: /** * Saved working directory. */ string saved_pwd; /** * Whether we want to change back automatically. */ bool autopop; auto_chdir() : autopop(false) { } /** * @param td destination path. * @param ap automatically come back? */ auto_chdir(const string& td,bool ap=true) : autopop(false) { pushdir(td,ap); } ~auto_chdir() { if(autopop) popdir(); } /** * Change into directory. * @param td the directory. * @param ap automaticall pop back? */ void pushdir(const string& td,bool ap=true); /** * Change to the saved directory. */ void popdir(); }; } #endif /* __SITECING_SITECING_UTIL_H */