fixes strutils.unescape; refs #3634

This commit is contained in:
Andreas Rumpf 2016-01-17 21:29:25 +01:00
commit 2c2ab6884c
3 changed files with 28 additions and 7 deletions

View file

@ -25,7 +25,7 @@ const
proc toLower(c: char): char {.inline.} = proc toLower(c: char): char {.inline.} =
result = if c in {'A'..'Z'}: chr(ord(c)-ord('A')+ord('a')) else: c result = if c in {'A'..'Z'}: chr(ord(c)-ord('A')+ord('a')) else: c
proc parseHex*(s: string, number: var int, start = 0): int {. proc parseHex*(s: string, number: var int, start = 0; maxLen = 0): int {.
rtl, extern: "npuParseHex", noSideEffect.} = rtl, extern: "npuParseHex", noSideEffect.} =
## Parses a hexadecimal number and stores its value in ``number``. ## Parses a hexadecimal number and stores its value in ``number``.
## ##
@ -45,11 +45,14 @@ proc parseHex*(s: string, number: var int, start = 0): int {.
## discard parseHex("0x38", value) ## discard parseHex("0x38", value)
## assert value == -200 ## assert value == -200
## ##
## If 'maxLen==0' the length of the hexadecimal number has no
## upper bound. Not more than ```maxLen`` characters are parsed.
var i = start var i = start
var foundDigit = false var foundDigit = false
if s[i] == '0' and (s[i+1] == 'x' or s[i+1] == 'X'): inc(i, 2) if s[i] == '0' and (s[i+1] == 'x' or s[i+1] == 'X'): inc(i, 2)
elif s[i] == '#': inc(i) elif s[i] == '#': inc(i)
while true: let last = if maxLen == 0: s.len else: i+maxLen
while i < last:
case s[i] case s[i]
of '_': discard of '_': discard
of '0'..'9': of '0'..'9':

View file

@ -1210,22 +1210,21 @@ proc unescape*(s: string, prefix = "\"", suffix = "\""): string {.noSideEffect,
## If `s` does not begin with ``prefix`` and end with ``suffix`` a ## If `s` does not begin with ``prefix`` and end with ``suffix`` a
## ValueError exception will be raised. ## ValueError exception will be raised.
result = newStringOfCap(s.len) result = newStringOfCap(s.len)
var i = 0 var i = prefix.len
if not s.startsWith(prefix): if not s.startsWith(prefix):
raise newException(ValueError, raise newException(ValueError,
"String does not start with a prefix of: " & prefix) "String does not start with a prefix of: " & prefix)
inc(i)
while true: while true:
if i == s.len-suffix.len: break if i == s.len-suffix.len: break
case s[i] case s[i]
of '\\': of '\\':
case s[i+1]: case s[i+1]:
of 'x': of 'x':
inc i inc i, 2
var c: int var c: int
i += parseutils.parseHex(s, c, i) i += parseutils.parseHex(s, c, i, maxLen=2)
result.add(chr(c)) result.add(chr(c))
inc(i, 2) dec i, 2
of '\\': of '\\':
result.add('\\') result.add('\\')
of '\'': of '\'':
@ -1721,3 +1720,4 @@ when isMainModule:
doAssert isUpper("ABC") doAssert isUpper("ABC")
doAssert(not isUpper("AAcc")) doAssert(not isUpper("AAcc"))
doAssert(not isUpper("A#$")) doAssert(not isUpper("A#$"))
doAssert(unescape(r"\x013", "", "") == "\x013")

View file

@ -0,0 +1,18 @@
discard """
output: '''3'''
"""
proc main* =
##[Mutltie akdlsf comment with #[nesting].
Yay, that is so cool.
]##
echo "foo bar"
var foo #[ Test the new inline comments ]#: int = 3
##[ A
novel documentation comment
#[Nesting works to some extend]
##[ Nested doc comment! ]##
]#
]##
echo $foo