Apply resolution for LWG DR 3096
authorJonathan Wakely <jwakely@redhat.com>
Wed, 28 Nov 2018 15:36:56 +0000 (15:36 +0000)
committerJonathan Wakely <redi@gcc.gnu.org>
Wed, 28 Nov 2018 15:36:56 +0000 (15:36 +0000)
Add fix for "path::lexically_relative is confused by trailing slashes".

* doc/xml/manual/intro.xml: Document LWG 3096 change.
* src/filesystem/std-path.cc (path::lexically_relative(const path&)):
Treat a final empty element equivalently to a final dot element.
* testsuite/27_io/filesystem/path/generation/relative.cc: Add checks
for the examples in the DR.

From-SVN: r266566

libstdc++-v3/ChangeLog
libstdc++-v3/doc/xml/manual/intro.xml
libstdc++-v3/src/filesystem/std-path.cc
libstdc++-v3/testsuite/27_io/filesystem/path/generation/relative.cc

index fe0d1652c2ccc5f1d2fcead0da00dac2c0362516..9ef71f13897b7dd51c2aa0390cf0a8a711367734 100644 (file)
@@ -1,5 +1,11 @@
 2018-11-28  Jonathan Wakely  <jwakely@redhat.com>
 
+       * doc/xml/manual/intro.xml: Document LWG 3096 change.
+       * src/filesystem/std-path.cc (path::lexically_relative(const path&)):
+       Treat a final empty element equivalently to a final dot element.
+       * testsuite/27_io/filesystem/path/generation/relative.cc: Add checks
+       for the examples in the DR.
+
        PR libstdc++/83306
        * include/bits/fs_path.h (filesystem_error): Move data members into
        pimpl class owned by shared_ptr. Remove inline definitions of member
index cb187e1a2ed7733305069872aac70c2c383a5b7b..7159b592c9f9da3f6901a02ba62e5716c146b6de 100644 (file)
@@ -1194,6 +1194,13 @@ requirements of the license of GCC.
     <listitem><para>Change constructors to constrained templates.
     </para></listitem></varlistentry>
 
+    <varlistentry xml:id="manual.bugs.dr3096"><term><link xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="&DR;#3096">3096</link>:
+       <emphasis><code>path::lexically_relative</code> is confused by trailing slashes
+       </emphasis>
+    </term>
+    <listitem><para>Implement the fix for trailing slashes.
+    </para></listitem></varlistentry>
+
   </variablelist>
 
  </section>
index fb8898d904033fe99b82329147159a96f0f1cdff..06d882cf4de9191e37b8f79bd4bed1d025f85818 100644 (file)
@@ -529,10 +529,12 @@ path::lexically_relative(const path& base) const
       const path& p = *b;
       if (is_dotdot(p))
        --n;
-      else if (!is_dot(p))
+      else if (!p.empty() && !is_dot(p))
        ++n;
     }
-    if (n >= 0)
+    if (n == 0 && (a == end() || a->empty()))
+      ret = ".";
+    else if (n >= 0)
     {
       const path dotdot("..");
       while (n--)
index 4bc475827b23ead465bcff4252d03923575f6d36..6652c196d076e92b4718893dc865a854390e2788 100644 (file)
@@ -45,6 +45,25 @@ test02()
   compare_paths( p.lexically_relative(p), "." );
   compare_paths( p.lexically_relative("a/../a/b/../b/c/../c/."), "../../b/c" );
   compare_paths( p.lexically_relative("../../../"), "" );
+
+  compare_paths( path("a/./.").lexically_relative("a"), "./." );
+}
+
+void
+test03()
+{
+  // LWG 3096
+  compare_paths( path("/dir").lexically_relative("/dir"), "." );
+  compare_paths( path("/dir").lexically_relative("/dir/"), "." );
+  compare_paths( path("/dir").lexically_relative("/dir/."), "." );
+
+  compare_paths( path("/dir/").lexically_relative("/dir"), "." );
+  compare_paths( path("/dir/").lexically_relative("/dir/"), "." );
+  compare_paths( path("/dir/").lexically_relative("/dir/."), "." );
+
+  compare_paths( path("/dir/.").lexically_relative("/dir"), "." );
+  compare_paths( path("/dir/.").lexically_relative("/dir/"), "." );
+  compare_paths( path("/dir/.").lexically_relative("/dir/."), "." );
 }
 
 int
@@ -52,4 +71,5 @@ main()
 {
   test01();
   test02();
+  test03();
 }