summary refs log tree commit diff stats
path: root/compiler/pathutils.nim
diff options
context:
space:
mode:
Diffstat (limited to 'compiler/pathutils.nim')
-rw-r--r--compiler/pathutils.nim35
1 files changed, 10 insertions, 25 deletions
diff --git a/compiler/pathutils.nim b/compiler/pathutils.nim
index 03fcfe07e..703467bc4 100644
--- a/compiler/pathutils.nim
+++ b/compiler/pathutils.nim
@@ -73,23 +73,6 @@ iterator dirs(x: string): (int, int) =
   var it: PathIter
   while hasNext(it, x): yield next(it, x)
 
-when false:
-  iterator dirs(x: string): (int, int) =
-    var i = 0
-    var first = true
-    while i < x.len:
-      let prev = i
-      if first and x[i] in {DirSep, AltSep}:
-        # absolute path:
-        inc i
-      else:
-        while i < x.len and x[i] notin {DirSep, AltSep}: inc i
-      if i > prev:
-        yield (prev, i-1)
-      first = false
-      # skip all separators:
-      while i < x.len and x[i] in {DirSep, AltSep}: inc i
-
 proc isDot(x: string; bounds: (int, int)): bool =
   bounds[1] == bounds[0] and x[bounds[0]] == '.'
 
@@ -99,24 +82,26 @@ proc isDotDot(x: string; bounds: (int, int)): bool =
 proc isSlash(x: string; bounds: (int, int)): bool =
   bounds[1] == bounds[0] and x[bounds[0]] in {DirSep, AltSep}
 
+const canonDirSep = when isMainModule: '/' else: DirSep
+
 proc canon(x: string; result: var string; state: var int) =
   # state: 0th bit set if isAbsolute path. Other bits count
   # the number of path components.
   for b in dirs(x):
     if (state shr 1 == 0) and isSlash(x, b):
-      result.add DirSep
+      result.add canonDirSep
       state = state or 1
     elif result.len > (state and 1) and isDotDot(x, b):
       var d = result.len
       # f/..
-      while d > (state and 1) and result[d-1] != DirSep:
+      while (d-1) > (state and 1) and result[d-1] notin {DirSep, AltSep}:
         dec d
       if d > 0: setLen(result, d-1)
     elif isDot(x, b):
       discard "discard the dot"
     elif b[1] >= b[0]:
-      if result.len > 0 and result[^1] != DirSep:
-        result.add DirSep
+      if result.len > 0 and result[^1] notin {DirSep, AltSep}:
+        result.add canonDirSep
       result.add substr(x, b[0], b[1])
     inc state, 2
 
@@ -133,7 +118,7 @@ when FileSystemCaseSensitive:
 else:
   template `!=?`(a, b: char): bool = a != b
 
-proc relativeTo(full, base: string; sep = DirSep): string =
+proc relativeTo(full, base: string; sep = canonDirSep): string =
   if full.len == 0: return ""
   var f, b: PathIter
   var ff = (0, -1)
@@ -207,7 +192,7 @@ when true:
     canon(f.string, result.string, state)
 
   proc relativeTo*(fullPath: AbsoluteFile, baseFilename: AbsoluteDir;
-                   sep = DirSep): RelativeFile =
+                   sep = canonDirSep): RelativeFile =
     RelativeFile(relativeTo(fullPath.string, baseFilename.string, sep))
 
   proc toAbsolute*(file: string; base: AbsoluteDir): AbsoluteFile =
@@ -222,7 +207,7 @@ when true:
 
   proc writeFile*(x: AbsoluteFile; content: string) {.borrow.}
 
-when isMainModule and defined(posix):
+when isMainModule:
   doAssert canon"/foo/../bar" == "/bar"
   doAssert canon"foo/../bar" == "bar"
 
@@ -257,4 +242,4 @@ when isMainModule and defined(posix):
 
 when isMainModule and defined(windows):
   let nasty = string(AbsoluteDir(r"C:\Users\rumpf\projects\nim\tests\nimble\nimbleDir\linkedPkgs\pkgB-#head\../../simplePkgs/pkgB-#head/") / RelativeFile"pkgA/module.nim")
-  doAssert nasty == r"C:\Users\rumpf\projects\nim\tests\nimble\nimbleDir\simplePkgs\pkgB-#head\pkgA\module.nim"
+  doAssert nasty.replace('/', '\\') == r"C:\Users\rumpf\projects\nim\tests\nimble\nimbleDir\simplePkgs\pkgB-#head\pkgA\module.nim"