Add path_strip_last_volume

This gets the volume that the path eventually refers to by parsing
the last volume specifier and returning the part of the path after
it (which does not contain any volume specifiers). The initial part
of the path therefore contains everything up to and including the
last volume specifier.

Change-Id: I9a935543256f8f22e0b8b1e3c88d4e47bd9dae8a
This commit is contained in:
Aidan MacDonald 2022-03-31 20:38:24 +01:00
parent ca0c3dee0a
commit 4f05a9d066
2 changed files with 38 additions and 2 deletions

View file

@ -109,8 +109,8 @@ static const unsigned char storage_dec_indexes[STORAGE_NUM_TYPES+1] =
/* Returns on which volume this is and sets *nameptr to the portion of the
* path after the volume specifier, which could be the null if the path is
* just a volume root. If *nameptr > name, then a volume specifier was
* found. If 'greedy' is 'true', then it all separators after the volume
* specifier are consumed, if one was found.
* found. If 'greedy' is 'true', then all separators after the volume
* specifier are consumed.
*/
int path_strip_volume(const char *name, const char **nameptr, bool greedy)
{
@ -167,6 +167,41 @@ psv_out:
return volume;
}
/* Strip the last volume component in the path and return the remainder of
* the path in *nameptr. If 'greedy' is 'true', then all separators after
* the volume specifier are consumed.
*/
int path_strip_last_volume(const char *name, const char **nameptr, bool greedy)
{
const char *p = name + strlen(name);
while (p > name)
{
/* skip the component */
while (p > name && p[-1] != PATH_SEPCH)
--p;
/* bail if we reached the beginning */
if (p <= name+1)
break;
/* point at the seprator */
--p;
/* try to strip the volume and return it if found */
int volume = path_strip_volume(p, nameptr, greedy);
if (volume != ROOT_VOLUME)
return volume;
/* skip any extra separators */
while (p > name && p[-1] == PATH_SEPCH)
--p;
}
/* return whatever is at the beginning of the path */
return path_strip_volume(name, nameptr, greedy);
}
/* Returns the volume specifier decorated with the storage type name.
* Assumes the supplied buffer size is at least {VOL_MAX_LEN}+1.
*/

View file

@ -79,6 +79,7 @@ static inline bool name_is_dot_dot(const char *name)
#ifdef HAVE_MULTIVOLUME
int path_strip_volume(const char *name, const char **nameptr, bool greedy);
int path_strip_last_volume(const char *name, const char **nameptr, bool greedy);
int get_volume_name(int volume, char *name);
int make_volume_root(int volume, char *dst);
#endif