-rw-r--r-- | lib/util.cc | 1 |
1 files changed, 1 insertions, 0 deletions
diff --git a/lib/util.cc b/lib/util.cc index 74039c6..069590b 100644 --- a/lib/util.cc +++ b/lib/util.cc | |||
@@ -1,66 +1,67 @@ | |||
1 | #include <sys/types.h> | 1 | #include <sys/types.h> |
2 | #include <sys/stat.h> | 2 | #include <sys/stat.h> |
3 | #include <cassert> | ||
3 | #include <konforka/util.h> | 4 | #include <konforka/util.h> |
4 | 5 | ||
5 | namespace konforka { | 6 | namespace konforka { |
6 | 7 | ||
7 | /* | 8 | /* |
8 | * XXX: this code is borrowed from sitecing as is, although it should be optimized. | 9 | * XXX: this code is borrowed from sitecing as is, although it should be optimized. |
9 | */ | 10 | */ |
10 | 11 | ||
11 | string normalize_path(const string& p,int o) { | 12 | string normalize_path(const string& p,int o) { |
12 | const char *s = p.c_str(); | 13 | const char *s = p.c_str(); |
13 | if( s[0]=='.' && s[1]=='/' ) | 14 | if( s[0]=='.' && s[1]=='/' ) |
14 | s += 2; // skip leading './' | 15 | s += 2; // skip leading './' |
15 | if(o&strip_leading_slash) | 16 | if(o&strip_leading_slash) |
16 | for(;(*s)=='/';s++); | 17 | for(;(*s)=='/';s++); |
17 | string rv; | 18 | string rv; |
18 | string::size_type notslash = 0; | 19 | string::size_type notslash = 0; |
19 | for(;*s;s++) { | 20 | for(;*s;s++) { |
20 | if(s[0]=='/') { | 21 | if(s[0]=='/') { |
21 | if(s[1]=='/') | 22 | if(s[1]=='/') |
22 | continue; // skip duplicate slash | 23 | continue; // skip duplicate slash |
23 | if(s[1]=='.' && s[2]=='/') { | 24 | if(s[1]=='.' && s[2]=='/') { |
24 | // '/./' sequence encountered | 25 | // '/./' sequence encountered |
25 | s += 2; | 26 | s += 2; |
26 | continue; | 27 | continue; |
27 | } | 28 | } |
28 | } | 29 | } |
29 | if( | 30 | if( |
30 | (o&restrict_dotdot) && ( | 31 | (o&restrict_dotdot) && ( |
31 | ( rv.empty() && s[0]=='.' && s[1]=='.' && s[2]=='/' ) // '^../' | 32 | ( rv.empty() && s[0]=='.' && s[1]=='.' && s[2]=='/' ) // '^../' |
32 | || | 33 | || |
33 | ( s[0]=='/' && s[1]=='.' && s[2]=='.' && (s[3]=='/' || s[3]==0) ) // '/../' or '/..$' | 34 | ( s[0]=='/' && s[1]=='.' && s[2]=='.' && (s[3]=='/' || s[3]==0) ) // '/../' or '/..$' |
34 | ) | 35 | ) |
35 | ) | 36 | ) |
36 | throw restricted_sequence_error(CODEPOINT,"restricted updir (..) sequence encountered"); | 37 | throw restricted_sequence_error(CODEPOINT,"restricted updir (..) sequence encountered"); |
37 | rv += *s; | 38 | rv += *s; |
38 | if( (*s) !='/' ) | 39 | if( (*s) !='/' ) |
39 | notslash = rv.length(); | 40 | notslash = rv.length(); |
40 | } | 41 | } |
41 | if(!(o&strip_trailing_slash)) | 42 | if(!(o&strip_trailing_slash)) |
42 | notslash++; | 43 | notslash++; |
43 | if(notslash<rv.length()) | 44 | if(notslash<rv.length()) |
44 | rv.erase(notslash); // XXX: does this operation have enough sense to be performed? | 45 | rv.erase(notslash); // XXX: does this operation have enough sense to be performed? |
45 | return rv; | 46 | return rv; |
46 | } | 47 | } |
47 | 48 | ||
48 | string dir_name(const string& p) { | 49 | string dir_name(const string& p) { |
49 | string::size_type sl = p.find_last_of('/'); | 50 | string::size_type sl = p.find_last_of('/'); |
50 | if(sl==string::npos) | 51 | if(sl==string::npos) |
51 | return ""; // no slashes -- no dir. | 52 | return ""; // no slashes -- no dir. |
52 | string::size_type nosl = p.find_last_not_of('/',sl); | 53 | string::size_type nosl = p.find_last_not_of('/',sl); |
53 | if(nosl==string::npos) | 54 | if(nosl==string::npos) |
54 | return ""; // only slashes -- no dir. | 55 | return ""; // only slashes -- no dir. |
55 | return p.substr(0,nosl+1); | 56 | return p.substr(0,nosl+1); |
56 | } | 57 | } |
57 | 58 | ||
58 | string combine_path(const string& orig,const string& rel,int o) { | 59 | string combine_path(const string& orig,const string& rel,int o) { |
59 | string r = normalize_path(rel,0); | 60 | string r = normalize_path(rel,0); |
60 | if(r.empty()) { | 61 | if(r.empty()) { |
61 | // XXX: this behaviour is questionable. | 62 | // XXX: this behaviour is questionable. |
62 | return normalize_path( (o&origin_is_file)?dir_name(orig):orig, strip_leading_slash|restrict_dotdot|strip_trailing_slash); | 63 | return normalize_path( (o&origin_is_file)?dir_name(orig):orig, strip_leading_slash|restrict_dotdot|strip_trailing_slash); |
63 | } | 64 | } |
64 | string rv; | 65 | string rv; |
65 | if(r[0]=='/') { | 66 | if(r[0]=='/') { |
66 | r.erase(0,1); | 67 | r.erase(0,1); |