1 /* Copyright (C) 2010 Wildfire Games.
3 * Permission is hereby granted, free of charge, to any person obtaining
4 * a copy of this software and associated documentation files (the
5 * "Software"), to deal in the Software without restriction, including
6 * without limitation the rights to use, copy, modify, merge, publish,
7 * distribute, sublicense, and/or sell copies of the Software, and to
8 * permit persons to whom the Software is furnished to do so, subject to
9 * the following conditions:
11 * The above copyright notice and this permission notice shall be included
12 * in all copies or substantial portions of the Software.
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
17 * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
18 * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
19 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
20 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 * helper functions for path strings.
27 #include "precompiled.h"
33 static const StatusDefinition pathStatusDefinitions
[] = {
34 { ERR::PATH_CHARACTER_ILLEGAL
, L
"illegal path character" },
35 { ERR::PATH_CHARACTER_UNSAFE
, L
"unsafe path character" },
36 { ERR::PATH_NOT_FOUND
, L
"path not found" },
37 { ERR::PATH_MIXED_SEPARATORS
, L
"path contains both slash and backslash separators" }
39 STATUS_ADD_DEFINITIONS(pathStatusDefinitions
);
42 static bool path_is_dir_sep(wchar_t c
)
44 if(c
== '/' || c
== '\\')
49 // is s2 a subpath of s1, or vice versa?
50 // (equal counts as subpath)
51 bool path_is_subpath(const wchar_t* s1
, const wchar_t* s2
)
53 // make sure s1 is the shorter string
54 if(wcslen(s1
) > wcslen(s2
))
57 wchar_t c1
= 0, last_c1
, c2
;
61 c1
= *s1
++, c2
= *s2
++;
66 // s1 matched s2 up until:
67 if((c2
== '\0') || // its end (i.e. they're equal length) OR
68 path_is_dir_sep(c2
) || // start of next component OR
69 path_is_dir_sep(last_c1
)) // ", but both have a trailing slash
74 // mismatch => is not subpath
81 //-----------------------------------------------------------------------------
83 // return pointer to the name component within path (i.e. skips over all
84 // characters up to the last dir separator, if any).
85 const wchar_t* path_name_only(const wchar_t* path
)
87 const wchar_t* slash1
= wcsrchr(path
, '/');
88 const wchar_t* slash2
= wcsrchr(path
, '\\');
89 // neither present, it's a filename only
90 if(!slash1
&& !slash2
)
93 // return name, i.e. component after the last slash
94 const wchar_t* name
= std::max(slash1
, slash2
)+1;
99 /*static*/ Status
Path::Validate(String::value_type c
)
102 return ERR::PATH_CHARACTER_UNSAFE
;
106 return ERR::PATH_CHARACTER_UNSAFE
;
121 return ERR::PATH_CHARACTER_ILLEGAL
;