mirror of
https://github.com/nim-lang/Nim.git
synced 2026-01-02 03:02:31 +00:00
bugfix: init of temps
This commit is contained in:
18
.bzrignore
18
.bzrignore
@@ -1,18 +0,0 @@
|
||||
web/*.html
|
||||
doc/*.html
|
||||
*.o
|
||||
*.pyc
|
||||
*.pyo
|
||||
*.obj
|
||||
*.ppu
|
||||
*.exe
|
||||
*.dll
|
||||
*.zip
|
||||
*.tar.gz
|
||||
dist
|
||||
web
|
||||
misc
|
||||
lib/base/devel
|
||||
lib/base/devel/*
|
||||
lib/devel
|
||||
lib/devel/*
|
||||
@@ -433,4 +433,15 @@ struct NimException {
|
||||
|
||||
#define NIM_POSIX_INIT __attribute__((constructor))
|
||||
|
||||
|
||||
#if defined(_MSCVER) && defined(__i386__)
|
||||
__declspec(naked) int __fastcall NimXadd(volatile int* pNum, int val) {
|
||||
__asm {
|
||||
lock xadd dword ptr [ECX], EDX
|
||||
mov EAX, EDX
|
||||
ret
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
@@ -345,6 +345,8 @@ proc next*(my: var TJsonParser) =
|
||||
## retrieves the first/next event. This controls the parser.
|
||||
var tk = getTok(my)
|
||||
var i = my.state.len-1
|
||||
# the following code is a state machine. If we had proper coroutines,
|
||||
# the code could be much simpler.
|
||||
case my.state[i]
|
||||
of stateEof:
|
||||
if tk == tkEof:
|
||||
|
||||
@@ -73,7 +73,7 @@ proc mustRehash(length, counter: int): bool =
|
||||
assert(length > counter)
|
||||
result = (length * 2 < counter * 3) or (length - counter < 4)
|
||||
|
||||
proc nextTry(h, maxHash: THash): THash =
|
||||
proc nextTry(h, maxHash: THash): THash {.inline.} =
|
||||
result = ((5 * h) + 1) and maxHash
|
||||
|
||||
proc RawGet(t: PStringTable, key: string): int =
|
||||
|
||||
@@ -1303,6 +1303,12 @@ when not defined(EcmaScript) and not defined(NimrodVM):
|
||||
|
||||
when not defined(EcmaScript) and not defined(NimrodVM):
|
||||
|
||||
proc atomicInc*(memLoc: var int, x: int): int {.inline.}
|
||||
## atomic increment of `memLoc`. Returns the value after the operation.
|
||||
|
||||
proc atomicDec*(memLoc: var int, x: int): int {.inline.}
|
||||
## atomic decrement of `memLoc`. Returns the value after the operation.
|
||||
|
||||
proc initGC()
|
||||
|
||||
proc initStackBottom() {.inline.} =
|
||||
|
||||
@@ -7,9 +7,35 @@
|
||||
# distribution, for details about the copyright.
|
||||
#
|
||||
|
||||
when defined(gcc) or defined(llvm_gcc):
|
||||
proc sync_add_and_fetch(p: var int, val: int): int {.
|
||||
importc: "__sync_add_and_fetch", nodecl.}
|
||||
proc sync_sub_and_fetch(p: var int, val: int): int {.
|
||||
importc: "__sync_sub_and_fetch", nodecl.}
|
||||
elif defined(vcc):
|
||||
proc sync_add_and_fetch(p: var int, val: int): int {.
|
||||
importc: "NimXadd", nodecl.}
|
||||
|
||||
const
|
||||
isMultiThreaded* = true
|
||||
maxThreads = 256
|
||||
|
||||
proc atomicInc(memLoc: var int, x: int): int =
|
||||
when isMultiThreaded:
|
||||
result = sync_add_and_fetch(memLoc, x)
|
||||
else:
|
||||
inc(memLoc, x)
|
||||
result = memLoc
|
||||
|
||||
proc atomicDec(memLoc: var int, x: int): int =
|
||||
when isMultiThreaded:
|
||||
when defined(sync_sub_and_fetch):
|
||||
result = sync_sub_and_fetch(memLoc, x)
|
||||
else:
|
||||
result = sync_add_and_fetch(memLoc, -x)
|
||||
else:
|
||||
dec(memLoc, x)
|
||||
result = memLoc
|
||||
|
||||
type
|
||||
TThread* {.final, pure.} = object
|
||||
|
||||
0
lib/wrappers/expat.nim
Normal file → Executable file
0
lib/wrappers/expat.nim
Normal file → Executable file
@@ -153,21 +153,6 @@ proc getStorageLoc(n: PNode): TStorageLoc =
|
||||
result = getStorageLoc(n.sons[0])
|
||||
else: result = OnUnknown
|
||||
|
||||
proc rdLoc(a: TLoc): PRope =
|
||||
# 'read' location (deref if indirect)
|
||||
result = a.r
|
||||
if lfIndirect in a.flags: result = ropef("(*$1)", [result])
|
||||
|
||||
proc addrLoc(a: TLoc): PRope =
|
||||
result = a.r
|
||||
if not (lfIndirect in a.flags): result = con("&", result)
|
||||
|
||||
proc rdCharLoc(a: TLoc): PRope =
|
||||
# read a location that may need a char-cast:
|
||||
result = rdLoc(a)
|
||||
if skipTypes(a.t, abstractRange).kind == tyChar:
|
||||
result = ropef("((NU8)($1))", [result])
|
||||
|
||||
type
|
||||
TAssignmentFlag = enum
|
||||
needToCopy, needForSubtypeCheck, afDestIsNil, afDestIsNotNil, afSrcIsNil,
|
||||
@@ -1242,7 +1227,8 @@ proc genSetOp(p: BProc, e: PNode, d: var TLoc, op: TMagic) =
|
||||
initLocExpr(p, e.sons[2], b)
|
||||
if d.k == locNone: getTemp(p, a.t, d)
|
||||
appf(p.s[cpsStmts],
|
||||
"for ($1 = 0; $1 < $2; $1++) $n" & " $3[$1] = $4[$1] $6 $5[$1];$n", [
|
||||
"for ($1 = 0; $1 < $2; $1++) $n" &
|
||||
" $3[$1] = $4[$1] $6 $5[$1];$n", [
|
||||
rdLoc(i), toRope(size), rdLoc(d), rdLoc(a), rdLoc(b),
|
||||
toRope(lookupOpr[op])])
|
||||
of mInSet: genInOp(p, e, d)
|
||||
|
||||
@@ -44,29 +44,6 @@ proc genReturnStmt(p: BProc, t: PNode) =
|
||||
finishTryStmt(p, p.nestedTryStmts)
|
||||
appff(p.s[cpsStmts], "goto BeforeRet;$n", "br label %BeforeRet$n", [])
|
||||
|
||||
proc initVariable(p: BProc, v: PSym) =
|
||||
if containsGarbageCollectedRef(v.typ) or (v.ast == nil):
|
||||
if not (skipTypes(v.typ, abstractVarRange).Kind in
|
||||
{tyArray, tyArrayConstr, tySet, tyTuple, tyObject}):
|
||||
if gCmd == cmdCompileToLLVM:
|
||||
appf(p.s[cpsStmts], "store $2 0, $2* $1$n",
|
||||
[addrLoc(v.loc), getTypeDesc(p.module, v.loc.t)])
|
||||
else:
|
||||
appf(p.s[cpsStmts], "$1 = 0;$n", [rdLoc(v.loc)])
|
||||
else:
|
||||
if gCmd == cmdCompileToLLVM:
|
||||
app(p.module.s[cfsProcHeaders],
|
||||
"declare void @llvm.memset.i32(i8*, i8, i32, i32)" & tnl)
|
||||
inc(p.labels, 2)
|
||||
appf(p.s[cpsStmts], "%LOC$3 = getelementptr $2* null, %NI 1$n" &
|
||||
"%LOC$4 = cast $2* %LOC$3 to i32$n" &
|
||||
"call void @llvm.memset.i32(i8* $1, i8 0, i32 %LOC$4, i32 0)$n", [
|
||||
addrLoc(v.loc), getTypeDesc(p.module, v.loc.t), toRope(p.labels),
|
||||
toRope(p.labels - 1)])
|
||||
else:
|
||||
appf(p.s[cpsStmts], "memset((void*)$1, 0, sizeof($2));$n",
|
||||
[addrLoc(v.loc), rdLoc(v.loc)])
|
||||
|
||||
proc genVarTuple(p: BProc, n: PNode) =
|
||||
var
|
||||
L: int
|
||||
|
||||
46
rod/cgen.nim
46
rod/cgen.nim
@@ -236,6 +236,51 @@ include "ccgtypes.nim"
|
||||
|
||||
# ------------------------------ Manager of temporaries ------------------
|
||||
|
||||
proc rdLoc(a: TLoc): PRope =
|
||||
# 'read' location (deref if indirect)
|
||||
result = a.r
|
||||
if lfIndirect in a.flags: result = ropef("(*$1)", [result])
|
||||
|
||||
proc addrLoc(a: TLoc): PRope =
|
||||
result = a.r
|
||||
if not (lfIndirect in a.flags): result = con("&", result)
|
||||
|
||||
proc rdCharLoc(a: TLoc): PRope =
|
||||
# read a location that may need a char-cast:
|
||||
result = rdLoc(a)
|
||||
if skipTypes(a.t, abstractRange).kind == tyChar:
|
||||
result = ropef("((NU8)($1))", [result])
|
||||
|
||||
proc zeroLoc(p: BProc, loc: TLoc) =
|
||||
if not (skipTypes(loc.t, abstractVarRange).Kind in
|
||||
{tyArray, tyArrayConstr, tySet, tyTuple, tyObject}):
|
||||
if gCmd == cmdCompileToLLVM:
|
||||
appf(p.s[cpsStmts], "store $2 0, $2* $1$n",
|
||||
[addrLoc(loc), getTypeDesc(p.module, loc.t)])
|
||||
else:
|
||||
appf(p.s[cpsStmts], "$1 = 0;$n", [rdLoc(loc)])
|
||||
else:
|
||||
if gCmd == cmdCompileToLLVM:
|
||||
app(p.module.s[cfsProcHeaders],
|
||||
"declare void @llvm.memset.i32(i8*, i8, i32, i32)" & tnl)
|
||||
inc(p.labels, 2)
|
||||
appf(p.s[cpsStmts], "%LOC$3 = getelementptr $2* null, %NI 1$n" &
|
||||
"%LOC$4 = cast $2* %LOC$3 to i32$n" &
|
||||
"call void @llvm.memset.i32(i8* $1, i8 0, i32 %LOC$4, i32 0)$n", [
|
||||
addrLoc(loc), getTypeDesc(p.module, loc.t), toRope(p.labels),
|
||||
toRope(p.labels - 1)])
|
||||
else:
|
||||
appf(p.s[cpsStmts], "memset((void*)$1, 0, sizeof($2));$n",
|
||||
[addrLoc(loc), rdLoc(loc)])
|
||||
|
||||
proc initVariable(p: BProc, v: PSym) =
|
||||
if containsGarbageCollectedRef(v.typ) or (v.ast == nil):
|
||||
zeroLoc(p, v.loc)
|
||||
|
||||
proc initTemp(p: BProc, tmp: var TLoc) =
|
||||
if containsGarbageCollectedRef(tmp.t):
|
||||
zeroLoc(p, tmp)
|
||||
|
||||
proc getTemp(p: BProc, t: PType, result: var TLoc) =
|
||||
inc(p.labels)
|
||||
if gCmd == cmdCompileToLLVM:
|
||||
@@ -248,6 +293,7 @@ proc getTemp(p: BProc, t: PType, result: var TLoc) =
|
||||
result.t = getUniqueType(t)
|
||||
result.s = OnStack
|
||||
result.flags = {}
|
||||
initTemp(p, result)
|
||||
|
||||
proc cstringLit(p: BProc, r: var PRope, s: string): PRope =
|
||||
if gCmd == cmdCompileToLLVM:
|
||||
|
||||
@@ -315,7 +315,7 @@ proc evalFieldAccess(c: PEvalContext, n: PNode, flags: TEvalFlags): PNode =
|
||||
for i in countup(0, sonsLen(n) - 1):
|
||||
if x.sons[i].kind != nkExprColonExpr:
|
||||
InternalError(n.info, "evalFieldAccess")
|
||||
if x.sons[i].sons[0].sym.name.id == field.id:
|
||||
if x.sons[i].sons[0].sym.name.id == field.name.id:
|
||||
result = x.sons[i].sons[1]
|
||||
if not aliasNeeded(result, flags): result = copyTree(result)
|
||||
return
|
||||
|
||||
@@ -2,8 +2,8 @@
|
||||
Name: "Nimrod"
|
||||
Version: "$version"
|
||||
; Windows and i386 must be first!
|
||||
OS: "windows" ;linux;macosx;freebsd;netbsd;openbsd;solaris"
|
||||
CPU: "i386" ;amd64" # ;sparc;powerpc
|
||||
OS: "windows;linux;macosx;freebsd;netbsd;openbsd;solaris"
|
||||
CPU: "i386;amd64;powerpc" # ;sparc
|
||||
Authors: "Andreas Rumpf"
|
||||
Description: """This is the Nimrod Compiler. Nimrod is a new statically typed,
|
||||
imperative programming language, that supports procedural, functional, object
|
||||
|
||||
@@ -663,10 +663,14 @@ proc semProcAux(c: PContext, n: PNode, kind: TSymKind,
|
||||
n.sons[genericParamsPos] = semGenericParamList(c, n.sons[genericParamsPos])
|
||||
gp = n.sons[genericParamsPos]
|
||||
else:
|
||||
gp = newNodeI(nkGenericParams, n.info) # process parameters:
|
||||
gp = newNodeI(nkGenericParams, n.info)
|
||||
# process parameters:
|
||||
if n.sons[paramsPos] != nil:
|
||||
semParamList(c, n.sons[ParamsPos], gp, s)
|
||||
if sonsLen(gp) > 0: n.sons[genericParamsPos] = gp
|
||||
if sonsLen(gp) > 0:
|
||||
if n.sons[genericParamsPos] == nil:
|
||||
# we have a list of implicit type parameters:
|
||||
n.sons[genericParamsPos] = gp
|
||||
addParams(c, s.typ.n)
|
||||
else:
|
||||
s.typ = newTypeS(tyProc, c)
|
||||
|
||||
@@ -485,15 +485,9 @@ proc semProcTypeNode(c: PContext, n, genericParams: PNode, prev: PType): PType =
|
||||
result.callConv = lastOptionEntry(c).defaultCC
|
||||
result.n = newNodeI(nkFormalParams, n.info)
|
||||
if (genericParams != nil) and (sonsLen(genericParams) == 0): IntSetInit(cl)
|
||||
if n.sons[0] == nil:
|
||||
addSon(result, nil) # return type
|
||||
addSon(result.n, newNodeI(nkType, n.info))
|
||||
# BUGFIX: nkType must exist!
|
||||
# XXX but it does not, if n.sons[paramsPos] == nil?
|
||||
else:
|
||||
addSon(result, nil)
|
||||
res = newNodeI(nkType, n.info)
|
||||
addSon(result.n, res)
|
||||
addSon(result, nil) # return type
|
||||
res = newNodeI(nkType, n.info)
|
||||
addSon(result.n, res)
|
||||
IntSetInit(check)
|
||||
var counter = 0
|
||||
for i in countup(1, sonsLen(n) - 1):
|
||||
@@ -531,9 +525,8 @@ proc semProcTypeNode(c: PContext, n, genericParams: PNode, prev: PType): PType =
|
||||
res.typ = result.sons[0]
|
||||
|
||||
proc semStmtListType(c: PContext, n: PNode, prev: PType): PType =
|
||||
var length: int
|
||||
checkMinSonsLen(n, 1)
|
||||
length = sonsLen(n)
|
||||
var length = sonsLen(n)
|
||||
for i in countup(0, length - 2):
|
||||
n.sons[i] = semStmt(c, n.sons[i])
|
||||
if length > 0:
|
||||
|
||||
2
todo.txt
2
todo.txt
@@ -17,8 +17,6 @@ Bugs
|
||||
----
|
||||
- proc (x: int) is passable to proc (x: var int) !?
|
||||
- detected by pegs module 64bit: p(result, result) should use a temporary!
|
||||
- seq[TLoc] in C code generator always failed --> probably some reference
|
||||
counting is wrong; try to reproduce this in the GC test
|
||||
- the parser allows empty object case branches
|
||||
- SDL event handling
|
||||
|
||||
|
||||
Reference in New Issue
Block a user