mirror of
https://github.com/nim-lang/Nim.git
synced 2026-01-09 14:32:53 +00:00
[backport:1.4] JS cstring null fixes (#16979)
* [backport:1.4] JS cstring null fixes
* fix JS move string
* make it look cleaner
(cherry picked from commit 81533a0014)
This commit is contained in:
@@ -1997,7 +1997,9 @@ proc genMagic(p: PProc, n: PNode, r: var TCompRes) =
|
||||
gen(p, n[2], rhs)
|
||||
|
||||
if skipTypes(n[1].typ, abstractVarRange).kind == tyCString:
|
||||
r.res = "$1 += $2;" % [lhs.rdLoc, rhs.rdLoc]
|
||||
let (b, tmp) = maybeMakeTemp(p, n[2], rhs)
|
||||
r.res = "if (null != $1) { if (null == $2) $2 = $3; else $2 += $3; }" %
|
||||
[b, lhs.rdLoc, tmp]
|
||||
else:
|
||||
let (a, tmp) = maybeMakeTemp(p, n[1], lhs)
|
||||
r.res = "$1.push.apply($3, $2);" % [a, rhs.rdLoc, tmp]
|
||||
@@ -2048,9 +2050,23 @@ proc genMagic(p: PProc, n: PNode, r: var TCompRes) =
|
||||
of mDestroy: discard "ignore calls to the default destructor"
|
||||
of mOrd: genOrd(p, n, r)
|
||||
of mLengthStr, mLengthSeq, mLengthOpenArray, mLengthArray:
|
||||
unaryExpr(p, n, r, "", "($1).length")
|
||||
var x: TCompRes
|
||||
gen(p, n[1], x)
|
||||
if skipTypes(n[1].typ, abstractInst).kind == tyCString:
|
||||
let (a, tmp) = maybeMakeTemp(p, n[1], x)
|
||||
r.res = "(($1) == null ? 0 : ($2).length)" % [a, tmp]
|
||||
else:
|
||||
r.res = "($1).length" % [x.rdLoc]
|
||||
r.kind = resExpr
|
||||
of mHigh:
|
||||
unaryExpr(p, n, r, "", "(($1).length-1)")
|
||||
var x: TCompRes
|
||||
gen(p, n[1], x)
|
||||
if skipTypes(n[1].typ, abstractInst).kind == tyCString:
|
||||
let (a, tmp) = maybeMakeTemp(p, n[1], x)
|
||||
r.res = "(($1) == null ? -1 : ($2).length - 1)" % [a, tmp]
|
||||
else:
|
||||
r.res = "($1).length - 1" % [x.rdLoc]
|
||||
r.kind = resExpr
|
||||
of mInc:
|
||||
if n[1].typ.skipTypes(abstractRange).kind in {tyUInt..tyUInt64}:
|
||||
binaryUintExpr(p, n, r, "+", true)
|
||||
|
||||
@@ -1957,8 +1957,14 @@ type
|
||||
when NimStackTraceMsgs:
|
||||
frameMsgLen*: int ## end position in frameMsgBuf for this frame.
|
||||
|
||||
when defined(js):
|
||||
when defined(js) or defined(nimdoc):
|
||||
proc add*(x: var string, y: cstring) {.asmNoStackFrame.} =
|
||||
## Appends `y` to `x` in place.
|
||||
runnableExamples:
|
||||
var tmp = ""
|
||||
tmp.add(cstring("ab"))
|
||||
tmp.add(cstring("cd"))
|
||||
doAssert tmp == "abcd"
|
||||
asm """
|
||||
if (`x` === null) { `x` = []; }
|
||||
var off = `x`.length;
|
||||
@@ -1967,7 +1973,15 @@ when defined(js):
|
||||
`x`[off+i] = `y`.charCodeAt(i);
|
||||
}
|
||||
"""
|
||||
proc add*(x: var cstring, y: cstring) {.magic: "AppendStrStr".}
|
||||
proc add*(x: var cstring, y: cstring) {.magic: "AppendStrStr".} =
|
||||
## Appends `y` to `x` in place.
|
||||
## Only implemented for JS backend.
|
||||
runnableExamples:
|
||||
when defined(js):
|
||||
var tmp: cstring = ""
|
||||
tmp.add(cstring("ab"))
|
||||
tmp.add(cstring("cd"))
|
||||
doAssert tmp == cstring("abcd")
|
||||
|
||||
elif hasAlloc:
|
||||
{.push stackTrace: off, profiler: off.}
|
||||
|
||||
@@ -634,7 +634,7 @@ proc genericReset(x: JSRef, ti: PNimType): JSRef {.compilerproc.} =
|
||||
asm "`result` = {m_type: `ti`};"
|
||||
else:
|
||||
asm "`result` = {};"
|
||||
of tySequence, tyOpenArray:
|
||||
of tySequence, tyOpenArray, tyString:
|
||||
asm """
|
||||
`result` = [];
|
||||
"""
|
||||
|
||||
@@ -14,4 +14,12 @@ block:
|
||||
var x = "foo".cstring
|
||||
var y: string
|
||||
add(y, x)
|
||||
doAssert y == "foo"
|
||||
doAssert y == "foo"
|
||||
|
||||
block:
|
||||
type Foo = object
|
||||
a: string
|
||||
var foo = Foo(a: "foo")
|
||||
var y = move foo.a
|
||||
doAssert foo.a.len == 0
|
||||
doAssert y == "foo"
|
||||
|
||||
@@ -71,9 +71,58 @@ block: # `$`(SomeInteger)
|
||||
testType int64
|
||||
testType BiggestInt
|
||||
|
||||
block: # #14350 for JS
|
||||
block: # #14350, #16674, #16686 for JS
|
||||
var cstr: cstring
|
||||
doAssert cstr == cstring(nil)
|
||||
doAssert cstr == nil
|
||||
doAssert cstr.isNil
|
||||
doAssert cstr != cstring("")
|
||||
doAssert cstr.len == 0
|
||||
|
||||
when defined(js):
|
||||
cstr.add(cstring("abc"))
|
||||
doAssert cstr == cstring("abc")
|
||||
|
||||
var nil1, nil2: cstring = nil
|
||||
|
||||
nil1.add(nil2)
|
||||
doAssert nil1 == cstring(nil)
|
||||
doAssert nil2 == cstring(nil)
|
||||
|
||||
nil1.add(cstring(""))
|
||||
doAssert nil1 == cstring("")
|
||||
doAssert nil2 == cstring(nil)
|
||||
|
||||
nil1.add(nil2)
|
||||
doAssert nil1 == cstring("")
|
||||
doAssert nil2 == cstring(nil)
|
||||
|
||||
nil2.add(nil1)
|
||||
doAssert nil1 == cstring("")
|
||||
doAssert nil2 == cstring("")
|
||||
|
||||
|
||||
proc main()=
|
||||
block:
|
||||
let a = -0.0
|
||||
doAssert $a == "-0.0"
|
||||
doAssert $(-0.0) == "-0.0"
|
||||
|
||||
block:
|
||||
let a = 0.0
|
||||
doAssert $a == "0.0"
|
||||
doAssert $(0.0) == "0.0"
|
||||
|
||||
block:
|
||||
let b = -0
|
||||
doAssert $b == "0"
|
||||
doAssert $(-0) == "0"
|
||||
|
||||
block:
|
||||
let b = 0
|
||||
doAssert $b == "0"
|
||||
doAssert $(0) == "0"
|
||||
|
||||
|
||||
static: main()
|
||||
main()
|
||||
|
||||
Reference in New Issue
Block a user