3 #include <msp/core/except.h>
7 #include <msp/strings/glob.h>
9 #include <msp/strings/utils.h>
20 string basename(const Path &p)
25 Path dirname(const Path &p)
33 return p.subpath(0, p.size()-1);
36 string basepart(const string &fn)
38 unsigned dot = fn.rfind('.');
39 return fn.substr(0, dot);
42 string extpart(const string &fn)
44 string::size_type dot = fn.rfind('.');
47 return fn.substr(dot);
50 Path fix_case(const Path &path)
54 for(Path::Iterator i=path.begin(); i!=path.end(); ++i)
62 files = list_files(result);
64 files = list_files(".");
67 for(list<string>::iterator j=files.begin(); (j!=files.end() && !found); ++j)
68 if(!strcasecmp(*j,*i))
82 Path readlink(const Path &link)
86 throw Exception("No symbolic links on win32");
89 int len = ::readlink(link.str().c_str(), buf, sizeof(buf));
91 throw SystemError("readlink failed", errno);
92 return string(buf, len);
96 Path realpath(const Path &path)
99 if(path.is_absolute())
102 return getcwd()/path;
104 list<string> queue(path.begin(), path.end());
105 if(!path.is_absolute())
108 queue.insert(queue.begin(), cwd.begin(), cwd.end());
112 unsigned n_links = 0;
113 while(!queue.empty())
115 Path next = real/queue.front();
118 struct stat st = lstat(next);
119 if(S_ISLNK(st.st_mode))
122 throw Exception("Ludicrous amount of symlinks detected in realpath, giving up");
123 Path link = readlink(next);
124 queue.insert(queue.begin(), link.begin(), link.end());
134 void rename(const Path &from, const Path &to)
136 if(::rename(from.str().c_str(), to.str().c_str())==-1)
137 throw SystemError("rename failed", errno);
140 void unlink(const Path &path)
142 if(::unlink(path.str().c_str())==-1)
143 throw SystemError("unlink failed", errno);
146 Path relative(const Path &path, const Path &base)
148 Path::Iterator i = path.begin();
149 Path::Iterator j = base.begin();
150 for(; (i!=path.end() && j!=base.end() && *i==*j); ++i, ++j) ;
153 for(; j!=base.end(); ++j)
155 for(; i!=path.end(); ++i)
161 int descendant_depth(const Path &path, const Path &parent)
163 Path::Iterator i = path.begin();
164 Path::Iterator j = parent.begin();
165 for(; (i!=path.end() && j!=parent.end() && *i==*j); ++i, ++j) ;
171 for(; i!=path.end(); ++i)