summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--compiler/ccgexprs.nim2
-rw-r--r--compiler/transf.nim2
-rw-r--r--compiler/vm.nim6
-rw-r--r--tests/types/tcast1.nim35
4 files changed, 44 insertions, 1 deletions
diff --git a/compiler/ccgexprs.nim b/compiler/ccgexprs.nim
index 9c683a071..e1561ae12 100644
--- a/compiler/ccgexprs.nim
+++ b/compiler/ccgexprs.nim
@@ -1941,6 +1941,8 @@ proc genSomeCast(p: BProc, e: PNode, d: var TLoc) =
     elif optSeqDestructors in p.config.globalOptions and etyp.kind in {tySequence, tyString}:
       putIntoDest(p, d, e, "(*($1*) (&$2))" %
           [getTypeDesc(p.module, e.typ), rdCharLoc(a)], a.storage)
+    elif etyp.kind == tyBool and srcTyp.kind in IntegralTypes:
+      putIntoDest(p, d, e, "(($1) != 0)" % [rdCharLoc(a)], a.storage)
     else:
       putIntoDest(p, d, e, "(($1) ($2))" %
           [getTypeDesc(p.module, e.typ), rdCharLoc(a)], a.storage)
diff --git a/compiler/transf.nim b/compiler/transf.nim
index c1af6c23f..18d9b9130 100644
--- a/compiler/transf.nim
+++ b/compiler/transf.nim
@@ -462,7 +462,7 @@ proc transformConv(c: PTransf, n: PNode): PNode =
   var dest = skipTypes(n.typ, abstractVarRange)
   var source = skipTypes(n[1].typ, abstractVarRange)
   case dest.kind
-  of tyInt..tyInt64, tyEnum, tyChar, tyBool, tyUInt8..tyUInt32:
+  of tyInt..tyInt64, tyEnum, tyChar, tyUInt8..tyUInt32:
     # we don't include uint and uint64 here as these are no ordinal types ;-)
     if not isOrdinalType(source):
       # float -> int conversions. ugh.
diff --git a/compiler/vm.nim b/compiler/vm.nim
index 6a12b615e..8e05c5618 100644
--- a/compiler/vm.nim
+++ b/compiler/vm.nim
@@ -463,6 +463,12 @@ proc opConv(c: PCtx; dest: var TFullReg, src: TFullReg, desttyp, srctyp: PType):
         value = (value shl srcDist) shr srcDist
         value = (value shl destDist) shr destDist
         dest.intVal = cast[BiggestInt](value)
+    of tyBool:
+      dest.ensureKind(rkInt)
+      dest.intVal = 
+        case skipTypes(srctyp, abstractRange).kind
+          of tyFloat..tyFloat64: int(src.floatVal != 0.0)
+          else: int(src.intVal != 0)
     of tyFloat..tyFloat64:
       dest.ensureKind(rkFloat)
       case skipTypes(srctyp, abstractRange).kind
diff --git a/tests/types/tcast1.nim b/tests/types/tcast1.nim
index 10e876ded..04596baff 100644
--- a/tests/types/tcast1.nim
+++ b/tests/types/tcast1.nim
@@ -19,3 +19,38 @@ proc remap2[T](s: seq[int], typ: typedesc[T]): seq[T] =
 
 echo remap1(@[1,2,3], float)
 echo remap2(@[1,2,3], float)
+
+
+#--------------------------------------------------------------------
+# conversion to bool, issue #13744
+proc test_conv_to_bool = 
+  var 
+    i0 = 0
+    i1 = 1
+    ih = high(uint)
+    il = low(int)
+
+    f0 = 0.0
+    f1 = 1.0
+    fh = Inf
+    fl = -Inf
+    f_nan = NaN
+
+  doAssert(bool(i0) == false)
+  doAssert(bool(i1) == true)
+  doAssert(bool(-i1) == true)
+  doAssert(bool(il) == true)
+  doAssert(bool(ih) == true)
+
+  doAssert(bool(f0) == false)
+  doAssert(bool(-f0) == false)
+  doAssert(bool(f1) == true)
+  doAssert(bool(-f1) == true)
+  doAssert(bool(fh) == true)
+  doAssert(bool(fl) == true)
+  doAssert(bool(fnan) == true) # NaN to bool gives true according to standard
+
+
+static:
+  test_conv_to_bool()
+test_conv_to_bool()
\ No newline at end of file