00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 #include "util/log.hpp"
00018
00019 #include <sstream>
00020 #include <vector>
00021
00022 namespace FileSystem {
00023
00024 std::string dirname(const std::string& filename)
00025 {
00026 std::string::size_type p = filename.find_last_of('/');
00027 if(p == std::string::npos)
00028 p = filename.find_last_of('\\');
00029 if(p == std::string::npos)
00030 return "./";
00031
00032 return filename.substr(0, p+1);
00033 }
00034
00035 std::string basename(const std::string& filename)
00036 {
00037 std::string::size_type p = filename.find_last_of('/');
00038 if(p == std::string::npos)
00039 p = filename.find_last_of('\\');
00040 if(p == std::string::npos)
00041 return filename;
00042
00043 return filename.substr(p+1, filename.size()-p-1);
00044 }
00045
00046 std::string strip_extension(const std::string& filename)
00047 {
00048 std::string::size_type p = filename.find_last_of('.');
00049 if(p == std::string::npos)
00050 return filename;
00051
00052 return filename.substr(0, p);
00053 }
00054
00055 std::string normalize(const std::string& filename)
00056 {
00057 std::vector<std::string> path_stack;
00058
00059 const char* p = filename.c_str();
00060
00061 while(true) {
00062 while(*p == '/' || *p == '\\') {
00063 p++;
00064 continue;
00065 }
00066
00067 const char* pstart = p;
00068 while(*p != '/' && *p != '\\' && *p != 0) {
00069 ++p;
00070 }
00071
00072 size_t len = p - pstart;
00073 if(len == 0)
00074 break;
00075
00076 std::string pathelem(pstart, p-pstart);
00077 if(pathelem == ".")
00078 continue;
00079
00080 if(pathelem == "..") {
00081 if(path_stack.empty()) {
00082
00083 log_warning << "Invalid '..' in path '" << filename << "'" << std::endl;
00084
00085 path_stack.push_back(pathelem);
00086 } else {
00087 path_stack.pop_back();
00088 }
00089 } else {
00090 path_stack.push_back(pathelem);
00091 }
00092 }
00093
00094
00095 std::ostringstream result;
00096 for(std::vector<std::string>::iterator i = path_stack.begin();
00097 i != path_stack.end(); ++i) {
00098 result << '/' << *i;
00099 }
00100 if(path_stack.empty())
00101 result << '/';
00102
00103 return result.str();
00104 }
00105
00106 }
00107
00108