Filesystem abstraction prototype - Make paths relative

This commit is contained in:
Emmanuel BENOîT 2017-12-27 09:37:36 +01:00
parent 2e8d460f1f
commit 124b95db69
2 changed files with 40 additions and 2 deletions

View file

@ -290,9 +290,42 @@ bool T_FSPath::isAbove(
/*----------------------------------------------------------------------------*/
T_FSPath T_FSPath::makeRelative(
T_FSPath const& relTo ) const noexcept
{
assert( isValid( ) && relTo.isValid( ) );
assert( isCanonical( ) && relTo.isCanonical( ) );
if ( relTo.root_ != root_ ) {
return *this;
}
const auto nca{ components_.size( ) } ,
ncb{ relTo.components_.size( ) } ,
nc{ std::min( nca , ncb ) };
uint32_t nCommon{ 0u };
for ( auto i = 0u ; i < nc ; i ++ ) {
if ( M_CMPSTR_( components_[ i ] , relTo.components_[ i ] ) != 0 ) {
break;
}
nCommon ++;
}
T_FSPath np;
const T_String parent{ T_String::Pooled( ".." ) };
for ( auto i = nca ; i > nCommon ; i -- ) {
np.components_.add( parent );
}
for ( auto i = nCommon ; i < nca ; i ++ ) {
np.components_.add( components_[ i ] );
}
return np;
}
/*----------------------------------------------------------------------------*/
bool T_FSPath::isCanonical( ) const noexcept
{
if ( !valid_ ) {
if ( !( valid_ && root_ ) ) {
return false;
}
@ -308,7 +341,7 @@ bool T_FSPath::isCanonical( ) const noexcept
T_FSPath T_FSPath::canonical( ) const noexcept
{
auto const nc{ components_.size( ) };
if ( !( valid_ && nc ) ) {
if ( !( valid_ && nc && root_ ) ) {
return *this;
}

View file

@ -102,6 +102,11 @@ class T_FSPath
// Checks if the current path is a child of the specified path
bool isUnder( T_FSPath const& other ) const noexcept;
// Create a relative path based on the current path and a "parent" path.
// Both paths must be canonical and valid. If they have different roots,
// a copy of the current path will be returned.
T_FSPath makeRelative( T_FSPath const& relTo ) const noexcept;
//----------------------------------------------------------------------
// Checks whether the specified path is canonical