Skip to content

path::lexically_normal() behaves slightly differently from the standard #33

Closed
@rikyoz

Description

@rikyoz

Hi!
First of all, thank you for this library!

Describe the bug
I'm trying to use this library as a fallback when the compiler does not support the final standard version of <filesystem> library.
However, I've found that in some cases the result returned by path::lexically_normal() of ghc is different from the one returned by the C++17 standard version.
In particular, the normal version of path("../") should be "..", while ghc retains the trailing '/' (eventually converted to '\\' on Windows).
On Windows, the same applies also to path("..\\"), which should be normalized to ".." and instead still retains the trailing '\\'.

To Reproduce
To reproduce the behavior, I've created a small program to compare the different results between ghc::filesystem and std::filesystem:

#include <iostream>
#include <filesystem>
#include "ghc/filesystem.hpp"

using std::cout;
using std::endl;

int main() {
    cout << "[std] path(\"../\").lexically_normal() == ";
    cout << std::filesystem::path("../").lexically_normal() << endl;
    
    cout << "[ghc] path(\"../\").lexically_normal() == ";
    cout << ghc::filesystem::path("../").lexically_normal() << endl;

#ifdef _WIN32
    cout << "[std] path(\"..\\\\\").lexically_normal() == ";
    cout << std::filesystem::path("..\\").lexically_normal() << endl;
    
    cout << "[ghc] path(\"..\\\\\").lexically_normal() == ";
    cout << ghc::filesystem::path("..\\").lexically_normal() << endl;
#endif
    return 0;
}

I've tested the program using various compilers and operating systems.

  • On Windows 10 using

    • MSVC 2017
    • MinGW-w64 9.2.0
    • clang 9.0

    the program output is:

    [std] path("../").lexically_normal() == ".."
    [ghc] path("../").lexically_normal() == "..\\"
    [std] path("..\\").lexically_normal() == ".."
    [ghc] path("..\\").lexically_normal() == "..\\"
  • On Ubuntu 18.04 LTS using

    • g++ 8.3.0
    • clang 6.0

    the program output is:

    [std] path("../").lexically_normal() == ".."
    [ghc] path("../").lexically_normal() == "../"

Expected behavior
In all these cases path::lexically_normal() of ghc should return a path("..") in order to conform to the standard.

External References

  • std::filesystem::path from cppreference.com

    A path can be normalized by following this algorithm:
    ...
    7. If the last filename is dot-dot, remove any trailing directory-separator.

  • Relative Paths from Open Standards

    A path in normal form has no redundant current directory (dot) elements, no redundant parent directory (dot-dot) elements, and no redundant directory-separators.

Metadata

Metadata

Assignees

Labels

available on masterFix is done on master branch, issue closed on next releasebugSomething isn't working

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions