fixes a regression where memset was used without including <string.h>
This commit is contained in:
parent
5dcfa97fb9
commit
fe983b1309
5 changed files with 29 additions and 2 deletions
|
|
@ -240,6 +240,7 @@ proc genGenericAsgn(p: BProc, dest, src: TLoc, flags: TAssignmentFlags) =
|
||||||
if needToCopy notin flags or
|
if needToCopy notin flags or
|
||||||
tfShallow in skipTypes(dest.t, abstractVarRange).flags:
|
tfShallow in skipTypes(dest.t, abstractVarRange).flags:
|
||||||
if dest.s == OnStack or not usesNativeGC():
|
if dest.s == OnStack or not usesNativeGC():
|
||||||
|
useStringh(p.module)
|
||||||
linefmt(p, cpsStmts,
|
linefmt(p, cpsStmts,
|
||||||
"memcpy((void*)$1, (NIM_CONST void*)$2, sizeof($3));$n",
|
"memcpy((void*)$1, (NIM_CONST void*)$2, sizeof($3));$n",
|
||||||
addrLoc(dest), addrLoc(src), rdLoc(dest))
|
addrLoc(dest), addrLoc(src), rdLoc(dest))
|
||||||
|
|
@ -316,6 +317,7 @@ proc genAssignment(p: BProc, dest, src: TLoc, flags: TAssignmentFlags) =
|
||||||
if needsComplexAssignment(dest.t):
|
if needsComplexAssignment(dest.t):
|
||||||
genGenericAsgn(p, dest, src, flags)
|
genGenericAsgn(p, dest, src, flags)
|
||||||
else:
|
else:
|
||||||
|
useStringh(p.module)
|
||||||
linefmt(p, cpsStmts,
|
linefmt(p, cpsStmts,
|
||||||
"memcpy((void*)$1, (NIM_CONST void*)$2, sizeof($1));$n",
|
"memcpy((void*)$1, (NIM_CONST void*)$2, sizeof($1));$n",
|
||||||
rdLoc(dest), rdLoc(src))
|
rdLoc(dest), rdLoc(src))
|
||||||
|
|
@ -327,11 +329,13 @@ proc genAssignment(p: BProc, dest, src: TLoc, flags: TAssignmentFlags) =
|
||||||
"#genericAssignOpenArray((void*)$1, (void*)$2, $1Len0, $3);$n",
|
"#genericAssignOpenArray((void*)$1, (void*)$2, $1Len0, $3);$n",
|
||||||
addrLoc(dest), addrLoc(src), genTypeInfo(p.module, dest.t))
|
addrLoc(dest), addrLoc(src), genTypeInfo(p.module, dest.t))
|
||||||
else:
|
else:
|
||||||
|
useStringh(p.module)
|
||||||
linefmt(p, cpsStmts,
|
linefmt(p, cpsStmts,
|
||||||
"memcpy((void*)$1, (NIM_CONST void*)$2, sizeof($1[0])*$1Len0);$n",
|
"memcpy((void*)$1, (NIM_CONST void*)$2, sizeof($1[0])*$1Len0);$n",
|
||||||
rdLoc(dest), rdLoc(src))
|
rdLoc(dest), rdLoc(src))
|
||||||
of tySet:
|
of tySet:
|
||||||
if mapType(ty) == ctArray:
|
if mapType(ty) == ctArray:
|
||||||
|
useStringh(p.module)
|
||||||
linefmt(p, cpsStmts, "memcpy((void*)$1, (NIM_CONST void*)$2, $3);$n",
|
linefmt(p, cpsStmts, "memcpy((void*)$1, (NIM_CONST void*)$2, $3);$n",
|
||||||
rdLoc(dest), rdLoc(src), toRope(getSize(dest.t)))
|
rdLoc(dest), rdLoc(src), toRope(getSize(dest.t)))
|
||||||
else:
|
else:
|
||||||
|
|
@ -1361,6 +1365,7 @@ proc genSetOp(p: BProc, e: PNode, d: var TLoc, op: TMagic) =
|
||||||
lineF(p, cpsStmts, lookupOpr[op],
|
lineF(p, cpsStmts, lookupOpr[op],
|
||||||
[rdLoc(i), toRope(size), rdLoc(d), rdLoc(a), rdLoc(b)])
|
[rdLoc(i), toRope(size), rdLoc(d), rdLoc(a), rdLoc(b)])
|
||||||
of mEqSet:
|
of mEqSet:
|
||||||
|
useStringh(p.module)
|
||||||
binaryExprChar(p, e, d, "(memcmp($1, $2, " & $(size) & ")==0)")
|
binaryExprChar(p, e, d, "(memcmp($1, $2, " & $(size) & ")==0)")
|
||||||
of mMulSet, mPlusSet, mMinusSet, mSymDiffSet:
|
of mMulSet, mPlusSet, mMinusSet, mSymDiffSet:
|
||||||
# we inline the simple for loop for better code generation:
|
# we inline the simple for loop for better code generation:
|
||||||
|
|
@ -1612,6 +1617,7 @@ proc genSetConstr(p: BProc, e: PNode, d: var TLoc) =
|
||||||
if d.k == locNone: getTemp(p, e.typ, d)
|
if d.k == locNone: getTemp(p, e.typ, d)
|
||||||
if getSize(e.typ) > 8:
|
if getSize(e.typ) > 8:
|
||||||
# big set:
|
# big set:
|
||||||
|
useStringh(p.module)
|
||||||
lineF(p, cpsStmts, "memset($1, 0, sizeof($1));$n", [rdLoc(d)])
|
lineF(p, cpsStmts, "memset($1, 0, sizeof($1));$n", [rdLoc(d)])
|
||||||
for i in countup(0, sonsLen(e) - 1):
|
for i in countup(0, sonsLen(e) - 1):
|
||||||
if e.sons[i].kind == nkRange:
|
if e.sons[i].kind == nkRange:
|
||||||
|
|
|
||||||
|
|
@ -72,6 +72,11 @@ proc isSimpleConst(typ: PType): bool =
|
||||||
{tyTuple, tyObject, tyArray, tyArrayConstr, tySet, tySequence} and not
|
{tyTuple, tyObject, tyArray, tyArrayConstr, tySet, tySequence} and not
|
||||||
(t.kind == tyProc and t.callConv == ccClosure)
|
(t.kind == tyProc and t.callConv == ccClosure)
|
||||||
|
|
||||||
|
proc useStringh(m: BModule) =
|
||||||
|
if not m.includesStringh:
|
||||||
|
m.includesStringh = true
|
||||||
|
discard lists.IncludeStr(m.headerFiles, "<string.h>")
|
||||||
|
|
||||||
proc useHeader(m: BModule, sym: PSym) =
|
proc useHeader(m: BModule, sym: PSym) =
|
||||||
if lfHeader in sym.loc.Flags:
|
if lfHeader in sym.loc.Flags:
|
||||||
assert(sym.annex != nil)
|
assert(sym.annex != nil)
|
||||||
|
|
@ -358,6 +363,7 @@ proc resetLoc(p: BProc, loc: var TLoc) =
|
||||||
# field, so disabling this should be safe:
|
# field, so disabling this should be safe:
|
||||||
genObjectInit(p, cpsStmts, loc.t, loc, true)
|
genObjectInit(p, cpsStmts, loc.t, loc, true)
|
||||||
else:
|
else:
|
||||||
|
useStringh(p.module)
|
||||||
linefmt(p, cpsStmts, "memset((void*)$1, 0, sizeof($2));$n",
|
linefmt(p, cpsStmts, "memset((void*)$1, 0, sizeof($2));$n",
|
||||||
addrLoc(loc), rdLoc(loc))
|
addrLoc(loc), rdLoc(loc))
|
||||||
# XXX: We can be extra clever here and call memset only
|
# XXX: We can be extra clever here and call memset only
|
||||||
|
|
@ -368,6 +374,7 @@ proc constructLoc(p: BProc, loc: TLoc, section = cpsStmts) =
|
||||||
if not isComplexValueType(skipTypes(loc.t, abstractRange)):
|
if not isComplexValueType(skipTypes(loc.t, abstractRange)):
|
||||||
linefmt(p, section, "$1 = 0;$n", rdLoc(loc))
|
linefmt(p, section, "$1 = 0;$n", rdLoc(loc))
|
||||||
else:
|
else:
|
||||||
|
useStringh(p.module)
|
||||||
linefmt(p, section, "memset((void*)$1, 0, sizeof($2));$n",
|
linefmt(p, section, "memset((void*)$1, 0, sizeof($2));$n",
|
||||||
addrLoc(loc), rdLoc(loc))
|
addrLoc(loc), rdLoc(loc))
|
||||||
genObjectInit(p, section, loc.t, loc, true)
|
genObjectInit(p, section, loc.t, loc, true)
|
||||||
|
|
@ -418,6 +425,7 @@ proc keepAlive(p: BProc, toKeepAlive: TLoc) =
|
||||||
if not isComplexValueType(skipTypes(toKeepAlive.t, abstractVarRange)):
|
if not isComplexValueType(skipTypes(toKeepAlive.t, abstractVarRange)):
|
||||||
linefmt(p, cpsStmts, "$1 = $2;$n", rdLoc(result), rdLoc(toKeepAlive))
|
linefmt(p, cpsStmts, "$1 = $2;$n", rdLoc(result), rdLoc(toKeepAlive))
|
||||||
else:
|
else:
|
||||||
|
useStringh(p.module)
|
||||||
linefmt(p, cpsStmts,
|
linefmt(p, cpsStmts,
|
||||||
"memcpy((void*)$1, (NIM_CONST void*)$2, sizeof($3));$n",
|
"memcpy((void*)$1, (NIM_CONST void*)$2, sizeof($3));$n",
|
||||||
addrLoc(result), addrLoc(toKeepAlive), rdLoc(result))
|
addrLoc(result), addrLoc(toKeepAlive), rdLoc(result))
|
||||||
|
|
|
||||||
|
|
@ -91,6 +91,7 @@ type
|
||||||
FrameDeclared*: bool # hack for ROD support so that we don't declare
|
FrameDeclared*: bool # hack for ROD support so that we don't declare
|
||||||
# a frame var twice in an init proc
|
# a frame var twice in an init proc
|
||||||
isHeaderFile*: bool # C source file is the header file
|
isHeaderFile*: bool # C source file is the header file
|
||||||
|
includesStringh*: bool # C source file already includes ``<string.h>``
|
||||||
cfilename*: string # filename of the module (including path,
|
cfilename*: string # filename of the module (including path,
|
||||||
# without extension)
|
# without extension)
|
||||||
typeCache*: TIdTable # cache the generated types
|
typeCache*: TIdTable # cache the generated types
|
||||||
|
|
|
||||||
|
|
@ -629,7 +629,6 @@ proc doOperation(p: pointer, op: TWalkOp) =
|
||||||
case op
|
case op
|
||||||
of waZctDecRef:
|
of waZctDecRef:
|
||||||
#if not isAllocatedPtr(gch.region, c):
|
#if not isAllocatedPtr(gch.region, c):
|
||||||
# return
|
|
||||||
# c_fprintf(c_stdout, "[GC] decref bug: %p", c)
|
# c_fprintf(c_stdout, "[GC] decref bug: %p", c)
|
||||||
gcAssert(isAllocatedPtr(gch.region, c), "decRef: waZctDecRef")
|
gcAssert(isAllocatedPtr(gch.region, c), "decRef: waZctDecRef")
|
||||||
gcAssert(c.refcount >=% rcIncrement, "doOperation 2")
|
gcAssert(c.refcount >=% rcIncrement, "doOperation 2")
|
||||||
|
|
|
||||||
13
tests/reject/twrongiter.nim
Normal file
13
tests/reject/twrongiter.nim
Normal file
|
|
@ -0,0 +1,13 @@
|
||||||
|
discard """
|
||||||
|
line: 14
|
||||||
|
errormsg: "type mismatch"
|
||||||
|
"""
|
||||||
|
|
||||||
|
proc first(it: iterator(): int): seq[int] =
|
||||||
|
return @[]
|
||||||
|
|
||||||
|
iterator primes(): int =
|
||||||
|
yield 1
|
||||||
|
|
||||||
|
for i in first(primes):
|
||||||
|
break
|
||||||
Loading…
Add table
Add a link
Reference in a new issue