aboutsummaryrefslogtreecommitdiff
path: root/stdlib
diff options
context:
space:
mode:
authorBruce Hill <bruce@bruce-hill.com>2024-11-24 16:13:23 -0500
committerBruce Hill <bruce@bruce-hill.com>2024-11-24 16:13:23 -0500
commit0e10313d64f54dd587ebbcd5f413bd999333c911 (patch)
tree16a07c4b01467d59807611b23f91f9eb125959e2 /stdlib
parent6ecf6a272446af04f3affd354520d21127a5b952 (diff)
Switch `NaN` to be identical to the null value
Diffstat (limited to 'stdlib')
-rw-r--r--stdlib/integers.c4
-rw-r--r--stdlib/integers.h2
-rw-r--r--stdlib/nums.c8
-rw-r--r--stdlib/optionals.c2
-rw-r--r--stdlib/stdlib.c18
5 files changed, 24 insertions, 10 deletions
diff --git a/stdlib/integers.c b/stdlib/integers.c
index 48ab6019..3b95c994 100644
--- a/stdlib/integers.c
+++ b/stdlib/integers.c
@@ -300,8 +300,10 @@ public Int_t Int$power(Int_t base, Int_t exponent)
return Int$from_mpz(result);
}
-public Int_t Int$sqrt(Int_t i)
+public OptionalInt_t Int$sqrt(Int_t i)
{
+ if (Int$compare_value(i, I(0)) < 0)
+ return NULL_INT;
mpz_t result;
mpz_init_set_int(result, i);
mpz_sqrt(result, result);
diff --git a/stdlib/integers.h b/stdlib/integers.h
index 430a3eac..7bda6398 100644
--- a/stdlib/integers.h
+++ b/stdlib/integers.h
@@ -106,7 +106,7 @@ OptionalInt_t Int$from_str(const char *str);
OptionalInt_t Int$parse(Text_t text);
Int_t Int$abs(Int_t x);
Int_t Int$power(Int_t base, Int_t exponent);
-Int_t Int$sqrt(Int_t i);
+OptionalInt_t Int$sqrt(Int_t i);
#define BIGGEST_SMALL_INT ((1<<29)-1)
diff --git a/stdlib/nums.c b/stdlib/nums.c
index 9f69bb1c..4c9be226 100644
--- a/stdlib/nums.c
+++ b/stdlib/nums.c
@@ -78,10 +78,6 @@ public OptionalNum_t Num$parse(Text_t text) {
return nan("null");
}
-public double Num$nan(Text_t tag) {
- return nan(Text$as_c_string(tag));
-}
-
public CONSTFUNC bool Num$isinf(double n) { return (fpclassify(n) == FP_INFINITE); }
public CONSTFUNC bool Num$finite(double n) { return (fpclassify(n) != FP_INFINITE); }
public CONSTFUNC bool Num$isnan(double n) { return (fpclassify(n) == FP_NAN); }
@@ -155,10 +151,6 @@ public OptionalNum32_t Num32$parse(Text_t text) {
return nan("null");
}
-public float Num32$nan(Text_t tag) {
- return nanf(Text$as_c_string(tag));
-}
-
public CONSTFUNC bool Num32$isinf(float n) { return (fpclassify(n) == FP_INFINITE); }
public CONSTFUNC bool Num32$finite(float n) { return (fpclassify(n) != FP_INFINITE); }
public CONSTFUNC bool Num32$isnan(float n) { return (fpclassify(n) == FP_NAN); }
diff --git a/stdlib/optionals.c b/stdlib/optionals.c
index b6a5989e..8c295228 100644
--- a/stdlib/optionals.c
+++ b/stdlib/optionals.c
@@ -21,6 +21,8 @@ public PUREFUNC bool is_null(const void *obj, const TypeInfo_t *non_optional_typ
return *((OptionalBool_t*)obj) == NULL_BOOL;
else if (non_optional_type == &Num$info)
return isnan(*((Num_t*)obj));
+ else if (non_optional_type == &Num32$info)
+ return isnan(*((Num32_t*)obj));
else if (non_optional_type == &Int64$info)
return ((OptionalInt64_t*)obj)->is_null;
else if (non_optional_type == &Int32$info)
diff --git a/stdlib/stdlib.c b/stdlib/stdlib.c
index 5dac3d3a..0e72dfc4 100644
--- a/stdlib/stdlib.c
+++ b/stdlib/stdlib.c
@@ -27,6 +27,18 @@
public bool USE_COLOR;
+static void signal_handler(int sig, siginfo_t *, void *)
+{
+ assert(sig == SIGILL);
+ fflush(stdout);
+ if (USE_COLOR) fputs("\x1b[31;7m ===== ILLEGAL INSTRUCTION ===== \n\n\x1b[m", stderr);
+ else fputs("===== ILLEGAL INSTRUCTION =====\n\n", stderr);
+ print_stack_trace(stderr, 3, 4);
+ fflush(stderr);
+ raise(SIGABRT);
+ _exit(1);
+}
+
public void tomo_init(void)
{
GC_INIT();
@@ -44,6 +56,12 @@ public void tomo_init(void)
if (register_printf_specifier('k', printf_text, printf_text_size))
errx(1, "Couldn't set printf specifier");
+
+ struct sigaction sigact;
+ sigact.sa_sigaction = signal_handler;
+ sigemptyset(&sigact.sa_mask);
+ sigact.sa_flags = 0;
+ sigaction(SIGILL, &sigact, (struct sigaction *)NULL);
}
static bool parse_single_arg(const TypeInfo_t *info, char *arg, void *dest)