From 7e7699a856854c2e53b76dd4c41cd92661fb7463 Mon Sep 17 00:00:00 2001 From: wt Date: Mon, 5 Jun 2017 10:52:23 +0800 Subject: [PATCH 01/10] Fix bad tail for status response --- lib/pure/asynchttpserver.nim | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/pure/asynchttpserver.nim b/lib/pure/asynchttpserver.nim index 8d059dbbc6..0dd32afc74 100644 --- a/lib/pure/asynchttpserver.nim +++ b/lib/pure/asynchttpserver.nim @@ -127,7 +127,7 @@ proc parseProtocol(protocol: string): tuple[orig: string, major, minor: int] = i.inc protocol.parseInt(result.minor, i) proc sendStatus(client: AsyncSocket, status: string): Future[void] = - client.send("HTTP/1.1 " & status & "\c\L") + client.send("HTTP/1.1 " & status & "\c\L\c\L") proc processClient(client: AsyncSocket, address: string, callback: proc (request: Request): From 622b4a7b47c4a9b0bc7c670fddd37f628c5226af Mon Sep 17 00:00:00 2001 From: wt Date: Tue, 6 Jun 2017 08:52:19 +0800 Subject: [PATCH 02/10] Update asynchttpserver.nim --- lib/pure/asynchttpserver.nim | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/pure/asynchttpserver.nim b/lib/pure/asynchttpserver.nim index 0dd32afc74..a374e80e89 100644 --- a/lib/pure/asynchttpserver.nim +++ b/lib/pure/asynchttpserver.nim @@ -127,7 +127,7 @@ proc parseProtocol(protocol: string): tuple[orig: string, major, minor: int] = i.inc protocol.parseInt(result.minor, i) proc sendStatus(client: AsyncSocket, status: string): Future[void] = - client.send("HTTP/1.1 " & status & "\c\L\c\L") + client.send("HTTP/1.1 " & status & "\c\L\c\L") proc processClient(client: AsyncSocket, address: string, callback: proc (request: Request): From 27e2a343403197af08d20207ac884cf134d4892e Mon Sep 17 00:00:00 2001 From: Parashurama Date: Tue, 6 Jun 2017 13:47:34 +0200 Subject: [PATCH 03/10] fixes parseopt/parseopt2 custom cmdline args. --- lib/pure/parseopt.nim | 45 ++++++++++++++++++++----------- lib/pure/parseopt2.nim | 45 ++++++++++++++++++++----------- tests/misc/tparseopt.nim | 57 ++++++++++++++++++++++++++++++++++++++++ 3 files changed, 117 insertions(+), 30 deletions(-) create mode 100644 tests/misc/tparseopt.nim diff --git a/lib/pure/parseopt.nim b/lib/pure/parseopt.nim index 218f5ab814..23568edb91 100644 --- a/lib/pure/parseopt.nim +++ b/lib/pure/parseopt.nim @@ -149,26 +149,41 @@ proc cmdLineRest*(p: OptParser): TaintedString {.rtl, extern: "npo$1".} = ## retrieves the rest of the command line that has not been parsed yet. result = strip(substr(p.cmd, p.pos, len(p.cmd) - 1)).TaintedString +iterator getopt*(p: var OptParser): tuple[kind: CmdLineKind, key, val: TaintedString] = + ## This is an convenience iterator for iterating over the given OptParser object. + ## Example: + ## + ## .. code-block:: nim + ## var p = initOptParser("--left --debug:3 -l=4 -r:2") + ## for kind, key, val in p.getopt(): + ## case kind + ## of cmdArgument: + ## filename = key + ## of cmdLongOption, cmdShortOption: + ## case key + ## of "help", "h": writeHelp() + ## of "version", "v": writeVersion() + ## of cmdEnd: assert(false) # cannot happen + ## if filename == "": + ## # no filename has been given, so we show the help: + ## writeHelp() + p.pos = 0 + while true: + next(p) + if p.kind == cmdEnd: break + yield (p.kind, p.key, p.val) + when declared(initOptParser): iterator getopt*(): tuple[kind: CmdLineKind, key, val: TaintedString] = - ## This is an convenience iterator for iterating over the command line. - ## This uses the OptParser object. Example: + ## This is an convenience iterator for iterating over the command line arguments. + ## This create a new OptParser object. + ## See above for a more detailed example ## ## .. code-block:: nim - ## var - ## filename = "" ## for kind, key, val in getopt(): - ## case kind - ## of cmdArgument: - ## filename = key - ## of cmdLongOption, cmdShortOption: - ## case key - ## of "help", "h": writeHelp() - ## of "version", "v": writeVersion() - ## of cmdEnd: assert(false) # cannot happen - ## if filename == "": - ## # no filename has been given, so we show the help: - ## writeHelp() + ## # this will iterate over all arguments passed to the cmdline. + ## continue + ## var p = initOptParser() while true: next(p) diff --git a/lib/pure/parseopt2.nim b/lib/pure/parseopt2.nim index 7fd9c60fec..2e8dbe1402 100644 --- a/lib/pure/parseopt2.nim +++ b/lib/pure/parseopt2.nim @@ -123,26 +123,41 @@ type {.deprecated: [TGetoptResult: GetoptResult].} +iterator getopt*(p: var OptParser): GetoptResult = + ## This is an convenience iterator for iterating over the given OptParser object. + ## Example: + ## + ## .. code-block:: nim + ## var p = initOptParser("--left --debug:3 -l=4 -r:2") + ## for kind, key, val in p.getopt(): + ## case kind + ## of cmdArgument: + ## filename = key + ## of cmdLongOption, cmdShortOption: + ## case key + ## of "help", "h": writeHelp() + ## of "version", "v": writeVersion() + ## of cmdEnd: assert(false) # cannot happen + ## if filename == "": + ## # no filename has been given, so we show the help: + ## writeHelp() + p.pos = 0 + while true: + next(p) + if p.kind == cmdEnd: break + yield (p.kind, p.key, p.val) + when declared(paramCount): iterator getopt*(): GetoptResult = - ## This is an convenience iterator for iterating over the command line. - ## This uses the OptParser object. Example: + ## This is an convenience iterator for iterating over the command line arguments. + ## This create a new OptParser object. + ## See above for a more detailed example ## ## .. code-block:: nim - ## var - ## filename = "" ## for kind, key, val in getopt(): - ## case kind - ## of cmdArgument: - ## filename = key - ## of cmdLongOption, cmdShortOption: - ## case key - ## of "help", "h": writeHelp() - ## of "version", "v": writeVersion() - ## of cmdEnd: assert(false) # cannot happen - ## if filename == "": - ## # no filename has been given, so we show the help: - ## writeHelp() + ## # this will iterate over all arguments passed to the cmdline. + ## continue + ## var p = initOptParser() while true: next(p) diff --git a/tests/misc/tparseopt.nim b/tests/misc/tparseopt.nim new file mode 100644 index 0000000000..1f8375dfd1 --- /dev/null +++ b/tests/misc/tparseopt.nim @@ -0,0 +1,57 @@ +discard """ + file: "tparseopt.nim" + output: ''' +parseopt +first round +kind: cmdLongOption key:val -- left: +second round +kind: cmdLongOption key:val -- left: +kind: cmdLongOption key:val -- debug:3 +kind: cmdShortOption key:val -- l:4 +kind: cmdShortOption key:val -- r:2 +parseopt2 +first round +kind: cmdLongOption key:val -- left: +second round +kind: cmdLongOption key:val -- left: +kind: cmdLongOption key:val -- debug:3 +kind: cmdShortOption key:val -- l:4 +kind: cmdShortOption key:val -- r:2''' +""" +from parseopt import nil +from parseopt2 import nil + + +block: + echo "parseopt" + for kind, key, val in parseopt.getopt(): + echo "kind: ", kind, "\tkey:val -- ", key, ":", val + + # pass custom cmdline arguments + echo "first round" + var argv = "--left --debug:3 -l=4 -r:2" + var p = parseopt.initOptParser(argv) + for kind, key, val in parseopt.getopt(p): + echo "kind: ", kind, "\tkey:val -- ", key, ":", val + break + # reset getopt iterator and check arguments are returned correctly. + echo "second round" + for kind, key, val in parseopt.getopt(p): + echo "kind: ", kind, "\tkey:val -- ", key, ":", val + +block: + echo "parseopt2" + for kind, key, val in parseopt2.getopt(): + echo "kind: ", kind, "\tkey:val -- ", key, ":", val + + # pass custom cmdline arguments + echo "first round" + var argv: seq[string] = @["--left", "--debug:3", "-l=4", "-r:2"] + var p = parseopt2.initOptParser(argv) + for kind, key, val in parseopt2.getopt(p): + echo "kind: ", kind, "\tkey:val -- ", key, ":", val + break + # reset getopt iterator and check arguments are returned correctly. + echo "second round" + for kind, key, val in parseopt2.getopt(p): + echo "kind: ", kind, "\tkey:val -- ", key, ":", val From 963679389c6866672b939fcd0bd4c631be81fca7 Mon Sep 17 00:00:00 2001 From: "Markus F.X.J. Oberhumer" Date: Tue, 13 Jun 2017 10:12:23 +0200 Subject: [PATCH 04/10] cgen: #undef some more predefined symbols. (#5831) This is a followup to issue #5171. --- compiler/cgen.nim | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/compiler/cgen.nim b/compiler/cgen.nim index c67dd65814..3797a92c23 100644 --- a/compiler/cgen.nim +++ b/compiler/cgen.nim @@ -601,8 +601,18 @@ proc generateHeaders(m: BModule) = addf(m.s[cfsHeaders], "#include \"$1\"$N", [rope(it)]) else: addf(m.s[cfsHeaders], "#include $1$N", [rope(it)]) + add(m.s[cfsHeaders], "#undef LANGUAGE_C" & tnl) + add(m.s[cfsHeaders], "#undef MIPSEB" & tnl) + add(m.s[cfsHeaders], "#undef MIPSEL" & tnl) + add(m.s[cfsHeaders], "#undef PPC" & tnl) + add(m.s[cfsHeaders], "#undef R3000" & tnl) + add(m.s[cfsHeaders], "#undef R4000" & tnl) + add(m.s[cfsHeaders], "#undef i386" & tnl) add(m.s[cfsHeaders], "#undef linux" & tnl) + add(m.s[cfsHeaders], "#undef mips" & tnl) add(m.s[cfsHeaders], "#undef near" & tnl) + add(m.s[cfsHeaders], "#undef powerpc" & tnl) + add(m.s[cfsHeaders], "#undef unix" & tnl) proc initFrame(p: BProc, procname, filename: Rope): Rope = discard cgsym(p.module, "nimFrame") From 91a3cb67ec53f28c919316bf611bea07e8677d02 Mon Sep 17 00:00:00 2001 From: Andreas Rumpf Date: Tue, 13 Jun 2017 13:51:33 +0200 Subject: [PATCH 05/10] fixes #5824 --- compiler/ccgtypes.nim | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/compiler/ccgtypes.nim b/compiler/ccgtypes.nim index 02eb5ba829..0c81ca8143 100644 --- a/compiler/ccgtypes.nim +++ b/compiler/ccgtypes.nim @@ -470,7 +470,12 @@ proc genRecordFieldsAux(m: BModule, n: PNode, let a = genRecordFieldsAux(m, k, "$1.$2" % [ae, sname], rectype, check) if a != nil: - add(unionBody, "struct {") + if tfPacked notin rectype.flags: + add(unionBody, "struct {") + else: + addf(unionBody, CC[cCompiler].structStmtFmt, + [rope"struct", nil, rope(CC[cCompiler].packedPragma)]) + add(unionBody, "{") add(unionBody, a) addf(unionBody, "} $1;$n", [sname]) else: From 1ddf10b23bc79c0140b477fda4554607f5936016 Mon Sep 17 00:00:00 2001 From: impbox Date: Tue, 13 Jun 2017 23:21:38 +1000 Subject: [PATCH 06/10] Create system.nim Fix `deepCopy` incorrect argument description. --- lib/system.nim | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/lib/system.nim b/lib/system.nim index 49f24c9730..0e94bcc231 100644 --- a/lib/system.nim +++ b/lib/system.nim @@ -3774,7 +3774,8 @@ proc locals*(): RootObj {.magic: "Plugin", noSideEffect.} = when hasAlloc and not defined(nimscript) and not defined(JS): proc deepCopy*[T](x: var T, y: T) {.noSideEffect, magic: "DeepCopy".} = - ## performs a deep copy of `x`. This is also used by the code generator + ## performs a deep copy of `y` and copies it into `x`. + ## This is also used by the code generator ## for the implementation of ``spawn``. discard From 64cbcec54d7bf94ff9718416722e06f4462e8a5c Mon Sep 17 00:00:00 2001 From: daneb Date: Tue, 13 Jun 2017 21:08:04 +0200 Subject: [PATCH 07/10] Working example to resolve #5863 --- lib/pure/httpclient.nim | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/lib/pure/httpclient.nim b/lib/pure/httpclient.nim index 4f43177a8d..641576bf79 100644 --- a/lib/pure/httpclient.nim +++ b/lib/pure/httpclient.nim @@ -62,7 +62,8 @@ ## let body = %*{ ## "data": "some text" ## } -## echo client.request("http://some.api", httpMethod = HttpPost, body = $body) +## var response = client.request("http://some.api", httpMethod = HttpPost, body = $body) +## echo response.status ## ## Progress reporting ## ================== From 0a022664d513dc01ca03b4a74b6a6d80314cfcf4 Mon Sep 17 00:00:00 2001 From: daneb Date: Tue, 13 Jun 2017 21:45:18 +0200 Subject: [PATCH 08/10] Minor formatting --- lib/pure/httpclient.nim | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/pure/httpclient.nim b/lib/pure/httpclient.nim index 641576bf79..909a2613f1 100644 --- a/lib/pure/httpclient.nim +++ b/lib/pure/httpclient.nim @@ -62,7 +62,7 @@ ## let body = %*{ ## "data": "some text" ## } -## var response = client.request("http://some.api", httpMethod = HttpPost, body = $body) +## let response = client.request("http://some.api", httpMethod = HttpPost, body = $body) ## echo response.status ## ## Progress reporting From a0f39e0ab4b050a0ef189917e3892a07f92b57dc Mon Sep 17 00:00:00 2001 From: "Markus F.X.J. Oberhumer" Date: Thu, 15 Jun 2017 20:42:23 +0200 Subject: [PATCH 09/10] Ascii character code 127 (DEL) is not printable and must be quoted. (#5984) This is a follow-up to #5823. --- compiler/msgs.nim | 2 +- lib/pure/json.nim | 2 +- lib/pure/pegs.nim | 2 +- lib/pure/strutils.nim | 4 ++-- lib/system/repr.nim | 4 ++-- lib/system/reprjs.nim | 4 ++-- 6 files changed, 9 insertions(+), 9 deletions(-) diff --git a/compiler/msgs.nim b/compiler/msgs.nim index e416a38266..5f4a0caf14 100644 --- a/compiler/msgs.nim +++ b/compiler/msgs.nim @@ -543,7 +543,7 @@ var proc toCChar*(c: char): string = case c - of '\0'..'\x1F', '\x80'..'\xFF': result = '\\' & toOctal(c) + of '\0'..'\x1F', '\x7F'..'\xFF': result = '\\' & toOctal(c) of '\'', '\"', '\\', '?': result = '\\' & c else: result = $(c) diff --git a/lib/pure/json.nim b/lib/pure/json.nim index 6780ca164c..e3d5191c6e 100644 --- a/lib/pure/json.nim +++ b/lib/pure/json.nim @@ -1001,7 +1001,7 @@ proc escapeJson*(s: string; result: var string) = result.add("\"") for x in runes(s): var r = int(x) - if r >= 32 and r <= 127: + if r >= 32 and r <= 126: var c = chr(r) case c of '"': result.add("\\\"") diff --git a/lib/pure/pegs.nim b/lib/pure/pegs.nim index 5c978a2f8c..6a52e2cd54 100644 --- a/lib/pure/pegs.nim +++ b/lib/pure/pegs.nim @@ -371,7 +371,7 @@ proc esc(c: char, reserved = {'\0'..'\255'}): string = of '\a': result = "\\a" of '\\': result = "\\\\" of 'a'..'z', 'A'..'Z', '0'..'9', '_': result = $c - elif c < ' ' or c >= '\128': result = '\\' & $ord(c) + elif c < ' ' or c >= '\127': result = '\\' & $ord(c) elif c in reserved: result = '\\' & c else: result = $c diff --git a/lib/pure/strutils.nim b/lib/pure/strutils.nim index 458c22f3a5..20b2657f6f 100644 --- a/lib/pure/strutils.nim +++ b/lib/pure/strutils.nim @@ -1643,7 +1643,7 @@ proc escape*(s: string, prefix = "\"", suffix = "\""): string {.noSideEffect, ## * replaces any ``\`` by ``\\`` ## * replaces any ``'`` by ``\'`` ## * replaces any ``"`` by ``\"`` - ## * replaces any other character in the set ``{'\0'..'\31', '\128'..'\255'}`` + ## * replaces any other character in the set ``{'\0'..'\31', '\127'..'\255'}`` ## by ``\xHH`` where ``HH`` is its hexadecimal value. ## The procedure has been designed so that its output is usable for many ## different common syntaxes. The resulting string is prefixed with @@ -1653,7 +1653,7 @@ proc escape*(s: string, prefix = "\"", suffix = "\""): string {.noSideEffect, result.add(prefix) for c in items(s): case c - of '\0'..'\31', '\128'..'\255': + of '\0'..'\31', '\127'..'\255': add(result, "\\x") add(result, toHex(ord(c), 2)) of '\\': add(result, "\\\\") diff --git a/lib/system/repr.nim b/lib/system/repr.nim index d9aa03b535..ab02c58a2a 100644 --- a/lib/system/repr.nim +++ b/lib/system/repr.nim @@ -49,7 +49,7 @@ proc reprStrAux(result: var string, s: cstring; len: int) = of '"': add result, "\\\"" of '\\': add result, "\\\\" # BUGFIX: forgotten of '\10': add result, "\\10\"\n\"" # " \n " # better readability - of '\128' .. '\255', '\0'..'\9', '\11'..'\31': + of '\127' .. '\255', '\0'..'\9', '\11'..'\31': add result, "\\" & reprInt(ord(c)) else: result.add(c) @@ -68,7 +68,7 @@ proc reprChar(x: char): string {.compilerRtl.} = case x of '"': add result, "\\\"" of '\\': add result, "\\\\" - of '\128' .. '\255', '\0'..'\31': add result, "\\" & reprInt(ord(x)) + of '\127' .. '\255', '\0'..'\31': add result, "\\" & reprInt(ord(x)) else: add result, x add result, "\'" diff --git a/lib/system/reprjs.nim b/lib/system/reprjs.nim index 6b0e32191e..5c265a8913 100644 --- a/lib/system/reprjs.nim +++ b/lib/system/reprjs.nim @@ -44,7 +44,7 @@ proc reprChar(x: char): string {.compilerRtl.} = case x of '"': add(result, "\\\"") of '\\': add(result, "\\\\") - of '\128'..'\255', '\0'..'\31': add( result, "\\" & reprInt(ord(x)) ) + of '\127'..'\255', '\0'..'\31': add( result, "\\" & reprInt(ord(x)) ) else: add(result, x) add(result, "\'") @@ -56,7 +56,7 @@ proc reprStrAux(result: var string, s: cstring, len: int) = of '"': add(result, "\\\"") of '\\': add(result, "\\\\") of '\10': add(result, "\\10\"\n\"") - of '\128'..'\255', '\0'..'\9', '\11'..'\31': + of '\127'..'\255', '\0'..'\9', '\11'..'\31': add( result, "\\" & reprInt(ord(c)) ) else: add( result, reprInt(ord(c)) ) # Not sure about this. From 17b55f9b29484f47e0008666cf638f6e26a782e2 Mon Sep 17 00:00:00 2001 From: John Novak Date: Fri, 16 Jun 2017 05:00:18 +1000 Subject: [PATCH 10/10] Add sgn() function to the math module (#5971) --- lib/pure/math.nim | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+) diff --git a/lib/pure/math.nim b/lib/pure/math.nim index a8432b6f0f..a1b2690a24 100644 --- a/lib/pure/math.nim +++ b/lib/pure/math.nim @@ -395,6 +395,12 @@ proc radToDeg*[T: float32|float64](d: T): T {.inline.} = ## Convert from radians to degrees result = T(d) / RadPerDeg +proc sgn*[T: SomeNumber](x: T): int {.inline.} = + ## Sign function. Returns -1 for negative numbers and `NegInf`, 1 for + ## positive numbers and `Inf`, and 0 for positive zero, negative zero and + ## `NaN`. + ord(T(0) < x) - ord(x < T(0)) + proc `mod`*[T: float32|float64](x, y: T): T = ## Computes the modulo operation for float operators. Equivalent ## to ``x - y * floor(x/y)``. Note that the remainder will always @@ -447,6 +453,7 @@ when isMainModule and not defined(JS): assert(lgamma(1.0) == 0.0) # ln(1.0) == 0.0 assert(erf(6.0) > erf(5.0)) assert(erfc(6.0) < erfc(5.0)) + when isMainModule: # Function for approximate comparison of floats proc `==~`(x, y: float): bool = (abs(x-y) < 1e-9) @@ -509,3 +516,21 @@ when isMainModule: doAssert(classify(trunc(-1e1000000'f32)) == fcNegInf) doAssert(classify(trunc(f_nan.float32)) == fcNan) doAssert(classify(trunc(0.0'f32)) == fcZero) + + block: # sgn() tests + assert sgn(1'i8) == 1 + assert sgn(1'i16) == 1 + assert sgn(1'i32) == 1 + assert sgn(1'i64) == 1 + assert sgn(1'u8) == 1 + assert sgn(1'u16) == 1 + assert sgn(1'u32) == 1 + assert sgn(1'u64) == 1 + assert sgn(-12342.8844'f32) == -1 + assert sgn(123.9834'f64) == 1 + assert sgn(0'i32) == 0 + assert sgn(0'f32) == 0 + assert sgn(NegInf) == -1 + assert sgn(Inf) == 1 + assert sgn(NaN) == 0 +