mirror of
https://github.com/nim-lang/Nim.git
synced 2026-02-15 15:44:14 +00:00
threading code deactivated; tiny C bugfix: don't report warnings to error callback
This commit is contained in:
@@ -1,3 +1,4 @@
|
||||
Comex
|
||||
Philippe Lhoste
|
||||
Mario Ray Mahardhika
|
||||
Dominik Picheta
|
||||
|
||||
@@ -1,14 +1,13 @@
|
||||
#
|
||||
#
|
||||
# Nimrod's Runtime Library
|
||||
# (c) Copyright 2006 Andreas Rumpf
|
||||
# (c) Copyright 2010 Andreas Rumpf
|
||||
#
|
||||
# See the file "copying.txt", included in this
|
||||
# distribution, for details about the copyright.
|
||||
#
|
||||
|
||||
## Declaration of the Document Object Model for the ECMAScript backend.
|
||||
## (c) 2008 Andreas Rumpf
|
||||
|
||||
when not defined(ecmascript):
|
||||
{.error: "This module only works on the ECMAScript platform".}
|
||||
|
||||
@@ -1605,10 +1605,8 @@ when not defined(EcmaScript) and not defined(NimrodVM):
|
||||
## can be used to mark a condition to be unlikely. This is a hint for the
|
||||
## optimizer.
|
||||
|
||||
elif defined(ecmaScript):
|
||||
include "system/ecmasys"
|
||||
elif defined(NimrodVM):
|
||||
# Stubs for the GC interface:
|
||||
elif defined(ecmaScript) or defined(NimrodVM):
|
||||
# Stubs:
|
||||
proc GC_disable() = nil
|
||||
proc GC_enable() = nil
|
||||
proc GC_fullCollect() = nil
|
||||
@@ -1620,16 +1618,19 @@ elif defined(NimrodVM):
|
||||
proc getOccupiedMem(): int = return -1
|
||||
proc getFreeMem(): int = return -1
|
||||
proc getTotalMem(): int = return -1
|
||||
|
||||
proc cmp(x, y: string): int =
|
||||
if x == y: return 0
|
||||
if x < y: return -1
|
||||
return 1
|
||||
|
||||
|
||||
proc dealloc(p: pointer) = nil
|
||||
proc alloc(size: int): pointer = nil
|
||||
proc alloc0(size: int): pointer = nil
|
||||
proc realloc(p: Pointer, newsize: int): pointer = nil
|
||||
|
||||
when defined(ecmaScript):
|
||||
include "system/ecmasys"
|
||||
elif defined(NimrodVM):
|
||||
proc cmp(x, y: string): int =
|
||||
if x == y: return 0
|
||||
if x < y: return -1
|
||||
return 1
|
||||
|
||||
{.pop.} # checks
|
||||
{.pop.} # hints
|
||||
|
||||
@@ -1,26 +1,12 @@
|
||||
#
|
||||
#
|
||||
# Nimrod's Runtime Library
|
||||
# (c) Copyright 2008 Andreas Rumpf
|
||||
# (c) Copyright 2010 Andreas Rumpf
|
||||
#
|
||||
# See the file "copying.txt", included in this
|
||||
# distribution, for details about the copyright.
|
||||
#
|
||||
|
||||
## Stubs for the GC interface:
|
||||
|
||||
proc GC_disable() = nil
|
||||
proc GC_enable() = nil
|
||||
proc GC_fullCollect() = nil
|
||||
proc GC_setStrategy(strategy: TGC_Strategy) = nil
|
||||
proc GC_enableMarkAndSweep() = nil
|
||||
proc GC_disableMarkAndSweep() = nil
|
||||
proc GC_getStatistics(): string = return ""
|
||||
|
||||
proc getOccupiedMem(): int = return -1
|
||||
proc getFreeMem(): int = return -1
|
||||
proc getTotalMem(): int = return -1
|
||||
|
||||
proc alert(s: cstring) {.importc, nodecl.}
|
||||
|
||||
type
|
||||
@@ -130,8 +116,6 @@ proc raiseIndexError() {.compilerproc, noreturn.} =
|
||||
proc raiseFieldError(f: string) {.compilerproc, noreturn.} =
|
||||
raise newException(EInvalidField, f & " is not accessible")
|
||||
|
||||
|
||||
|
||||
proc SetConstr() {.varargs, pure, compilerproc.} =
|
||||
asm """
|
||||
var result = {};
|
||||
@@ -317,61 +301,58 @@ proc ewriteln(x: cstring) =
|
||||
else:
|
||||
raise newException(EInvalidValue, "<body> element does not exist yet!")
|
||||
|
||||
proc echo*(x: int) = ewriteln($x)
|
||||
proc echo*(x: float) = ewriteln($x)
|
||||
proc echo*(x: bool) = ewriteln(if x: cstring("true") else: cstring("false"))
|
||||
proc echo*(x: string) = ewriteln(x)
|
||||
proc echo*(x: cstring) = ewriteln(x)
|
||||
|
||||
proc echo[Ty](x: Ty) =
|
||||
echo(x)
|
||||
|
||||
proc echo[Ty](x: openArray[Ty]) =
|
||||
for a in items(x): echo(a)
|
||||
proc rawEcho {.compilerproc.} =
|
||||
var node = document.getElementsByTagName("body")[0]
|
||||
if node == nil: raise newException(EIO, "<body> element does not exist yet!")
|
||||
asm """
|
||||
for (var i = 0; i < arguments.length; ++i) {
|
||||
var x = `toEcmaStr`(arguments[i]);
|
||||
`node`.appendChild(document.createTextNode(x))
|
||||
}
|
||||
"""
|
||||
node.appendChild(document.createElement("br"))
|
||||
|
||||
# Arithmetic:
|
||||
proc addInt(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
var result = `a` + `b`;
|
||||
if (result > 2147483647 || result < -2147483648) raiseOverflow();
|
||||
if (result > 2147483647 || result < -2147483648) `raiseOverflow`();
|
||||
return result;
|
||||
"""
|
||||
|
||||
proc subInt(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
var result = `a` - `b`;
|
||||
if (result > 2147483647 || result < -2147483648) raiseOverflow();
|
||||
if (result > 2147483647 || result < -2147483648) `raiseOverflow`();
|
||||
return result;
|
||||
"""
|
||||
|
||||
proc mulInt(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
var result = `a` * `b`;
|
||||
if (result > 2147483647 || result < -2147483648) raiseOverflow();
|
||||
if (result > 2147483647 || result < -2147483648) `raiseOverflow`();
|
||||
return result;
|
||||
"""
|
||||
|
||||
proc divInt(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
if (`b` == 0) raiseDivByZero();
|
||||
if (`b` == -1 && `a` == 2147483647) raiseOverflow();
|
||||
if (`b` == 0) `raiseDivByZero`();
|
||||
if (`b` == -1 && `a` == 2147483647) `raiseOverflow`();
|
||||
return Math.floor(`a` / `b`);
|
||||
"""
|
||||
|
||||
proc modInt(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
if (`b` == 0) raiseDivByZero();
|
||||
if (`b` == -1 && `a` == 2147483647) raiseOverflow();
|
||||
if (`b` == 0) `raiseDivByZero`();
|
||||
if (`b` == -1 && `a` == 2147483647) `raiseOverflow`();
|
||||
return Math.floor(`a` % `b`);
|
||||
"""
|
||||
|
||||
|
||||
|
||||
proc addInt64(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
var result = `a` + `b`;
|
||||
if (result > 9223372036854775807
|
||||
|| result < -9223372036854775808) raiseOverflow();
|
||||
|| result < -9223372036854775808) `raiseOverflow`();
|
||||
return result;
|
||||
"""
|
||||
|
||||
@@ -379,7 +360,7 @@ proc subInt64(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
var result = `a` - `b`;
|
||||
if (result > 9223372036854775807
|
||||
|| result < -9223372036854775808) raiseOverflow();
|
||||
|| result < -9223372036854775808) `raiseOverflow`();
|
||||
return result;
|
||||
"""
|
||||
|
||||
@@ -387,21 +368,21 @@ proc mulInt64(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
var result = `a` * `b`;
|
||||
if (result > 9223372036854775807
|
||||
|| result < -9223372036854775808) raiseOverflow();
|
||||
|| result < -9223372036854775808) `raiseOverflow`();
|
||||
return result;
|
||||
"""
|
||||
|
||||
proc divInt64(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
if (`b` == 0) raiseDivByZero();
|
||||
if (`b` == -1 && `a` == 9223372036854775807) raiseOverflow();
|
||||
if (`b` == 0) `raiseDivByZero`();
|
||||
if (`b` == -1 && `a` == 9223372036854775807) `raiseOverflow`();
|
||||
return Math.floor(`a` / `b`);
|
||||
"""
|
||||
|
||||
proc modInt64(a, b: int): int {.pure, compilerproc.} =
|
||||
asm """
|
||||
if (`b` == 0) raiseDivByZero();
|
||||
if (`b` == -1 && `a` == 9223372036854775807) raiseOverflow();
|
||||
if (`b` == 0) `raiseDivByZero`();
|
||||
if (`b` == -1 && `a` == 9223372036854775807) `raiseOverflow`();
|
||||
return Math.floor(`a` % `b`);
|
||||
"""
|
||||
|
||||
@@ -415,13 +396,13 @@ proc internalAssert(file: cstring, line: int) {.pure, compilerproc.} =
|
||||
asm """`e`.message = "[Assertion failure] file: "+`file`+", line: "+`line`"""
|
||||
raise e
|
||||
|
||||
include hti
|
||||
include "system/hti"
|
||||
|
||||
proc isFatPointer(ti: PNimType): bool =
|
||||
# This has to be consistent with the code generator!
|
||||
return ti.base.kind notin {tyRecord, tyRecordConstr, tyObject,
|
||||
return ti.base.kind notin {tyObject,
|
||||
tyArray, tyArrayConstr, tyPureObject, tyTuple,
|
||||
tyEmptySet, tyOpenArray, tySet, tyVar, tyRef, tyPtr}
|
||||
tyOpenArray, tySet, tyVar, tyRef, tyPtr}
|
||||
|
||||
proc NimCopy(x: pointer, ti: PNimType): pointer {.compilerproc.}
|
||||
|
||||
@@ -452,7 +433,7 @@ proc NimCopy(x: pointer, ti: PNimType): pointer =
|
||||
`result`[0] = `x`[0];
|
||||
`result`[1] = `x`[1];
|
||||
"""
|
||||
of tyEmptySet, tySet:
|
||||
of tySet:
|
||||
asm """
|
||||
`result` = {};
|
||||
for (var key in `x`) { `result`[key] = `x`[key]; }
|
||||
|
||||
@@ -10,6 +10,10 @@
|
||||
# Exception handling code. This is difficult because it has
|
||||
# to work if there is no more memory (but it doesn't yet!).
|
||||
|
||||
var
|
||||
stackTraceNewLine* = "\n" ## undocumented feature; it is replaced by ``<br>``
|
||||
## for CGI applications
|
||||
|
||||
when not defined(windows) or not defined(guiapp):
|
||||
proc writeToStdErr(msg: CString) = write(stdout, msg)
|
||||
|
||||
@@ -32,7 +36,7 @@ type
|
||||
TSafePoint {.compilerproc, final.} = object
|
||||
prev: PSafePoint # points to next safe point ON THE STACK
|
||||
status: int
|
||||
exc: ref E_Base # XXX only needed for bootstrapping
|
||||
exc: ref E_Base # XXX only needed for bootstrapping; unused
|
||||
context: C_JmpBuf
|
||||
|
||||
var
|
||||
@@ -55,6 +59,58 @@ proc pushCurrentException(e: ref E_Base) {.compilerRtl, inl.} =
|
||||
proc popCurrentException {.compilerRtl, inl.} =
|
||||
currException = currException.parent
|
||||
|
||||
# some platforms have native support for stack traces:
|
||||
const
|
||||
nimrodStackTrace = compileOption("stacktrace")
|
||||
nativeStackTrace = (defined(macosx) or defined(linux)) and
|
||||
not nimrodStackTrace and false
|
||||
|
||||
# `nativeStackTrace` does not work for me --> deactivated for now. Maybe for
|
||||
# the next release version.
|
||||
|
||||
when nativeStacktrace:
|
||||
type
|
||||
TDl_info {.importc: "Dl_info", header: "<dlfcn.h>",
|
||||
final, pure.} = object
|
||||
dli_fname: CString
|
||||
dli_fbase: pointer
|
||||
dli_sname: CString
|
||||
dli_saddr: pointer
|
||||
|
||||
proc backtrace(symbols: ptr pointer, size: int): int {.
|
||||
importc: "backtrace", header: "<execinfo.h>".}
|
||||
proc dladdr(addr1: pointer, info: ptr TDl_info): int {.
|
||||
importc: "dladdr", header: "<dlfcn.h>".}
|
||||
|
||||
var
|
||||
tempAddresses: array [0..127, pointer] # cannot be allocated on the stack!
|
||||
tempDlInfo: TDl_info
|
||||
|
||||
proc auxWriteStackTraceWithBacktrace(s: var string) =
|
||||
# This is allowed to be expensive since it only happens during crashes
|
||||
# (but this way you don't need manual stack tracing)
|
||||
var size = backtrace(cast[ptr pointer](addr(tempAddresses)),
|
||||
len(tempAddresses))
|
||||
var enabled = false
|
||||
for i in 0..size-1:
|
||||
var dlresult = dladdr(tempAddresses[i], addr(tempDlInfo))
|
||||
if enabled:
|
||||
if dlresult != 0:
|
||||
var oldLen = s.len
|
||||
add(s, tempDlInfo.dli_fname)
|
||||
if tempDlInfo.dli_sname != nil:
|
||||
for k in 1..max(1, 25-(s.len-oldLen)): add(s, ' ')
|
||||
add(s, tempDlInfo.dli_sname)
|
||||
else:
|
||||
add(s, '?')
|
||||
add(s, stackTraceNewLine)
|
||||
else:
|
||||
if dlresult != 0 and tempDlInfo.dli_sname != nil and
|
||||
c_strcmp(tempDlInfo.dli_sname, "signalHandler") == 0'i32:
|
||||
# Once we're past signalHandler, we're at what the user is
|
||||
# interested in
|
||||
enabled = true
|
||||
|
||||
type
|
||||
PFrame = ptr TFrame
|
||||
TFrame {.importc, nodecl, final.} = object
|
||||
@@ -74,9 +130,6 @@ var
|
||||
|
||||
tempFrames: array [0..127, PFrame] # cannot be allocated on the stack!
|
||||
|
||||
stackTraceNewLine* = "\n" ## undocumented feature; it is replaced by ``<br>``
|
||||
## for CGI applications
|
||||
|
||||
proc auxWriteStackTrace(f: PFrame, s: var string) =
|
||||
const
|
||||
firstCalls = 32
|
||||
@@ -120,7 +173,7 @@ proc auxWriteStackTrace(f: PFrame, s: var string) =
|
||||
add(s, stackTraceNewLine)
|
||||
|
||||
proc rawWriteStackTrace(s: var string) =
|
||||
when compileOption("stacktrace") or compileOption("linetrace"):
|
||||
when nimrodStackTrace:
|
||||
if framePtr == nil:
|
||||
add(s, "No stack traceback available")
|
||||
add(s, stackTraceNewLine)
|
||||
@@ -128,6 +181,10 @@ proc rawWriteStackTrace(s: var string) =
|
||||
add(s, "Traceback (most recent call last)")
|
||||
add(s, stackTraceNewLine)
|
||||
auxWriteStackTrace(framePtr, s)
|
||||
elif nativeStackTrace:
|
||||
add(s, "Traceback from system (most recent call last)")
|
||||
add(s, stackTraceNewLine)
|
||||
auxWriteStackTraceWithBacktrace(s)
|
||||
else:
|
||||
add(s, "No stack traceback available")
|
||||
add(s, stackTraceNewLine)
|
||||
@@ -197,11 +254,6 @@ proc WriteStackTrace() =
|
||||
rawWriteStackTrace(s)
|
||||
writeToStdErr(s)
|
||||
|
||||
#proc stackTraceWrapper {.noconv.} =
|
||||
# writeStackTrace()
|
||||
|
||||
#addQuitProc(stackTraceWrapper)
|
||||
|
||||
var
|
||||
dbgAborting: bool # whether the debugger wants to abort
|
||||
|
||||
|
||||
@@ -77,14 +77,16 @@ var
|
||||
# collection, not a lock for threads!
|
||||
|
||||
proc lock(gch: var TGcHeap) {.inline.} =
|
||||
if isMultiThreaded:
|
||||
Lock(gch.zctLock)
|
||||
lock(gch.cycleRootsLock)
|
||||
when hasThreadSupport:
|
||||
if isMultiThreaded:
|
||||
Lock(gch.zctLock)
|
||||
lock(gch.cycleRootsLock)
|
||||
|
||||
proc unlock(gch: var TGcHeap) {.inline.} =
|
||||
if isMultiThreaded:
|
||||
unlock(gch.zctLock)
|
||||
unlock(gch.cycleRootsLock)
|
||||
when hasThreadSupport:
|
||||
if isMultiThreaded:
|
||||
unlock(gch.zctLock)
|
||||
unlock(gch.cycleRootsLock)
|
||||
|
||||
proc addZCT(s: var TCellSeq, c: PCell) {.noinline.} =
|
||||
if (c.refcount and rcZct) == 0:
|
||||
@@ -202,15 +204,19 @@ proc prepareDealloc(cell: PCell) =
|
||||
|
||||
proc rtlAddCycleRoot(c: PCell) {.rtl, inl.} =
|
||||
# we MUST access gch as a global here, because this crosses DLL boundaries!
|
||||
if isMultiThreaded: Lock(gch.cycleRootsLock)
|
||||
when hasThreadSupport:
|
||||
if isMultiThreaded: Lock(gch.cycleRootsLock)
|
||||
incl(gch.cycleRoots, c)
|
||||
if isMultiThreaded: Unlock(gch.cycleRootsLock)
|
||||
when hasThreadSupport:
|
||||
if isMultiThreaded: Unlock(gch.cycleRootsLock)
|
||||
|
||||
proc rtlAddZCT(c: PCell) {.rtl, inl.} =
|
||||
# we MUST access gch as a global here, because this crosses DLL boundaries!
|
||||
if isMultiThreaded: Lock(gch.zctLock)
|
||||
when hasThreadSupport:
|
||||
if isMultiThreaded: Lock(gch.zctLock)
|
||||
addZCT(gch.zct, c)
|
||||
if isMultiThreaded: Unlock(gch.zctLock)
|
||||
when hasThreadSupport:
|
||||
if isMultiThreaded: Unlock(gch.zctLock)
|
||||
|
||||
proc decRef(c: PCell) {.inline.} =
|
||||
when stressGC:
|
||||
@@ -480,7 +486,7 @@ proc gcMark(p: pointer) {.inline.} =
|
||||
add(gch.decStack, cell)
|
||||
|
||||
proc markThreadStacks(gch: var TGcHeap) =
|
||||
when isMultiThreaded:
|
||||
when hasThreadSupport:
|
||||
nil
|
||||
|
||||
# ----------------- stack management --------------------------------------
|
||||
|
||||
@@ -7,12 +7,17 @@
|
||||
# distribution, for details about the copyright.
|
||||
#
|
||||
|
||||
when defined(gcc) or defined(llvm_gcc):
|
||||
const
|
||||
hasThreadSupport = false # deactivate for now: thread stack walking
|
||||
# is missing!
|
||||
maxThreads = 256
|
||||
|
||||
when (defined(gcc) or defined(llvm_gcc)) and hasThreadSupport:
|
||||
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):
|
||||
elif defined(vcc) and hasThreadSupport:
|
||||
proc sync_add_and_fetch(p: var int, val: int): int {.
|
||||
importc: "NimXadd", nodecl.}
|
||||
else:
|
||||
@@ -20,19 +25,18 @@ else:
|
||||
inc(p, val)
|
||||
result = p
|
||||
|
||||
const
|
||||
isMultiThreaded* = true
|
||||
maxThreads = 256
|
||||
var
|
||||
isMultiThreaded: bool # true when prog created at least 1 thread
|
||||
|
||||
proc atomicInc(memLoc: var int, x: int): int =
|
||||
when isMultiThreaded:
|
||||
when hasThreadSupport:
|
||||
result = sync_add_and_fetch(memLoc, x)
|
||||
else:
|
||||
inc(memLoc, x)
|
||||
result = memLoc
|
||||
|
||||
proc atomicDec(memLoc: var int, x: int): int =
|
||||
when isMultiThreaded:
|
||||
when hasThreadSupport:
|
||||
when defined(sync_sub_and_fetch):
|
||||
result = sync_sub_and_fetch(memLoc, x)
|
||||
else:
|
||||
@@ -85,11 +89,8 @@ type
|
||||
TThreadFunc* = proc (closure: pointer) {.cdecl.}
|
||||
|
||||
proc createThread*(t: var TThread, fn: TThreadFunc) =
|
||||
|
||||
nil
|
||||
|
||||
proc destroyThread*(t: var TThread) =
|
||||
nil
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -12,9 +12,9 @@
|
||||
# code!**
|
||||
|
||||
import
|
||||
ast, astalgo, strutils, nhashes, trees, platform, magicsys, extccomp, options,
|
||||
nversion, nimsets, msgs, crc, bitsets, idents, lists, types, os, times, ropes,
|
||||
math, passes, ccgutils, wordrecg, rnimsyn, rodread
|
||||
ast, astalgo, strutils, nhashes, trees, platform, magicsys, extccomp,
|
||||
options, nversion, nimsets, msgs, crc, bitsets, idents, lists, types, os,
|
||||
times, ropes, math, passes, ccgutils, wordrecg, rnimsyn, rodread
|
||||
|
||||
proc ecmasgenPass*(): TPass
|
||||
# implementation
|
||||
@@ -39,7 +39,8 @@ type
|
||||
kind*: TEcmasTypeKind
|
||||
com*: PRope # computation part
|
||||
# address if this is a (address, index)-tuple
|
||||
res*: PRope # result part; index if this is a (address, index)-tuple
|
||||
res*: PRope # result part; index if this is an
|
||||
# (address, index)-tuple
|
||||
|
||||
TBlock{.final.} = object
|
||||
id*: int # the ID of the label; positive means that it
|
||||
@@ -886,12 +887,11 @@ proc genDeref(p: var TProc, n: PNode, r: var TCompRes) =
|
||||
if a.kind != etyBaseIndex: InternalError(n.info, "genDeref")
|
||||
r.res = ropef("$1[$2]", [a.com, a.res])
|
||||
|
||||
proc genCall(p: var TProc, n: PNode, r: var TCompRes) =
|
||||
var a: TCompRes
|
||||
gen(p, n.sons[0], r)
|
||||
proc genArgs(p: var TProc, n: PNode, r: var TCompRes) =
|
||||
app(r.res, "(")
|
||||
for i in countup(1, sonsLen(n) - 1):
|
||||
if i > 1: app(r.res, ", ")
|
||||
var a: TCompRes
|
||||
gen(p, n.sons[i], a)
|
||||
if a.kind == etyBaseIndex:
|
||||
app(r.res, a.com)
|
||||
@@ -901,6 +901,14 @@ proc genCall(p: var TProc, n: PNode, r: var TCompRes) =
|
||||
app(r.res, mergeExpr(a))
|
||||
app(r.res, ")")
|
||||
|
||||
proc genCall(p: var TProc, n: PNode, r: var TCompRes) =
|
||||
gen(p, n.sons[0], r)
|
||||
genArgs(p, n, r)
|
||||
|
||||
proc genEcho(p: var TProc, n: PNode, r: var TCompRes) =
|
||||
app(r.res, "rawEcho")
|
||||
genArgs(p, n, r)
|
||||
|
||||
proc putToSeq(s: string, indirect: bool): PRope =
|
||||
result = toRope(s)
|
||||
if indirect: result = ropef("[$1]", [result])
|
||||
@@ -1124,6 +1132,8 @@ proc genMagic(p: var TProc, n: PNode, r: var TCompRes) =
|
||||
of mInSet: binaryExpr(p, n, r, "", "($1[$2] != undefined)")
|
||||
of mNLen..mNError:
|
||||
liMessage(n.info, errCannotGenerateCodeForX, n.sons[0].sym.name.s)
|
||||
of mNewSeq: binaryStmt(p, n, r, "", "$1 = new Array($2)")
|
||||
of mEcho: genEcho(p, n, r)
|
||||
else:
|
||||
genCall(p, n, r)
|
||||
#else internalError(e.info, 'genMagic: ' + magicToStr[op]);
|
||||
@@ -1389,7 +1399,7 @@ proc newModule(module: PSym, filename: string): BModule =
|
||||
|
||||
proc genHeader(): PRope =
|
||||
result = ropef("/* Generated by the Nimrod Compiler v$1 */$n" &
|
||||
"/* (c) 2008 Andreas Rumpf */$n$n" & "$nvar Globals = this;$n" &
|
||||
"/* (c) 2010 Andreas Rumpf */$n$n" & "$nvar Globals = this;$n" &
|
||||
"var framePtr = null;$n" & "var excHandler = null;$n",
|
||||
[toRope(versionAsString)])
|
||||
|
||||
|
||||
@@ -203,7 +203,7 @@ proc MainCommand(cmd, filename: string) =
|
||||
gCmd = cmdCompileToCpp
|
||||
wantFile(filename)
|
||||
CommandCompileToC(filename)
|
||||
of wCompileToEcmaScript:
|
||||
of wCompileToEcmaScript, wJs:
|
||||
gCmd = cmdCompileToEcmaScript
|
||||
wantFile(filename)
|
||||
CommandCompileToEcmaScript(filename)
|
||||
|
||||
@@ -55,7 +55,7 @@ type
|
||||
wCc, wGenscript, wCheckPoint, wCheckPoints, wNoMain, wSubsChar,
|
||||
wAcyclic, wIndex,
|
||||
wCompileToC, wCompileToCpp, wCompileToEcmaScript, wCompileToLLVM, wPretty,
|
||||
wDoc, wGenDepend, wListDef, wCheck, wParse, wScan, wLazy,
|
||||
wDoc, wGenDepend, wListDef, wCheck, wParse, wScan, wJs,
|
||||
wRst2html, wRst2tex, wI,
|
||||
wWrite, wPutEnv, wPrependEnv, wAppendEnv, wThreadVar
|
||||
|
||||
@@ -103,7 +103,7 @@ const
|
||||
"nomain", "subschar", "acyclic", "index",
|
||||
"compiletoc", "compiletocpp", "compiletoecmascript", "compiletollvm",
|
||||
"pretty", "doc", "gendepend", "listdef", "check", "parse", "scan",
|
||||
"lazy", "rst2html", "rst2tex", "i",
|
||||
"js", "rst2html", "rst2tex", "i",
|
||||
"write", "putenv", "prependenv", "appendenv", "threadvar"]
|
||||
|
||||
proc whichKeyword*(id: PIdent): TSpecialWord
|
||||
|
||||
@@ -2,18 +2,18 @@
|
||||
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
|
||||
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||
<!-- This has been written by hand. (c) 2008 Andreas Rumpf -->
|
||||
<!-- This has been written by hand. (c) 2010 Andreas Rumpf -->
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||
<title>Nimrod ECMAScript Generator Test</title>
|
||||
<style type="text/css">
|
||||
span.DecNumber {color: blue}
|
||||
</style>
|
||||
<script src="nimrcache/ecmas.js" type="text/javascript"></script>
|
||||
<script src="nimcache/ecmas.js" type="text/javascript"></script>
|
||||
</head>
|
||||
<body onload="OnLoad()">
|
||||
<form name="form1" action="ecmas.html">
|
||||
<input type="text" name="input" size="3" />
|
||||
<input type="text" name="input1" size="10" />
|
||||
<input type="button" value="Calculate square" onclick="OnButtonClick()" />
|
||||
</form>
|
||||
|
||||
|
||||
@@ -6,11 +6,14 @@ import
|
||||
# We need to declare the used elements here. This is annoying but
|
||||
# prevents any kind of typo:
|
||||
var
|
||||
inputElement {.importc: "document.form1.input", nodecl.}: ref TElement
|
||||
inputElement {.importc: "document.form1.input1", nodecl.}: ref TElement
|
||||
|
||||
proc OnButtonClick() {.exportc.} =
|
||||
var x: int = parseInt($inputElement.value)
|
||||
echo($(x * x))
|
||||
#var x = parseInt($inputElement.value)
|
||||
#echo($(x * x))
|
||||
var input = $inputElement.value
|
||||
echo "Test"
|
||||
echo "Hi, ", input
|
||||
|
||||
proc OnLoad() {.exportc.} =
|
||||
echo("Welcome! Please take your time to fill in this formular!")
|
||||
echo "Welcome! Please take your time to fill in this formular!"
|
||||
|
||||
@@ -808,11 +808,11 @@ void error1(TCCState *s1, int is_warning, const char *fmt, va_list ap)
|
||||
if (!s1->error_func) {
|
||||
/* default case: stderr */
|
||||
fprintf(stderr, "%s\n", buf);
|
||||
} else {
|
||||
}
|
||||
if (!is_warning || s1->warn_error) {
|
||||
s1->error_func(s1->error_opaque, buf);
|
||||
}
|
||||
if (!is_warning || s1->warn_error)
|
||||
s1->nb_errors++;
|
||||
}
|
||||
}
|
||||
|
||||
void tcc_set_error_func(TCCState *s, void *error_opaque,
|
||||
|
||||
2
todo.txt
2
todo.txt
@@ -3,6 +3,8 @@ For version 0.8.10
|
||||
|
||||
- fix implicit generic routines
|
||||
- bugfix: ccgexprs
|
||||
- bugfix: make ``finally`` more robust
|
||||
- bugfix: tiny C broken again!
|
||||
|
||||
|
||||
High priority (version 0.9.0)
|
||||
|
||||
@@ -7,17 +7,38 @@
|
||||
# distribution, for details about the copyright.
|
||||
#
|
||||
|
||||
import glib2, gtk2, gdk2, osproc, dialogs, strutils
|
||||
import glib2, gtk2, gdk2, os, osproc, dialogs, strutils
|
||||
|
||||
when defined(tinyc):
|
||||
const runCmd = "run"
|
||||
else:
|
||||
const runCmd = "c -r"
|
||||
|
||||
when not defined(findExe):
|
||||
# candidate for the stdlib:
|
||||
proc findExe(exe: string): string =
|
||||
## returns exe if the exe cannot be found
|
||||
result = addFileExt(exe, os.exeExt)
|
||||
if ExistsFile(result): return
|
||||
var path = os.getEnv("PATH")
|
||||
for candidate in split(path, pathSep):
|
||||
var x = candidate / result
|
||||
if ExistsFile(x): return x
|
||||
result = ""
|
||||
|
||||
var nimExe = findExe("nimrod")
|
||||
if nimExe.len == 0: nimExe = "../bin" / addFileExt("nimrod", os.exeExt)
|
||||
|
||||
proc execCode(code: string): string =
|
||||
var f: TFile
|
||||
if open(f, "temp.nim", fmWrite):
|
||||
f.write(code)
|
||||
f.close()
|
||||
result = osproc.execProcess(
|
||||
"$# $# --verbosity:0 --hint[Conf]:off temp.nim" % [nimExe, runCmd],
|
||||
{poStdErrToStdOut})
|
||||
else:
|
||||
raise newException(EIO, "Unable to open file")
|
||||
result = osproc.execProcess(
|
||||
"nimrod c -r --verbosity:0 --hint[Conf]:off temp.nim")
|
||||
result = "cannot open file 'temp.nim'"
|
||||
|
||||
var shiftPressed = False
|
||||
var w: gtk2.PWindow
|
||||
@@ -29,33 +50,29 @@ proc destroy(widget: PWidget, data: pgpointer){.cdecl.} =
|
||||
|
||||
proc FileOpenClicked(menuitem: PMenuItem, userdata: pgpointer) {.cdecl.} =
|
||||
var path = ChooseFileToOpen(w)
|
||||
|
||||
if path != "":
|
||||
|
||||
var file: string = readFile(path)
|
||||
if file != nil:
|
||||
set_text(InputTextBuffer, file, len(file))
|
||||
|
||||
else:
|
||||
error(w, "Unable to read from file")
|
||||
|
||||
proc FileSaveClicked(menuitem: PMenuItem, userdata: pgpointer) {.cdecl.} =
|
||||
var path = ChooseFileToSave(w)
|
||||
|
||||
if path != "":
|
||||
var startIter: TTextIter
|
||||
var endIter: TTextIter
|
||||
get_start_iter(InputTextBuffer, addr(startIter))
|
||||
get_end_iter(InputTextBuffer, addr(endIter))
|
||||
var InputText = get_text(InputTextBuffer, addr(startIter),
|
||||
addr(endIter), False)
|
||||
var f: TFile
|
||||
if open(f, path, fmWrite):
|
||||
f.write(InputText)
|
||||
f.close()
|
||||
else:
|
||||
error(w, "Unable to write to file")
|
||||
|
||||
if path == "": return
|
||||
var startIter: TTextIter
|
||||
var endIter: TTextIter
|
||||
get_start_iter(InputTextBuffer, addr(startIter))
|
||||
get_end_iter(InputTextBuffer, addr(endIter))
|
||||
var InputText = get_text(InputTextBuffer, addr(startIter),
|
||||
addr(endIter), False)
|
||||
var f: TFile
|
||||
if open(f, path, fmWrite):
|
||||
f.write(InputText)
|
||||
f.close()
|
||||
else:
|
||||
error(w, "Unable to write to file")
|
||||
|
||||
proc inputKeyPressed(widget: PWidget, event: PEventKey,
|
||||
userdata: pgpointer): bool =
|
||||
@@ -68,13 +85,13 @@ proc setError(msg: string) =
|
||||
|
||||
proc inputKeyReleased(widget: PWidget, event: PEventKey,
|
||||
userdata: pgpointer): bool =
|
||||
echo(keyval_name(event.keyval))
|
||||
#echo(keyval_name(event.keyval))
|
||||
if ($keyval_name(event.keyval)).tolower() == "shift_l":
|
||||
# SHIFT is released
|
||||
shiftPressed = False
|
||||
|
||||
if ($keyval_name(event.keyval)).tolower() == "return":
|
||||
echo($keyval_name(event.keyval), "Shift_L")
|
||||
#echo($keyval_name(event.keyval), "Shift_L")
|
||||
# Enter pressed
|
||||
if shiftPressed == False:
|
||||
var startIter: TTextIter
|
||||
|
||||
Reference in New Issue
Block a user