changed some numeric primitives to support fpdec
This commit is contained in:
parent
29f7058ebf
commit
c62a0ce3c5
@ -110,26 +110,26 @@ class(#limited) Number(Magnitude)
|
||||
{
|
||||
method + aNumber
|
||||
{
|
||||
<primitive: #_integer_add>
|
||||
<primitive: #_number_add>
|
||||
self primitiveFailed.
|
||||
}
|
||||
|
||||
method - aNumber
|
||||
{
|
||||
<primitive: #_integer_sub>
|
||||
<primitive: #_number_sub>
|
||||
self primitiveFailed.
|
||||
}
|
||||
|
||||
method * aNumber
|
||||
{
|
||||
<primitive: #_integer_mul>
|
||||
<primitive: #_number_mul>
|
||||
self primitiveFailed.
|
||||
}
|
||||
|
||||
method div: aNumber
|
||||
{
|
||||
## integer division rounded toward zero
|
||||
<primitive: #_integer_div>
|
||||
<primitive: #_number_div>
|
||||
self primitiveFailed.
|
||||
}
|
||||
|
||||
@ -161,13 +161,13 @@ class(#limited) Number(Magnitude)
|
||||
|
||||
method = aNumber
|
||||
{
|
||||
<primitive: #_integer_eq>
|
||||
<primitive: #_number_eq>
|
||||
self primitiveFailed.
|
||||
}
|
||||
|
||||
method ~= aNumber
|
||||
{
|
||||
<primitive: #_integer_ne>
|
||||
<primitive: #_number_ne>
|
||||
self primitiveFailed.
|
||||
}
|
||||
|
||||
|
@ -711,7 +711,6 @@ static moo_oop_t string_to_fpdec (moo_t* moo, moo_oocs_t* str)
|
||||
moo_oop_t v;
|
||||
int base = 10;
|
||||
|
||||
MOO_DEBUG2 (moo, "string to fpdec... %.*js\n", str->len, str->ptr);
|
||||
pos = str->len;
|
||||
while (pos > 0)
|
||||
{
|
||||
@ -1493,13 +1492,12 @@ static int get_numlit (moo_t* moo, int negated)
|
||||
}
|
||||
while (is_digitchar(c));
|
||||
|
||||
MOO_ASSERT (moo, scale > 0);
|
||||
MOO_ASSERT (moo, scale > 0 && scale <= MOO_SMOOI_MAX);
|
||||
|
||||
/* TODO: handle floating-point? fpdec if only suffixed with 's' like 1.23s4?, 'e','g' for floating point?
|
||||
* for now, there is no floating point support. as long as a point appears, it's a fpdec number. */
|
||||
|
||||
MOO_DEBUG2 (moo, "FPDEC LITERAL [%.*js]\n", TOKEN_NAME_LEN(moo), TOKEN_NAME_PTR(moo));
|
||||
SET_TOKEN_TYPE (moo, MOO_IOTOK_FPDECLIT);
|
||||
unget_char (moo, &moo->c->lxc);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
105
moo/lib/exec.c
105
moo/lib/exec.c
@ -2822,6 +2822,104 @@ static moo_pfrc_t pf_system_return_value_to_context (moo_t* moo, moo_mod_t* mod,
|
||||
|
||||
/* ------------------------------------------------------------------ */
|
||||
|
||||
static moo_pfrc_t pf_number_add (moo_t* moo, moo_mod_t* mod, moo_ooi_t nargs)
|
||||
{
|
||||
moo_oop_t rcv, arg, res;
|
||||
|
||||
MOO_ASSERT (moo, nargs == 1);
|
||||
|
||||
rcv = MOO_STACK_GETRCV(moo, nargs);
|
||||
arg = MOO_STACK_GETARG(moo, nargs, 0);
|
||||
|
||||
res = moo_addnums(moo, rcv, arg);
|
||||
if (!res) return (moo->errnum == MOO_EINVAL? MOO_PF_FAILURE: MOO_PF_HARD_FAILURE);
|
||||
|
||||
MOO_STACK_SETRET (moo, nargs, res);
|
||||
return MOO_PF_SUCCESS;
|
||||
}
|
||||
|
||||
static moo_pfrc_t pf_number_sub (moo_t* moo, moo_mod_t* mod, moo_ooi_t nargs)
|
||||
{
|
||||
moo_oop_t rcv, arg, res;
|
||||
|
||||
MOO_ASSERT (moo, nargs == 1);
|
||||
|
||||
rcv = MOO_STACK_GETRCV(moo, nargs);
|
||||
arg = MOO_STACK_GETARG(moo, nargs, 0);
|
||||
|
||||
res = moo_subnums(moo, rcv, arg);
|
||||
if (!res) return (moo->errnum == MOO_EINVAL? MOO_PF_FAILURE: MOO_PF_HARD_FAILURE);
|
||||
|
||||
MOO_STACK_SETRET (moo, nargs, res);
|
||||
return MOO_PF_SUCCESS;
|
||||
}
|
||||
|
||||
static moo_pfrc_t pf_number_mul (moo_t* moo, moo_mod_t* mod, moo_ooi_t nargs)
|
||||
{
|
||||
moo_oop_t rcv, arg, res;
|
||||
|
||||
MOO_ASSERT (moo, nargs == 1);
|
||||
|
||||
rcv = MOO_STACK_GETRCV(moo, nargs);
|
||||
arg = MOO_STACK_GETARG(moo, nargs, 0);
|
||||
|
||||
res = moo_mulnums(moo, rcv, arg);
|
||||
if (!res) return (moo->errnum == MOO_EINVAL? MOO_PF_FAILURE: MOO_PF_HARD_FAILURE);
|
||||
|
||||
MOO_STACK_SETRET (moo, nargs, res);
|
||||
return MOO_PF_SUCCESS;
|
||||
}
|
||||
|
||||
static moo_pfrc_t pf_number_div (moo_t* moo, moo_mod_t* mod, moo_ooi_t nargs)
|
||||
{
|
||||
moo_oop_t rcv, arg, res;
|
||||
|
||||
MOO_ASSERT (moo, nargs == 1);
|
||||
|
||||
rcv = MOO_STACK_GETRCV(moo, nargs);
|
||||
arg = MOO_STACK_GETARG(moo, nargs, 0);
|
||||
|
||||
res = moo_divnums(moo, rcv, arg);
|
||||
if (!res) return (moo->errnum == MOO_EINVAL? MOO_PF_FAILURE: MOO_PF_HARD_FAILURE);
|
||||
|
||||
MOO_STACK_SETRET (moo, nargs, res);
|
||||
return MOO_PF_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
static moo_pfrc_t pf_number_eq (moo_t* moo, moo_mod_t* mod, moo_ooi_t nargs)
|
||||
{
|
||||
moo_oop_t rcv, arg, res;
|
||||
|
||||
MOO_ASSERT (moo, nargs == 1);
|
||||
|
||||
rcv = MOO_STACK_GETRCV(moo, nargs);
|
||||
arg = MOO_STACK_GETARG(moo, nargs, 0);
|
||||
|
||||
res = moo_eqnums(moo, rcv, arg);
|
||||
if (!res) return (moo->errnum == MOO_EINVAL? MOO_PF_FAILURE: MOO_PF_HARD_FAILURE);
|
||||
|
||||
MOO_STACK_SETRET (moo, nargs, res);
|
||||
return MOO_PF_SUCCESS;
|
||||
}
|
||||
|
||||
static moo_pfrc_t pf_number_ne (moo_t* moo, moo_mod_t* mod, moo_ooi_t nargs)
|
||||
{
|
||||
moo_oop_t rcv, arg, res;
|
||||
|
||||
MOO_ASSERT (moo, nargs == 1);
|
||||
|
||||
rcv = MOO_STACK_GETRCV(moo, nargs);
|
||||
arg = MOO_STACK_GETARG(moo, nargs, 0);
|
||||
|
||||
res = moo_nenums(moo, rcv, arg);
|
||||
if (!res) return (moo->errnum == MOO_EINVAL? MOO_PF_FAILURE: MOO_PF_HARD_FAILURE);
|
||||
|
||||
MOO_STACK_SETRET (moo, nargs, res);
|
||||
return MOO_PF_SUCCESS;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------------ */
|
||||
static moo_pfrc_t pf_integer_add (moo_t* moo, moo_mod_t* mod, moo_ooi_t nargs)
|
||||
{
|
||||
moo_oop_t rcv, arg, res;
|
||||
@ -3653,6 +3751,13 @@ static pf_t pftab[] =
|
||||
{ "_integer_rem", { pf_integer_rem, 1, 1 } },
|
||||
{ "_integer_sub", { pf_integer_sub, 1, 1 } },
|
||||
|
||||
{ "_number_add", { pf_number_add, 1, 1 } },
|
||||
{ "_number_div", { pf_number_div, 1, 1 } },
|
||||
{ "_number_eq", { pf_number_eq, 1, 1 } },
|
||||
{ "_number_mul", { pf_number_mul, 1, 1 } },
|
||||
{ "_number_ne", { pf_number_ne, 1, 1 } },
|
||||
{ "_number_sub", { pf_number_sub, 1, 1 } },
|
||||
|
||||
{ "_utf8_seqlen", { moo_pf_utf8_seqlen, 0, 0 } },
|
||||
{ "_utf8_to_uc", { moo_pf_utf8_to_uc, 0, 0 } },
|
||||
};
|
||||
|
@ -26,8 +26,6 @@
|
||||
|
||||
#include "moo-prv.h"
|
||||
|
||||
#define MOO_IS_FPDEC(moo, x) (MOO_OBJ_GET_CLASS(x) == (moo)->_fixed_point_decimal)
|
||||
|
||||
moo_oop_t moo_makefpdec (moo_t* moo, moo_oop_t value, moo_ooi_t scale)
|
||||
{
|
||||
moo_oop_fpdec_t fpdec;
|
||||
@ -62,7 +60,7 @@ static moo_ooi_t equalize_scale (moo_t* moo, moo_oop_t* x, moo_oop_t* y)
|
||||
|
||||
xs = 0;
|
||||
xv = *x;
|
||||
if (MOO_IS_FPDEC(moo, xv))
|
||||
if (MOO_OOP_IS_FPDEC(moo, xv))
|
||||
{
|
||||
xs = MOO_OOP_TO_SMOOI(((moo_oop_fpdec_t)xv)->scale);
|
||||
xv = ((moo_oop_fpdec_t)xv)->value;
|
||||
@ -72,10 +70,10 @@ static moo_ooi_t equalize_scale (moo_t* moo, moo_oop_t* x, moo_oop_t* y)
|
||||
moo_seterrbfmt (moo, MOO_EINVAL, "parameter not numeric - %O", xv);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
ys = 0;
|
||||
yv = *y;
|
||||
if (MOO_IS_FPDEC(moo, *y))
|
||||
if (MOO_OOP_IS_FPDEC(moo, yv))
|
||||
{
|
||||
ys = MOO_OOP_TO_SMOOI(((moo_oop_fpdec_t)yv)->scale);
|
||||
yv = ((moo_oop_fpdec_t)yv)->value;
|
||||
@ -143,7 +141,7 @@ moo_oop_t moo_truncfpdecval (moo_t* moo, moo_oop_t iv, moo_ooi_t cs, moo_ooi_t n
|
||||
|
||||
moo_oop_t moo_addnums (moo_t* moo, moo_oop_t x, moo_oop_t y)
|
||||
{
|
||||
if (!MOO_IS_FPDEC(moo, x) && !MOO_IS_FPDEC(moo, y))
|
||||
if (!MOO_OOP_IS_FPDEC(moo, x) && !MOO_OOP_IS_FPDEC(moo, y))
|
||||
{
|
||||
/* both are probably integers */
|
||||
return moo_addints(moo, x, y);
|
||||
@ -172,7 +170,7 @@ moo_oop_t moo_addnums (moo_t* moo, moo_oop_t x, moo_oop_t y)
|
||||
|
||||
moo_oop_t moo_subnums (moo_t* moo, moo_oop_t x, moo_oop_t y)
|
||||
{
|
||||
if (!MOO_IS_FPDEC(moo, x) && !MOO_IS_FPDEC(moo, y))
|
||||
if (!MOO_OOP_IS_FPDEC(moo, x) && !MOO_OOP_IS_FPDEC(moo, y))
|
||||
{
|
||||
/* both are probably integers */
|
||||
return moo_subints(moo, x, y);
|
||||
@ -207,7 +205,7 @@ static moo_oop_t mul_nums (moo_t* moo, moo_oop_t x, moo_oop_t y, int mult)
|
||||
|
||||
xs = 0;
|
||||
xv = x;
|
||||
if (MOO_IS_FPDEC(moo, xv))
|
||||
if (MOO_OOP_IS_FPDEC(moo, xv))
|
||||
{
|
||||
xs = MOO_OOP_TO_SMOOI(((moo_oop_fpdec_t)xv)->scale);
|
||||
xv = ((moo_oop_fpdec_t)xv)->value;
|
||||
@ -220,7 +218,7 @@ static moo_oop_t mul_nums (moo_t* moo, moo_oop_t x, moo_oop_t y, int mult)
|
||||
|
||||
ys = 0;
|
||||
yv = y;
|
||||
if (MOO_IS_FPDEC(moo, y))
|
||||
if (MOO_OOP_IS_FPDEC(moo, y))
|
||||
{
|
||||
ys = MOO_OOP_TO_SMOOI(((moo_oop_fpdec_t)yv)->scale);
|
||||
yv = ((moo_oop_fpdec_t)yv)->value;
|
||||
@ -269,7 +267,7 @@ moo_oop_t moo_divnums (moo_t* moo, moo_oop_t x, moo_oop_t y)
|
||||
|
||||
xs = 0;
|
||||
xv = x;
|
||||
if (MOO_IS_FPDEC(moo, xv))
|
||||
if (MOO_OOP_IS_FPDEC(moo, xv))
|
||||
{
|
||||
xs = MOO_OOP_TO_SMOOI(((moo_oop_fpdec_t)xv)->scale);
|
||||
xv = ((moo_oop_fpdec_t)xv)->value;
|
||||
@ -282,7 +280,7 @@ moo_oop_t moo_divnums (moo_t* moo, moo_oop_t x, moo_oop_t y)
|
||||
|
||||
ys = 0;
|
||||
yv = y;
|
||||
if (MOO_IS_FPDEC(moo, y))
|
||||
if (MOO_OOP_IS_FPDEC(moo, y))
|
||||
{
|
||||
ys = MOO_OOP_TO_SMOOI(((moo_oop_fpdec_t)yv)->scale);
|
||||
yv = ((moo_oop_fpdec_t)yv)->value;
|
||||
@ -315,7 +313,7 @@ moo_oop_t moo_divnums (moo_t* moo, moo_oop_t x, moo_oop_t y)
|
||||
|
||||
static moo_oop_t comp_nums (moo_t* moo, moo_oop_t x, moo_oop_t y, moo_oop_t (*comper) (moo_t*, moo_oop_t, moo_oop_t))
|
||||
{
|
||||
if (!MOO_IS_FPDEC(moo, x) && !MOO_IS_FPDEC(moo, y))
|
||||
if (!MOO_OOP_IS_FPDEC(moo, x) && !MOO_OOP_IS_FPDEC(moo, y))
|
||||
{
|
||||
/* both are probably integers */
|
||||
return comper(moo, x, y);
|
||||
@ -371,7 +369,7 @@ moo_oop_t moo_nenums (moo_t* moo, moo_oop_t x, moo_oop_t y)
|
||||
|
||||
moo_oop_t moo_sqrtnum (moo_t* moo, moo_oop_t x)
|
||||
{
|
||||
if (!MOO_IS_FPDEC(moo, x))
|
||||
if (!MOO_OOP_IS_FPDEC(moo, x))
|
||||
{
|
||||
return moo_sqrtint(moo, x);
|
||||
}
|
||||
@ -402,7 +400,7 @@ moo_oop_t moo_sqrtnum (moo_t* moo, moo_oop_t x)
|
||||
|
||||
moo_oop_t moo_absnum (moo_t* moo, moo_oop_t x)
|
||||
{
|
||||
if (!MOO_IS_FPDEC(moo, x))
|
||||
if (!MOO_OOP_IS_FPDEC(moo, x))
|
||||
{
|
||||
return moo_absint(moo, x);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user