From ea196c3befe9fefe287e483164dbbdbac9a288ee Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:25:15 +0300
Subject: [PATCH 01/17] fix variable declarations outside block top
---
src/duk_hobject_props.c | 38 ++++++++++++++++++++++----------------
1 file changed, 22 insertions(+), 16 deletions(-)
diff --git a/src/duk_hobject_props.c b/src/duk_hobject_props.c
index 09ef01e8..5709a5b5 100644
--- a/src/duk_hobject_props.c
+++ b/src/duk_hobject_props.c
@@ -1984,6 +1984,8 @@ int duk_hobject_getprop(duk_hthread *thr, duk_tval *tv_obj, duk_tval *tv_key) {
if (duk__get_own_property_desc_raw(thr, h_target, key, arr_idx, &desc, 1 /*push_value*/)) {
duk_tval *tv_hook = duk_require_tval(ctx, -3); /* value from hook */
duk_tval *tv_targ = duk_require_tval(ctx, -1); /* value from target */
+ int datadesc_reject;
+ int accdesc_reject;
DUK_DDD(DUK_DDDPRINT("proxy 'get': target has matching property %!O, check for "
"conflicting property; tv_hook=%!T, tv_targ=%!T, desc.flags=0x%08x, "
@@ -1991,14 +1993,14 @@ int duk_hobject_getprop(duk_hthread *thr, duk_tval *tv_obj, duk_tval *tv_key) {
key, tv_hook, tv_targ, (int) desc.flags,
(void *) desc.get, (void *) desc.set));
- int datadesc_reject = !(desc.flags & DUK_PROPDESC_FLAG_ACCESSOR) &&
- !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE) &&
- !(desc.flags & DUK_PROPDESC_FLAG_WRITABLE) &&
- !duk_js_samevalue(tv_hook, tv_targ);
- int accdesc_reject = (desc.flags & DUK_PROPDESC_FLAG_ACCESSOR) &&
- !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE) &&
- (desc.get == NULL) &&
- !DUK_TVAL_IS_UNDEFINED(tv_hook);
+ datadesc_reject = !(desc.flags & DUK_PROPDESC_FLAG_ACCESSOR) &&
+ !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE) &&
+ !(desc.flags & DUK_PROPDESC_FLAG_WRITABLE) &&
+ !duk_js_samevalue(tv_hook, tv_targ);
+ accdesc_reject = (desc.flags & DUK_PROPDESC_FLAG_ACCESSOR) &&
+ !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE) &&
+ (desc.get == NULL) &&
+ !DUK_TVAL_IS_UNDEFINED(tv_hook);
if (datadesc_reject || accdesc_reject) {
DUK_ERROR(thr, DUK_ERR_TYPE_ERROR, "proxy get rejected");
}
@@ -2769,6 +2771,8 @@ int duk_hobject_putprop(duk_hthread *thr, duk_tval *tv_obj, duk_tval *tv_key, du
if (duk__get_own_property_desc_raw(thr, h_target, key, arr_idx, &desc, 1 /*push_value*/)) {
duk_tval *tv_targ = duk_require_tval(ctx, -1);
+ int datadesc_reject;
+ int accdesc_reject;
DUK_DDD(DUK_DDDPRINT("proxy 'set': target has matching property %!O, check for "
"conflicting property; tv_val=%!T, tv_targ=%!T, desc.flags=0x%08x, "
@@ -2776,13 +2780,13 @@ int duk_hobject_putprop(duk_hthread *thr, duk_tval *tv_obj, duk_tval *tv_key, du
key, tv_val, tv_targ, (int) desc.flags,
(void *) desc.get, (void *) desc.set));
- int datadesc_reject = !(desc.flags & DUK_PROPDESC_FLAG_ACCESSOR) &&
- !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE) &&
- !(desc.flags & DUK_PROPDESC_FLAG_WRITABLE) &&
- !duk_js_samevalue(tv_val, tv_targ);
- int accdesc_reject = (desc.flags & DUK_PROPDESC_FLAG_ACCESSOR) &&
- !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE) &&
- (desc.set == NULL);
+ datadesc_reject = !(desc.flags & DUK_PROPDESC_FLAG_ACCESSOR) &&
+ !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE) &&
+ !(desc.flags & DUK_PROPDESC_FLAG_WRITABLE) &&
+ !duk_js_samevalue(tv_val, tv_targ);
+ accdesc_reject = (desc.flags & DUK_PROPDESC_FLAG_ACCESSOR) &&
+ !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE) &&
+ (desc.set == NULL);
if (datadesc_reject || accdesc_reject) {
DUK_ERROR(thr, DUK_ERR_TYPE_ERROR, "proxy set rejected");
}
@@ -3606,12 +3610,14 @@ int duk_hobject_delprop(duk_hthread *thr, duk_tval *tv_obj, duk_tval *tv_key, in
DUK_ASSERT(key != NULL);
if (duk__get_own_property_desc_raw(thr, h_target, key, arr_idx, &desc, 0 /*push_value*/)) {
+ int desc_reject;
+
DUK_DDD(DUK_DDDPRINT("proxy 'deleteProperty': target has matching property %!O, check for "
"conflicting property; desc.flags=0x%08x, "
"desc.get=%p, desc.set=%p",
key, (int) desc.flags, (void *) desc.get, (void *) desc.set));
- int desc_reject = !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE);
+ desc_reject = !(desc.flags & DUK_PROPDESC_FLAG_CONFIGURABLE);
if (desc_reject) {
/* unconditional */
DUK_ERROR(thr, DUK_ERR_TYPE_ERROR, "proxy deleteProperty rejected");
From 9d85ee153613b9d2c6aceb387688317375208afd Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:25:27 +0300
Subject: [PATCH 02/17] add missing duk_internal.h include
---
src/duk_replacements.c | 2 ++
1 file changed, 2 insertions(+)
diff --git a/src/duk_replacements.c b/src/duk_replacements.c
index 97eff8d9..fce1868e 100644
--- a/src/duk_replacements.c
+++ b/src/duk_replacements.c
@@ -6,6 +6,8 @@
* mimics the standard prototypes.
*/
+#include "duk_internal.h"
+
#ifdef DUK_USE_COMPUTED_NAN
double duk_computed_nan;
#endif
From 922b832859f011be78d1138629d33dbf2fa61298 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:26:17 +0300
Subject: [PATCH 03/17] bcc detection
---
src/duk_features.h.in | 10 +++++++++-
1 file changed, 9 insertions(+), 1 deletion(-)
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index d9a540ee..fdb8e6ef 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -244,6 +244,11 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#define DUK_F_MINGW
#endif
+/* BCC (Bruce's C compiler): this is a "torture target" for compilation */
+#if defined(__BCC__) || defined(__BCC_VERSION__)
+#define DUK_F_BCC
+#endif
+
/*
* Platform detection, system includes, Date provider selection.
*
@@ -484,8 +489,11 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#error cannot check complement of two
#endif
-/* Pointer size determination based on architecture. */
+/* Pointer size determination based on architecture.
+ * XXX: unsure about BCC correctness.
+ */
#if defined(DUK_F_X86) || defined(DUK_F_X32) || \
+ defined(DUK_F_BCC) || \
(defined(__WORDSIZE) && (__WORDSIZE == 32))
#define DUK_F_32BIT_PTRS
#elif defined(DUK_F_X64) || \
From 70d1cb2bf1b1b14dae7d72993974a8a701d0ded1 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:38:26 +0300
Subject: [PATCH 04/17] avoid endian.h and stdint.h with BCC, force byteorder
and align with BCC
---
src/duk_features.h.in | 22 ++++++++++++++++++----
1 file changed, 18 insertions(+), 4 deletions(-)
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index fdb8e6ef..739e588c 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -394,7 +394,11 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#define DUK_USE_DATE_PRS_STRPTIME
#define DUK_USE_DATE_FMT_STRFTIME
#include
+#if defined(DUK_F_BCC)
+/* no endian.h */
+#else
#include
+#endif /* DUK_F_BCC */
#include
#include
#include
@@ -418,7 +422,11 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#define DUK_USE_DATE_PRS_STRPTIME
#define DUK_USE_DATE_FMT_STRFTIME
#include
+#if defined(DUK_F_BCC)
+/* no endian.h */
+#else
#include
+#endif /* DUK_F_BCC */
#include
#include
#include
@@ -432,10 +440,10 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#include /* varargs */
#include
#include /* e.g. ptrdiff_t */
-#ifdef DUK_F_TOS
-/*FIXME*/
+#if defined(DUK_F_TOS) || defined(DUK_F_BCC)
+/* stdint.h not available */
#else
-/* XXX: technically C99 (C++11) but found in many systems */
+/* technically C99 (C++11) but found in many systems */
#include
#endif
#include
@@ -869,7 +877,8 @@ typedef double duk_double_t;
#define DUK_USE_ALIGN_4
#elif defined(DUK_F_MIPS)
#define DUK_USE_ALIGN_4
-#elif defined(DUK_F_X86) || defined(DUK_F_X32) || defined(DUK_F_X64)
+#elif defined(DUK_F_X86) || defined(DUK_F_X32) || defined(DUK_F_X64) || \
+ defined(DUK_F_BCC)
#define DUK_USE_UNALIGNED_ACCESSES_POSSIBLE
#else
/* unknown, use safe default */
@@ -1110,6 +1119,11 @@ typedef double duk_double_t;
#endif
#endif
+/* Bruce's C Compiler (BCC), assume we're on x86. */
+#if !defined(DUK_F_BYTEORDER) && defined(DUK_F_BCC)
+#define DUK_F_BYTEORDER 1
+#endif
+
/* Check whether or not byte order detection worked based on the intermediate
* define, and define final values. If detection failed, #error out.
*/
From dd7552613282ced8a96af14203b68e66c8cbb63b Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:39:05 +0300
Subject: [PATCH 05/17] invert DUK_F_HAVE_64BIT determination to allow better
if-else ladder
---
src/duk_features.h.in | 6 ++++--
1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index 739e588c..9fdd5abf 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -661,20 +661,22 @@ typedef signed long duk_int32_t;
#error cannot detect 32-bit type
#endif
-#define DUK_F_HAVE_64BIT
+#undef DUK_F_HAVE_64BIT
#if defined(ULONG_MAX) && (ULONG_MAX == 18446744073709551615ULL)
+#define DUK_F_HAVE_64BIT
typedef unsigned long duk_uint64_t;
typedef signed long duk_int64_t;
#elif defined(ULLONG_MAX) && (ULLONG_MAX == 18446744073709551615ULL)
+#define DUK_F_HAVE_64BIT
typedef unsigned long long duk_uint64_t;
typedef signed long long duk_int64_t;
#elif defined(DUK_F_MINGW) || defined(DUK_F_MSVC)
/* Both MinGW and MSVC have a 64-bit type. */
+#define DUK_F_HAVE_64BIT
typedef unsigned long duk_uint64_t;
typedef signed long duk_int64_t;
#else
/* cannot detect 64-bit type, not always needed so don't error */
-#undef DUK_F_HAVE_64BIT
#endif
typedef duk_uint8_t duk_uint_least8_t;
From 337f65bf1c8a122e41209e0575877141fc8ea59e Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:42:36 +0300
Subject: [PATCH 06/17] hide ULL constants from the preprocessor if they are
not supported (as with BCC)
---
src/duk_features.h.in | 12 ++++++++++++
1 file changed, 12 insertions(+)
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index 9fdd5abf..c4d29257 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -249,6 +249,14 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#define DUK_F_BCC
#endif
+#if defined(DUK_F_BCC)
+/* preprocessor does not understand ULL constants (12345ULL) so we can't
+ * evaluate any expressions with them (e.g. BCC).
+ */
+#else
+#define DUK_F_ULL_CONSTS
+#endif
+
/*
* Platform detection, system includes, Date provider selection.
*
@@ -662,6 +670,7 @@ typedef signed long duk_int32_t;
#endif
#undef DUK_F_HAVE_64BIT
+#if defined(DUK_F_ULL_CONSTS)
#if defined(ULONG_MAX) && (ULONG_MAX == 18446744073709551615ULL)
#define DUK_F_HAVE_64BIT
typedef unsigned long duk_uint64_t;
@@ -678,6 +687,7 @@ typedef signed long duk_int64_t;
#else
/* cannot detect 64-bit type, not always needed so don't error */
#endif
+#endif /* DUK_F_ULL_CONSTS */
typedef duk_uint8_t duk_uint_least8_t;
typedef duk_int8_t duk_int_least8_t;
@@ -745,6 +755,7 @@ typedef duk_int32_t duk_intmax_t;
#define DUK_UINT_FAST32_MAX 0xffffffffUL
#define DUK_INT_FAST32_MIN (-0x80000000L)
#define DUK_INT_FAST32_MAX 0x7fffffffL
+#if defined(DUK_F_HAVE_64BIT)
#define DUK_UINT64_MIN 0ULL
#define DUK_UINT64_MAX 0xffffffffffffffffULL
#define DUK_INT64_MIN (-0x8000000000000000LL)
@@ -757,6 +768,7 @@ typedef duk_int32_t duk_intmax_t;
#define DUK_UINT_FAST64_MAX 0xffffffffffffffffULL
#define DUK_INT_FAST64_MIN (-0x8000000000000000LL)
#define DUK_INT_FAST64_MAX 0x7fffffffffffffffULL
+#endif
#define DUK_UINTPTR_MIN 0UL
#define DUK_UINTPTR_MAX 0xffffffffUL
#define DUK_INTPTR_MIN (-0x80000000L)
From 03b0d33bff9bc2649512bb64fb2fc9fd8e7e97a2 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:45:08 +0300
Subject: [PATCH 07/17] fix duk_intmax_t, duk_uintmax_t: duplicate definition,
did not take 64-bit type availability into account for non-C99 build
---
src/duk_features.h.in | 9 +++++----
1 file changed, 5 insertions(+), 4 deletions(-)
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index c4d29257..c22c75bd 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -701,8 +701,13 @@ typedef duk_uint16_t duk_uint_fast16_t;
typedef duk_int16_t duk_int_fast16_t;
typedef duk_uint32_t duk_uint_fast32_t;
typedef duk_int32_t duk_int_fast32_t;
+#if defined(DUK_F_HAVE_64BIT)
+typedef duk_int64_t duk_intmax_t;
+typedef duk_uint64_t duk_uintmax_t;
+#else
typedef duk_int32_t duk_intmax_t;
typedef duk_uint32_t duk_uintmax_t;
+#endif
/* This detection is not very reliable. */
#if defined(DUK_F_32BIT_PTRS)
@@ -715,10 +720,6 @@ typedef duk_uint64_t duk_uintptr_t;
#error cannot determine intptr type
#endif
-/* Pretend that maximum int is 32 bits. */
-typedef duk_uint32_t duk_uintmax_t;
-typedef duk_int32_t duk_intmax_t;
-
#define DUK_UINT8_MIN 0UL
#define DUK_UINT8_MAX 0xffUL
#define DUK_INT8_MIN (-0x80L)
From 1d215dc089789e9addbbbab3a69e279c490b961c Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:47:03 +0300
Subject: [PATCH 08/17] use computed nan/infinity on bcc
---
src/duk_features.h.in | 8 ++++++--
1 file changed, 6 insertions(+), 2 deletions(-)
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index c22c75bd..ebac0612 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -249,6 +249,10 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#define DUK_F_BCC
#endif
+#if defined(__VBCC_)
+#define DUK_F_VBCC
+#endif
+
#if defined(DUK_F_BCC)
/* preprocessor does not understand ULL constants (12345ULL) so we can't
* evaluate any expressions with them (e.g. BCC).
@@ -1211,7 +1215,7 @@ typedef double duk_double_t;
#define DUK_DOUBLE_INFINITY (__builtin_inf())
#elif defined(INFINITY)
#define DUK_DOUBLE_INFINITY ((double) INFINITY)
-#elif !defined(__VBCC__) && !defined(_MSC_VER)
+#elif !defined(__VBCC__) && !defined(DUK_F_MSVC) && !defined(DUK_F_BCC)
#define DUK_DOUBLE_INFINITY (1.0 / 0.0)
#else
/* In VBCC (1.0 / 0.0) results in a warning and 0.0 instead of infinity.
@@ -1226,7 +1230,7 @@ extern double duk_computed_infinity;
#undef DUK_USE_COMPUTED_NAN
#if defined(NAN)
#define DUK_DOUBLE_NAN NAN
-#elif !defined(__VBCC__) && !defined(_MSC_VER)
+#elif !defined(__VBCC__) && !defined(DUK_F_MSVC) && !defined(DUK_F_BCC)
#define DUK_DOUBLE_NAN (0.0 / 0.0)
#else
/* In VBCC (0.0 / 0.0) results in a warning and 0.0 instead of NaN.
From 63095c16604ee3b8c8c7de5cae7a8e8bc31d5844 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:48:52 +0300
Subject: [PATCH 09/17] fix DUK_F_VBCC detection, replace __VBCC__ with
DUK_F_VBCC, also some _MSC_VER to DUK_F_MSVC replacements
---
src/duk_features.h.in | 18 +++++++++---------
1 file changed, 9 insertions(+), 9 deletions(-)
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index ebac0612..854937a3 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -249,7 +249,7 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#define DUK_F_BCC
#endif
-#if defined(__VBCC_)
+#if defined(__VBCC__)
#define DUK_F_VBCC
#endif
@@ -526,7 +526,7 @@ static __inline__ unsigned long long duk_rdtsc(void) {
/* Intermediate define for 'have inttypes.h' */
#undef DUK_F_HAVE_INTTYPES
#if defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) && \
- !(defined(DUK_F_AMIGAOS) && defined(__VBCC__))
+ !(defined(DUK_F_AMIGAOS) && defined(DUK_F_VBCC))
/* vbcc + AmigaOS has C99 but no inttypes.h */
#define DUK_F_HAVE_INTTYPES
#elif defined(__cplusplus) && (__cplusplus >= 201103L)
@@ -869,7 +869,7 @@ typedef double duk_double_t;
* unless they are known to be unreliable. For instance, 64-bit types are
* available on VBCC but seem to misbehave.
*/
-#if defined(DUK_F_HAVE_64BIT) && !defined(__VBCC__)
+#if defined(DUK_F_HAVE_64BIT) && !defined(DUK_F_VBCC)
#define DUK_USE_64BIT_OPS
#else
#undef DUK_USE_64BIT_OPS
@@ -1215,7 +1215,7 @@ typedef double duk_double_t;
#define DUK_DOUBLE_INFINITY (__builtin_inf())
#elif defined(INFINITY)
#define DUK_DOUBLE_INFINITY ((double) INFINITY)
-#elif !defined(__VBCC__) && !defined(DUK_F_MSVC) && !defined(DUK_F_BCC)
+#elif !defined(DUK_F_VBCC) && !defined(DUK_F_MSVC) && !defined(DUK_F_BCC)
#define DUK_DOUBLE_INFINITY (1.0 / 0.0)
#else
/* In VBCC (1.0 / 0.0) results in a warning and 0.0 instead of infinity.
@@ -1230,7 +1230,7 @@ extern double duk_computed_infinity;
#undef DUK_USE_COMPUTED_NAN
#if defined(NAN)
#define DUK_DOUBLE_NAN NAN
-#elif !defined(__VBCC__) && !defined(DUK_F_MSVC) && !defined(DUK_F_BCC)
+#elif !defined(DUK_F_VBCC) && !defined(DUK_F_MSVC) && !defined(DUK_F_BCC)
#define DUK_DOUBLE_NAN (0.0 / 0.0)
#else
/* In VBCC (0.0 / 0.0) results in a warning and 0.0 instead of NaN.
@@ -1259,7 +1259,7 @@ extern double duk_computed_nan;
defined(FP_SUBNORMAL) && defined(FP_NORMAL))
/* missing some obvious constants */
#define DUK_F_USE_REPL_ALL
-#elif defined(DUK_F_AMIGAOS) && defined(__VBCC__)
+#elif defined(DUK_F_AMIGAOS) && defined(DUK_F_VBCC)
/* VBCC is missing the built-ins even in C99 mode (perhaps a header issue) */
#define DUK_F_USE_REPL_ALL
#elif defined(DUK_F_FREEBSD) && defined(DUK_F_CLANG)
@@ -1309,7 +1309,7 @@ extern double duk_computed_nan;
*/
#if defined(DUK_F_C99) && \
!defined(__UCLIBC__) /* uclibc may be missing these */ && \
- !(defined(DUK_F_AMIGAOS) && defined(__VBCC__)) /* vbcc + AmigaOS may be missing these */
+ !(defined(DUK_F_AMIGAOS) && defined(DUK_F_VBCC)) /* vbcc + AmigaOS may be missing these */
#define DUK_USE_MATH_FMIN
#define DUK_USE_MATH_FMAX
#define DUK_USE_MATH_ROUND
@@ -1496,7 +1496,7 @@ typedef FILE duk_file;
#elif defined(__clang__)
/* syntax same as gcc */
#define DUK_NORETURN(decl) decl __attribute__((noreturn))
-#elif defined(_MSC_VER)
+#elif defined(DUK_F_MSVC)
/* http://msdn.microsoft.com/en-us/library/aa235362(VS.60).aspx */
#define DUK_NORETURN(decl) __declspec(noreturn) decl
#else
@@ -1592,7 +1592,7 @@ typedef FILE duk_file;
#define DUK_LINE_MACRO __LINE__
-#if !defined(__VBCC__) && !defined(_MSC_VER)
+#if !defined(DUK_F_VBCC) && !defined(DUK_F_MSVC)
#define DUK_FUNC_MACRO __func__
#else
#define DUK_FUNC_MACRO "unknown"
From 8615b19ff89ab41cbfdbf162b452aafb941ef3c4 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 18:54:14 +0300
Subject: [PATCH 10/17] avoid auto initializers when variable is not static:
these are rejected by some old compilers like bcc
---
src/duk_api.c | 6 +++++-
src/duk_api_logging.c | 3 ++-
src/duk_bi_json.c | 3 ++-
3 files changed, 9 insertions(+), 3 deletions(-)
diff --git a/src/duk_api.c b/src/duk_api.c
index e945f52a..6f1ae7e3 100644
--- a/src/duk_api.c
+++ b/src/duk_api.c
@@ -1383,11 +1383,15 @@ static int duk__defaultvalue_coerce_attempt(duk_context *ctx, int index, int fun
void duk_to_defaultvalue(duk_context *ctx, int index, int hint) {
duk_hthread *thr = (duk_hthread *) ctx;
duk_hobject *obj;
- int coercers[] = { DUK_STRIDX_VALUE_OF, DUK_STRIDX_TO_STRING };
+ /* inline initializer for coercers[] is not allowed by old compilers like BCC */
+ int coercers[2];
DUK_ASSERT(ctx != NULL);
DUK_ASSERT(thr != NULL);
+ coercers[0] = DUK_STRIDX_VALUE_OF;
+ coercers[1] = DUK_STRIDX_TO_STRING;
+
index = duk_require_normalize_index(ctx, index);
if (!duk_is_object(ctx, index)) {
diff --git a/src/duk_api_logging.c b/src/duk_api_logging.c
index 5186cff5..02da2034 100644
--- a/src/duk_api_logging.c
+++ b/src/duk_api_logging.c
@@ -15,7 +15,8 @@ void duk_log(duk_context *ctx, int level, const char *fmt, ...) {
duk_hthread *thr = (duk_hthread *) ctx;
va_list ap;
char buf[DUK__LOGFMT_BUFSIZE];
- duk_uint16_t stridx_logfunc[6] = {
+ /* stridx_logfunc[] must be static to allow initializer with old compilers like BCC */
+ static const duk_uint16_t stridx_logfunc[6] = {
DUK_STRIDX_LC_TRACE, DUK_STRIDX_LC_DEBUG, DUK_STRIDX_LC_INFO,
DUK_STRIDX_LC_WARN, DUK_STRIDX_LC_ERROR, DUK_STRIDX_LC_FATAL
};
diff --git a/src/duk_bi_json.c b/src/duk_bi_json.c
index 0c4d1ca9..4b79fdcc 100644
--- a/src/duk_bi_json.c
+++ b/src/duk_bi_json.c
@@ -1860,7 +1860,8 @@ void duk_bi_json_stringify_helper(duk_context *ctx,
if (duk_is_number(ctx, idx_space)) {
double d;
int nspace;
- char spaces[10] = { ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ' }; /* FIXME:helper */
+ /* spaces[] must be static to allow initializer with old compilers like BCC */
+ static const char spaces[10] = { ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ' }; /* FIXME:helper */
/* ToInteger() coercion; NaN -> 0, infinities are clamped to 0 and 10 */
/* FIXME: get_clamped_int; double arithmetic is expensive */
From c889764db3ac9c3a7bc1f9f26971a3817422f9f8 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 19:00:35 +0300
Subject: [PATCH 11/17] add stubbed Math built-in for BCC torturing
---
src/duk_bi_math.c | 33 +++++++++++++++++++++++++++++++++
src/duk_features.h.in | 6 ++++++
2 files changed, 39 insertions(+)
diff --git a/src/duk_bi_math.c b/src/duk_bi_math.c
index c22cb349..7a5ed4b2 100644
--- a/src/duk_bi_math.c
+++ b/src/duk_bi_math.c
@@ -4,6 +4,8 @@
#include "duk_internal.h"
+#if defined(DUK_USE_MATH_BUILTIN)
+
/*
* Use static helpers which can work with math.h functions matching
* the following signatures. This is not portable if any of these math
@@ -248,3 +250,34 @@ duk_ret_t duk_bi_math_object_random(duk_context *ctx) {
duk_push_number(ctx, (duk_double_t) duk_util_tinyrandom_get_double((duk_hthread *) ctx));
return 1;
}
+
+#else /* DUK_USE_MATH_BUILTIN */
+
+/* A stubbed built-in is useful for e.g. compilation torture testing with BCC. */
+
+duk_ret_t duk_bi_math_object_onearg_shared(duk_context *ctx) {
+ DUK_UNREF(ctx);
+ return DUK_RET_UNIMPLEMENTED_ERROR;
+}
+
+duk_ret_t duk_bi_math_object_twoarg_shared(duk_context *ctx) {
+ DUK_UNREF(ctx);
+ return DUK_RET_UNIMPLEMENTED_ERROR;
+}
+
+duk_ret_t duk_bi_math_object_max(duk_context *ctx) {
+ DUK_UNREF(ctx);
+ return DUK_RET_UNIMPLEMENTED_ERROR;
+}
+
+duk_ret_t duk_bi_math_object_min(duk_context *ctx) {
+ DUK_UNREF(ctx);
+ return DUK_RET_UNIMPLEMENTED_ERROR;
+}
+
+duk_ret_t duk_bi_math_object_random(duk_context *ctx) {
+ DUK_UNREF(ctx);
+ return DUK_RET_UNIMPLEMENTED_ERROR;
+}
+
+#endif /* DUK_USE_MATH_BUILTIN */
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index 854937a3..1fe89707 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -1779,6 +1779,12 @@ typedef FILE duk_file;
* Ecmascript features / compliance options
*/
+#if defined(DUK_F_BCC)
+/* Math built-in is stubbed out on BCC to allow compiler torture testing. */
+#else
+#define DUK_USE_MATH_BUILTIN
+#endif
+
#define DUK_USE_REGEXP_SUPPORT
#if defined(DUK_OPT_NO_REGEXP_SUPPORT)
#undef DUK_USE_REGEXP_SUPPORT
From 69bd47dfd3f866d30ede92feb0995984634d2dd0 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 19:01:49 +0300
Subject: [PATCH 12/17] don't do function pointer casting in initializers, it
breaks bcc compilation
---
src/genbuiltins.py | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/src/genbuiltins.py b/src/genbuiltins.py
index 8de9107a..c03a8c83 100644
--- a/src/genbuiltins.py
+++ b/src/genbuiltins.py
@@ -1443,7 +1443,10 @@ class GenBuiltins:
genc.emitLine('/* native functions: %d */' % len(self.native_func_list))
genc.emitLine('const duk_c_function duk_bi_native_functions[] = {')
for i in self.native_func_list:
- genc.emitLine('\t(duk_c_function) %s,' % i)
+ # The function pointer cast here makes BCC complain about
+ # "initializer too complicated", so omit the cast.
+ #genc.emitLine('\t(duk_c_function) %s,' % i)
+ genc.emitLine('\t%s,' % i)
genc.emitLine('};')
def generateDefineNames(self, id):
From 7189f98a933d703c2b8ebe9f83dbcdedb26d84ed Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 19:02:27 +0300
Subject: [PATCH 13/17] comment inside assert macro breaks bcc build
---
src/duk_js_executor.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/duk_js_executor.c b/src/duk_js_executor.c
index f7cecbf8..d2c7131c 100644
--- a/src/duk_js_executor.c
+++ b/src/duk_js_executor.c
@@ -756,8 +756,8 @@ static int duk__handle_longjmp(duk_hthread *thr,
DUK_HOBJECT_IS_COMPILEDFUNCTION((resumee->callstack + resumee->callstack_top - 2)->func))); /* an Ecmascript function */
DUK_ASSERT(resumee->state != DUK_HTHREAD_STATE_YIELDED ||
(resumee->callstack + resumee->callstack_top - 2)->idx_retval >= 0); /* waiting for a value */
- DUK_ASSERT(resumee->state != DUK_HTHREAD_STATE_INACTIVE || /* INACTIVE: no activation, single function value on valstack */
- resumee->callstack_top == 0);
+ DUK_ASSERT(resumee->state != DUK_HTHREAD_STATE_INACTIVE ||
+ resumee->callstack_top == 0); /* INACTIVE: no activation, single function value on valstack */
DUK_ASSERT(resumee->state != DUK_HTHREAD_STATE_INACTIVE ||
(resumee->valstack_top == resumee->valstack + 1 &&
DUK_TVAL_IS_OBJECT(resumee->valstack_top - 1) &&
From 4455aaffd0307e1a082da6ad0a1cef4de19c233c Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 19:09:15 +0300
Subject: [PATCH 14/17] fix some preprocessor constants which were missing L
specifier
---
src/duk_features.h.in | 12 ++++++------
1 file changed, 6 insertions(+), 6 deletions(-)
diff --git a/src/duk_features.h.in b/src/duk_features.h.in
index 1fe89707..2e1e13d0 100644
--- a/src/duk_features.h.in
+++ b/src/duk_features.h.in
@@ -223,7 +223,7 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#define DUK_F_GCC
#if defined(__GNUC__) && defined(__GNUC_MINOR__) && defined(__GNUC_PATCHLEVEL__)
/* Convenience, e.g. gcc 4.5.1 == 40501; http://stackoverflow.com/questions/6031819/emulating-gccs-builtin-unreachable */
-#define DUK_F_GCC_VERSION (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__)
+#define DUK_F_GCC_VERSION (__GNUC__ * 10000L + __GNUC_MINOR__ * 100L + __GNUC_PATCHLEVEL__)
#else
#error cannot figure out gcc version
#endif
@@ -310,7 +310,7 @@ static __inline__ unsigned long long duk_rdtsc(void) {
#if defined(DUK_F_QNX) && defined(DUK_COMPILING_DUKTAPE)
/* See: /opt/qnx650/target/qnx6/usr/include/sys/platform.h */
#define _XOPEN_SOURCE 600
-#define _POSIX_C_SOURCE 200112
+#define _POSIX_C_SOURCE 200112L
#endif
#if defined(__APPLE__)
@@ -491,7 +491,7 @@ static __inline__ unsigned long long duk_rdtsc(void) {
* format characters need to be changed.
*/
#if defined(INT_MAX)
-#if INT_MAX < 2147483647
+#if INT_MAX < 2147483647L
#error INT_MAX too small, expected int to be 32 bits at least
#endif
#else
@@ -1490,7 +1490,7 @@ typedef FILE duk_file;
* http://clang.llvm.org/docs/LanguageExtensions.html
*/
-#if defined(DUK_F_GCC_VERSION) && (DUK_F_GCC_VERSION >= 20500)
+#if defined(DUK_F_GCC_VERSION) && (DUK_F_GCC_VERSION >= 20500L)
/* since gcc-2.5 */
#define DUK_NORETURN(decl) decl __attribute__((noreturn))
#elif defined(__clang__)
@@ -1514,7 +1514,7 @@ typedef FILE duk_file;
* http://clang.llvm.org/docs/LanguageExtensions.html
*/
-#if defined(DUK_F_GCC_VERSION) && (DUK_F_GCC_VERSION >= 40500)
+#if defined(DUK_F_GCC_VERSION) && (DUK_F_GCC_VERSION >= 40500L)
/* since gcc-4.5 */
#define DUK_UNREACHABLE() do { __builtin_unreachable(); } while(0)
#elif defined(__clang__) && defined(__has_builtin)
@@ -1563,7 +1563,7 @@ typedef FILE duk_file;
#endif
#if defined(DUK_USE_BRANCH_HINTS)
-#if defined(DUK_F_GCC_VERSION) && (DUK_F_GCC_VERISON >= 40500)
+#if defined(DUK_F_GCC_VERSION) && (DUK_F_GCC_VERISON >= 40500L)
/* GCC: test not very accurate; enable only in relatively recent builds
* because of bugs in gcc-4.4 (http://lists.debian.org/debian-gcc/2010/04/msg00000.html)
*/
From 7387fcda14a54ed628e225c94aa1a526123df94c Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 19:14:00 +0300
Subject: [PATCH 15/17] cast switch argument to duk_small_int_t to ensure it
fits into compiler 'int'; this was broken when compiler 'int' is 16 bits
---
src/duk_bi_duktape.c | 2 +-
src/duk_bi_string.c | 2 +-
src/duk_heap_alloc.c | 2 +-
src/duk_heap_markandsweep.c | 2 +-
src/duk_heap_refcount.c | 4 ++--
src/duk_js_executor.c | 2 +-
6 files changed, 7 insertions(+), 7 deletions(-)
diff --git a/src/duk_bi_duktape.c b/src/duk_bi_duktape.c
index ddb6bec7..5a123024 100644
--- a/src/duk_bi_duktape.c
+++ b/src/duk_bi_duktape.c
@@ -49,7 +49,7 @@ duk_ret_t duk_bi_duktape_object_info(duk_context *ctx) {
/* heaphdr size and additional allocation size, followed by
* type specific stuff (with varying value count)
*/
- switch (DUK_HEAPHDR_GET_TYPE(h)) {
+ switch ((duk_small_int_t) DUK_HEAPHDR_GET_TYPE(h)) {
case DUK_HTYPE_STRING: {
duk_hstring *h_str = (duk_hstring *) h;
duk_push_int(ctx, (int) (sizeof(duk_hstring) + DUK_HSTRING_GET_BYTELEN(h_str) + 1));
diff --git a/src/duk_bi_string.c b/src/duk_bi_string.c
index 961bf344..ba9ea080 100644
--- a/src/duk_bi_string.c
+++ b/src/duk_bi_string.c
@@ -655,7 +655,7 @@ duk_ret_t duk_bi_string_prototype_replace(duk_context *ctx) {
}
ch2 = r[0];
- switch (ch2) {
+ switch ((duk_small_int_t) ch2) {
case (duk_int_t) '$': {
ch1 = (1 << 8) + (duk_int_t) '$';
goto repl_write;
diff --git a/src/duk_heap_alloc.c b/src/duk_heap_alloc.c
index c5ebf1ee..1d90804f 100644
--- a/src/duk_heap_alloc.c
+++ b/src/duk_heap_alloc.c
@@ -69,7 +69,7 @@ void duk_heap_free_heaphdr_raw(duk_heap *heap, duk_heaphdr *hdr) {
DUK_DDD(DUK_DDDPRINT("free heaphdr %p, htype %d", (void *) hdr, (int) DUK_HEAPHDR_GET_TYPE(hdr)));
- switch (DUK_HEAPHDR_GET_TYPE(hdr)) {
+ switch ((duk_small_int_t) DUK_HEAPHDR_GET_TYPE(hdr)) {
case DUK_HTYPE_STRING:
/* no inner refs to free */
break;
diff --git a/src/duk_heap_markandsweep.c b/src/duk_heap_markandsweep.c
index ea3534b3..204e77ec 100644
--- a/src/duk_heap_markandsweep.c
+++ b/src/duk_heap_markandsweep.c
@@ -156,7 +156,7 @@ static void duk__mark_heaphdr(duk_heap *heap, duk_heaphdr *h) {
heap->mark_and_sweep_recursion_depth++;
- switch (DUK_HEAPHDR_GET_TYPE(h)) {
+ switch ((duk_small_int_t) DUK_HEAPHDR_GET_TYPE(h)) {
case DUK_HTYPE_STRING:
duk__mark_hstring(heap, (duk_hstring *) h);
break;
diff --git a/src/duk_heap_refcount.c b/src/duk_heap_refcount.c
index 9d0cdca6..c7a2a50d 100644
--- a/src/duk_heap_refcount.c
+++ b/src/duk_heap_refcount.c
@@ -144,7 +144,7 @@ static void duk__refcount_finalize_hobject(duk_hthread *thr, duk_hobject *h) {
void duk_heap_refcount_finalize_heaphdr(duk_hthread *thr, duk_heaphdr *hdr) {
DUK_ASSERT(hdr);
- switch (DUK_HEAPHDR_GET_TYPE(hdr)) {
+ switch ((duk_small_int_t) DUK_HEAPHDR_GET_TYPE(hdr)) {
case DUK_HTYPE_OBJECT:
duk__refcount_finalize_hobject(thr, (duk_hobject *) hdr);
break;
@@ -421,7 +421,7 @@ void duk_heap_heaphdr_decref(duk_hthread *thr, duk_heaphdr *h) {
}
#endif
- switch (DUK_HEAPHDR_GET_TYPE(h)) {
+ switch ((duk_small_int_t) DUK_HEAPHDR_GET_TYPE(h)) {
case DUK_HTYPE_STRING:
/*
* Strings have no internal references but do have "weak"
diff --git a/src/duk_js_executor.c b/src/duk_js_executor.c
index d2c7131c..4d9c1d64 100644
--- a/src/duk_js_executor.c
+++ b/src/duk_js_executor.c
@@ -1656,7 +1656,7 @@ void duk_js_execute_bytecode(duk_hthread *entry_thread) {
ins = bcode[act->pc++];
- switch (DUK_DEC_OP(ins)) {
+ switch ((duk_small_int_t) DUK_DEC_OP(ins)) {
case DUK_OP_LDREG: {
int t;
From 467112d04c23e99a4d19b2b9a075cdcd63d086e5 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 19:14:33 +0300
Subject: [PATCH 16/17] BCC note
---
website/guide/portability.html | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/website/guide/portability.html b/website/guide/portability.html
index 67916a6d..b35fc289 100644
--- a/website/guide/portability.html
+++ b/website/guide/portability.html
@@ -177,6 +177,13 @@ detail below the table.
32-bit Java. Tested with CrossBridge
1.0.1 on 64-bit Windows 7.
+
+Linux |
+BCC (Bruce's C compiler) |
+i386 |
+-3 and -ansi required; compiles but doesn't link. This is an
+ old compiler useful for portability torture tests (for instance 16-bit integers). |
+
From 4296fb40e612151ff2612402c8bff7096bd16376 Mon Sep 17 00:00:00 2001
From: Sami Vaarala
Date: Mon, 5 May 2014 19:21:46 +0300
Subject: [PATCH 17/17] document bcc compilation issues; they're most likely
similar to problems encountered with other older compilers
---
doc/code-issues.txt | 147 ++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 147 insertions(+)
diff --git a/doc/code-issues.txt b/doc/code-issues.txt
index 89c9be1f..76e48147 100644
--- a/doc/code-issues.txt
+++ b/doc/code-issues.txt
@@ -147,6 +147,34 @@ Be careful especially of assertions, debug prints, and other macros::
DUK_UNREF(y);
int flags = 0; /* problem: DUK_UNREF() */
+Note that even **disabled** debug prints break the variable declaration
+part because disabled debug prints are replaced with ``do {} while (0)``
+(this is intentional to flush out this kind of errors even in release
+builds)::
+
+ {
+ int x;
+
+ DUK_DDD(DUK_DDDPRINT("debug print"));
+
+ int y; /* error here */
+
+ x = 123;
+ ...
+ }
+
+The fix is::
+
+ {
+ int x;
+ int y;
+
+ DUK_DDD(DUK_DDDPRINT("debug print"));
+
+ x = 123;
+ ...
+ }
+
Include guards
--------------
@@ -626,6 +654,118 @@ EBCDIC
See separate section below.
+Portability issues on very old compilers
+========================================
+
+Initialization of auto arrays
+-----------------------------
+
+Some old compilers (such as bcc) refuse to compile the following (error
+message is something along the lines of: initialization of auto arrays
+is illegal)::
+
+ int myarray[] = { 123, 234 };
+
+or even::
+
+ int myarray[2] = { 123, 234 };
+
+Apparently the following would be legal::
+
+ static int myarray[2] = { 123, 234 };
+
+The workaround is to use a static array or initialize explicitly::
+
+ int myarray[2];
+
+ myarray[0] = 123;
+ myarray[1] = 234;
+
+Initializer is too complicated (bcc)
+------------------------------------
+
+BCC complains about "initializer is too complicated" when a function pointer
+array contains casts::
+
+ ...
+ (duk_c_function) my_function,
+ ...
+
+This works::
+
+ ...
+ my_function,
+ ...
+
+Non-integral selector in switch (bcc)
+-------------------------------------
+
+For some reason BCC fails to compile switch statements where the value is
+obtained with a macro such as::
+
+ switch (DUK_DEC_OP(ins)) {
+ ...
+ }
+
+This is probably caused by the fact that ``DUK_DEC_OP(ins)`` is a 32-bit value
+while BCC's integer type is 16 bits. Switch argument needs to be ``int``, so
+one needs to::
+
+ switch ((int) DUK_DEC_OP(ins)) {
+ ...
+ }
+
+Or perhaps (using type wrappers)::
+
+ switch ((duk_small_int_t) DUK_DEC_OP(ins)) {
+ ...
+ }
+
+Division by zero is a compile error
+-----------------------------------
+
+Attempting to create NaN or infinity values with expressions like ``0/0`` and
+``1/0`` are treated as compile errors by some compilers (such as BCC) while
+others will just replace them with an incorrect value (e.g. VBCC replaces them
+with zero). Run-time computed NaN / infinity values are needed on such platforms.
+
+ULL integer constants may cause an error
+----------------------------------------
+
+The following may cause a compilation error (e.g. BCC)::
+
+ #if defined(ULONG_MAX) && (ULONG_MAX == 18446744073709551615ULL)
+
+The error happens even if ``ULONG_MAX`` is not defined. Instead, this needs
+to be restructured in one of several ways. For instance, old compilers can be
+rejected explicitly::
+
+ #if defined(DUK_F_BCC)
+ /* cannot check ULONG_MAX */
+ #else
+ #if defined(ULONG_MAX) && (ULONG_MAX == 18446744073709551615ULL)
+ /* ... */
+ #endif
+ #endif
+
+The important point is that the old compiler cannot process the preprocessor
+line containing the integer constant; if it processes even part of the line,
+it may choke on a syntax error.
+
+Comments inside macro arguments may cause an error (BCC)
+--------------------------------------------------------
+
+The following causes an error on BCC::
+
+ DUK_ASSERT(FOO || /* foo happens */
+ BAR);
+
+The comment causes BCC to produce an error like "incorrect number of macro
+arguments". The fix is to remove the comment from inside the macro::
+
+ DUK_ASSERT(FOO ||
+ BAR);
+
Character values in char literals and strings, EBCDIC
=====================================================
@@ -839,3 +979,10 @@ clang
-----
Clang has some issues with union aliasing. See ``misc/clang_aliasing.c``.
+
+bcc
+---
+
+BCC is not a realistic compilation target at the moment but serves as a nice
+"torture target". Various issues have been documented above in portability
+issues.