From d8da07cb598f6d5627b97639f7c60ec521957c9d Mon Sep 17 00:00:00 2001 From: "hyunghwan.chung" Date: Sun, 22 Nov 2015 13:32:06 +0000 Subject: [PATCH] added some bigint code for division --- stix/kernel/Stix.st | 12 +++ stix/kernel/test-005.st | 3 + stix/lib/bigint.c | 65 ++++++-------- stix/lib/exec.c | 94 ++++++++----------- stix/lib/main.c | 10 ++- stix/lib/stix-cmn.h | 4 +- stix/lib/stix-msw.h | 193 ++++++++++++++++++++++++++++++++++++++++ stix/lib/stix-prv.h | 4 +- 8 files changed, 287 insertions(+), 98 deletions(-) create mode 100644 stix/lib/stix-msw.h diff --git a/stix/kernel/Stix.st b/stix/kernel/Stix.st index 21c1120..ecd4b90 100644 --- a/stix/kernel/Stix.st +++ b/stix/kernel/Stix.st @@ -47,6 +47,18 @@ self primitiveFailed. } + #method quo: aNumber + { + + self primitiveFailed. + } + + #method rem: aNumber + { + + self primitiveFailed. + } + #method = aNumber { diff --git a/stix/kernel/test-005.st b/stix/kernel/test-005.st index 344c296..8e87b9c 100644 --- a/stix/kernel/test-005.st +++ b/stix/kernel/test-005.st @@ -270,6 +270,9 @@ PROCESS TESTING (2r111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111 * 128971234897128931) dump. +(-10000 rem: -3) dump. +(-10000 quo: -3) dump. + " FFI isNil dump. FFI notNil dump. diff --git a/stix/lib/bigint.c b/stix/lib/bigint.c index 365036a..72f014e 100644 --- a/stix/lib/bigint.c +++ b/stix/lib/bigint.c @@ -28,7 +28,7 @@ #if defined(STIX_USE_FULL_WORD) - /* nothign special */ + /* nothing special */ #else # define MAKE_WORD(hw1,hw2) ((stix_oow_t)(hw1) | (stix_oow_t)(hw2) << STIX_LIW_BITS) #endif @@ -1054,62 +1054,53 @@ stix_oop_t stix_divints (stix_t* stix, stix_oop_t x, stix_oop_t y, stix_oop_t* r q = xv / yv; STIX_ASSERT (STIX_IN_SMOOI_RANGE(q)); -#if 1 -/* TODO : verify this... */ - r = xv - yv * q; - STIX_ASSERT (STIX_IN_SMOOI_RANGE(r)); - - /* handle sign difference */ - if (r && ((yv ^ r) < 0)) + if (rem) { - /* if the sign bit is different betwen yv and r, - * the sign bit of (yv ^ r) must be set */ - r += yv; - --q; - + r = xv - yv * q; /* r = xv % yv; */ STIX_ASSERT (STIX_IN_SMOOI_RANGE(r)); + *rem = STIX_SMOOI_TO_OOP(r); } -#else - r = xv % yv; - STIX_ASSERT (STIX_IN_SMOOI_RANGE(r)); -#endif - *rem = STIX_SMOOI_TO_OOP(r); return STIX_SMOOI_TO_OOP((stix_ooi_t)q); } else if (STIX_OOP_IS_SMOOI(x)) { if (STIX_OOP_TO_SMOOI(x) == 0) { - t = clone_bigint (stix, y, STIX_OBJ_GET_SIZE(y)); - if (!t) return STIX_NULL; - - *rem = t; + if (rem) + { + t = clone_bigint (stix, y, STIX_OBJ_GET_SIZE(y)); + if (!t) return STIX_NULL; + *rem = t; + } return STIX_SMOOI_TO_OOP(0); } +/* TODO: convert x to bigint */ } else if (STIX_OOP_IS_SMOOI(y)) { - stix_ooi_t yv; - - if (yv == 0) + switch (STIX_OOP_TO_SMOOI(y)) { - stix->errnum = STIX_EDIVBY0; - return STIX_NULL; - } - else if (yv == 1) - { - t = clone_bigint (stix, x, STIX_OBJ_GET_SIZE(x)); - if (!t) return STIX_NULL; + case 0: + stix->errnum = STIX_EDIVBY0; + return STIX_NULL; - *rem = STIX_SMOOI_TO_OOP(0); - return t; + case 1: + t = clone_bigint (stix, x, STIX_OBJ_GET_SIZE(x)); + if (!t) return STIX_NULL; + if (rem) *rem = STIX_SMOOI_TO_OOP(0); + return t; + + case -1: + t = clone_bigint_negated (stix, x, STIX_OBJ_GET_SIZE(x)); + if (!t) return STIX_NULL; + if (rem) *rem = STIX_SMOOI_TO_OOP(0); + return t; } - } - else - { +/* TODO: convert y to bigint */ } +/* TODO: do bigint division. */ return STIX_NULL; } diff --git a/stix/lib/exec.c b/stix/lib/exec.c index 4f77250..c7cbfeb 100644 --- a/stix/lib/exec.c +++ b/stix/lib/exec.c @@ -1018,31 +1018,12 @@ static int prim_integer_add (stix_t* stix, stix_ooi_t nargs) rcv = ACTIVE_STACK_GET(stix, stix->sp - 1); arg = ACTIVE_STACK_GET(stix, stix->sp); -#if 0 - if (STIX_OOP_IS_SMOOI(rcv) && STIX_OOP_IS_SMOOI(arg)) - { - stix_ooi_t tmp; - - tmp = STIX_OOP_TO_SMOOI(rcv) + STIX_OOP_TO_SMOOI(arg); - /* TODO: check overflow. if so convert it to LargeInteger */ - - ACTIVE_STACK_POP (stix); - ACTIVE_STACK_SETTOP (stix, STIX_SMOOI_TO_OOP(tmp)); - return 1; - } - -/* TODO: handle LargeInteger */ - return 0; - -#else res = stix_addints (stix, rcv, arg); - if (!res) return (stix->errnum == STIX_EINVAL)? 0: -1; /* soft or hard failure */ + if (!res) return (stix->errnum == STIX_EINVAL? 0: -1); /* soft or hard failure */ ACTIVE_STACK_POP (stix); ACTIVE_STACK_SETTOP (stix, res); return 1; -#endif - } static int prim_integer_sub (stix_t* stix, stix_ooi_t nargs) @@ -1054,28 +1035,12 @@ static int prim_integer_sub (stix_t* stix, stix_ooi_t nargs) rcv = ACTIVE_STACK_GET(stix, stix->sp - 1); arg = ACTIVE_STACK_GET(stix, stix->sp); -#if 0 - if (STIX_OOP_IS_SMOOI(rcv) && STIX_OOP_IS_SMOOI(arg)) - { - stix_ooi_t tmp; - tmp = STIX_OOP_TO_SMOOI(rcv) - STIX_OOP_TO_SMOOI(arg); - /* TODO: check overflow. if so convert it to LargeInteger */ - - ACTIVE_STACK_POP (stix); - ACTIVE_STACK_SETTOP (stix, STIX_SMOOI_TO_OOP(tmp)); - return 1; - } - -/* TODO: handle LargeInteger */ - return 0; -#else res = stix_subints (stix, rcv, arg); - if (!res) return (stix->errnum == STIX_EINVAL)? 0: -1; /* soft or hard failure */ + if (!res) return (stix->errnum == STIX_EINVAL? 0: -1); /* soft or hard failure */ ACTIVE_STACK_POP (stix); ACTIVE_STACK_SETTOP (stix, res); return 1; -#endif } static int prim_integer_mul (stix_t* stix, stix_ooi_t nargs) @@ -1087,29 +1052,46 @@ static int prim_integer_mul (stix_t* stix, stix_ooi_t nargs) rcv = ACTIVE_STACK_GET(stix, stix->sp - 1); arg = ACTIVE_STACK_GET(stix, stix->sp); -#if 0 - if (STIX_OOP_IS_SMOOI(rcv) && STIX_OOP_IS_SMOOI(arg)) - { - stix_ooi_t tmp; - - tmp = STIX_OOP_TO_SMOOI(rcv) * STIX_OOP_TO_SMOOI(arg); - /* TODO: check overflow. if so convert it to LargeInteger */ - - ACTIVE_STACK_POP (stix); - ACTIVE_STACK_SETTOP (stix, STIX_SMOOI_TO_OOP(tmp)); - return 1; - } - -/* TODO: handle LargeInteger */ - return 0; -#else res = stix_mulints (stix, rcv, arg); - if (!res) return (stix->errnum == STIX_EINVAL)? 0: -1; /* soft or hard failure */ + if (!res) return (stix->errnum == STIX_EINVAL? 0: -1); /* soft or hard failure */ ACTIVE_STACK_POP (stix); ACTIVE_STACK_SETTOP (stix, res); return 1; -#endif +} + +static int prim_integer_quo (stix_t* stix, stix_ooi_t nargs) +{ + stix_oop_t rcv, arg, quo; + + STIX_ASSERT (nargs == 1); + + rcv = ACTIVE_STACK_GET(stix, stix->sp - 1); + arg = ACTIVE_STACK_GET(stix, stix->sp); + + quo = stix_divints (stix, rcv, arg, STIX_NULL); + if (!quo) return (stix->errnum == STIX_EINVAL? 0: -1); /* soft or hard failure */ + + ACTIVE_STACK_POP (stix); + ACTIVE_STACK_SETTOP (stix, quo); + return 1; +} + +static int prim_integer_rem (stix_t* stix, stix_ooi_t nargs) +{ + stix_oop_t rcv, arg, quo, rem; + + STIX_ASSERT (nargs == 1); + + rcv = ACTIVE_STACK_GET(stix, stix->sp - 1); + arg = ACTIVE_STACK_GET(stix, stix->sp); + + quo = stix_divints (stix, rcv, arg, &rem); + if (!quo) return (stix->errnum == STIX_EINVAL? 0: -1); /* soft or hard failure */ + + ACTIVE_STACK_POP (stix); + ACTIVE_STACK_SETTOP (stix, rem); + return 1; } static int prim_integer_eq (stix_t* stix, stix_ooi_t nargs) @@ -1617,6 +1599,8 @@ static prim_t primitives[] = { 1, prim_integer_add, "_integer_add" }, { 1, prim_integer_sub, "_integer_sub" }, { 1, prim_integer_mul, "_integer_mul" }, + { 1, prim_integer_quo, "_integer_quo" }, + { 1, prim_integer_rem, "_integer_rem" }, { 1, prim_integer_eq, "_integer_eq" }, { 1, prim_integer_ne, "_integer_ne" }, { 1, prim_integer_lt, "_integer_lt" }, diff --git a/stix/lib/main.c b/stix/lib/main.c index c55e188..1208720 100644 --- a/stix/lib/main.c +++ b/stix/lib/main.c @@ -51,7 +51,6 @@ # include # define USE_LTDL #endif -#include #if !defined(STIX_DEFAULT_MODPREFIX) # if defined(_WIN32) @@ -464,6 +463,7 @@ int main (int argc, char* argv[]) return -1; } +#if 0 { /*const stix_bch_t* xxx = "9999999999999999999999999999999999999999999999999999999999999999999999999999999999";*/ @@ -488,6 +488,7 @@ buflen = STIX_COUNTOF(buf); stix_utf8toucs (yyy, &xxxlen, buf, &buflen); dump_object (stix, stix_strtoint (stix, buf, buflen, 3), "STRINT"); } + { stix_ooch_t x[] = { 'X', 't', 'r', 'i', 'n', 'g', '\0' }; stix_ooch_t y[] = { 'S', 'y', 'm', 'b', 'o', 'l', '\0' }; @@ -517,6 +518,7 @@ printf ("%p\n", a); dump_dictionary (stix, stix->sysdic, "System dictionary"); } +#endif xtn = stix_getxtn (stix); @@ -597,11 +599,15 @@ printf ("%p\n", a); } - dump_dictionary (stix, stix->sysdic, "System dictionary"); +/* dump_dictionary (stix, stix->sysdic, "System dictionary");*/ stix_close (stix); #if defined(USE_LTDL) lt_dlexit (); +#endif + +#if defined(_WIN32) && defined(_DEBUG) +getchar(); #endif return 0; } diff --git a/stix/lib/stix-cmn.h b/stix/lib/stix-cmn.h index 390c5e8..3479be5 100644 --- a/stix/lib/stix-cmn.h +++ b/stix/lib/stix-cmn.h @@ -33,6 +33,8 @@ #if defined(STIX_HAVE_CFG_H) # include "stix-cfg.h" +#elif defined(_WIN32) +# include "stix-msw.h" #else # error UNSUPPORTED SYSTEM #endif @@ -49,8 +51,6 @@ # endif #endif - - /* ========================================================================= * PRIMITIVE TYPE DEFINTIONS * ========================================================================= */ diff --git a/stix/lib/stix-msw.h b/stix/lib/stix-msw.h new file mode 100644 index 0000000..77be468 --- /dev/null +++ b/stix/lib/stix-msw.h @@ -0,0 +1,193 @@ +/* + * $Id$ + * + Copyright (c) 2014-2015 Chung, Hyung-Hwan. All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE AUTHOR "AS IS" AND ANY EXPRESS OR + IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/* +Macro Meaning +_WIN64 A 64-bit platform. +_WIN32 A 32-bit platform. This value is also defined by the 64-bit + compiler for backward compatibility. +_WIN16 A 16-bit platform + +The following macros are specific to the architecture. + +Macro Meaning +_M_IA64 Intel Itanium Processor Family +_M_IX86 x86 platform +_M_X64 x64 platform +*/ + +/* windows for most of non-x86 platforms dropped. + * make it selective to support old non-x86 windows platforms. */ +#define STIX_ENDIAN_LITTLE + +#if defined(__WATCOMC__) +# define STIX_SIZEOF_CHAR 1 +# define STIX_SIZEOF_SHORT 2 +# define STIX_SIZEOF_INT 4 +# define STIX_SIZEOF_LONG 4 +# if (__WATCOMC__ < 1200) +# define STIX_SIZEOF_LONG_LONG 0 +# else +# define STIX_SIZEOF_LONG_LONG 8 +# endif + +# if defined(_WIN64) +# define STIX_SIZEOF_VOID_P 8 +# else +# define STIX_SIZEOF_VOID_P 4 +# endif +# define STIX_SIZEOF_FLOAT 4 +# define STIX_SIZEOF_DOUBLE 8 +# define STIX_SIZEOF_LONG_DOUBLE 8 +# define STIX_SIZEOF_WCHAR_T 2 + +# define STIX_SIZEOF___INT8 1 +# define STIX_SIZEOF___INT16 2 +# define STIX_SIZEOF___INT32 4 +# define STIX_SIZEOF___INT64 8 +# define STIX_SIZEOF___INT128 0 + +# define STIX_SIZEOF_OFF64_T 0 +# define STIX_SIZEOF_OFF_T 8 + +# define STIX_SIZEOF_MBSTATE_T STIX_SIZEOF_LONG +# define STIX_MBLEN_MAX 16 + + /* these two have only to be large enough */ +# define STIX_SIZEOF_STRUCT_SOCKADDR_IN 32 +# define STIX_SIZEOF_STRUCT_SOCKADDR_IN6 64 +# define STIX_SIZEOF_SOCKLEN_T 4 + +#elif defined(__GNUC__) || defined(__DMC__) || defined(__POCC__) +# define STIX_SIZEOF_CHAR 1 +# define STIX_SIZEOF_SHORT 2 +# define STIX_SIZEOF_INT 4 +# define STIX_SIZEOF_LONG 4 +# define STIX_SIZEOF_LONG_LONG 8 + +# if defined(_WIN64) +# define STIX_SIZEOF_VOID_P 8 +# else +# define STIX_SIZEOF_VOID_P 4 +# endif +# define STIX_SIZEOF_FLOAT 4 +# define STIX_SIZEOF_DOUBLE 8 +# define STIX_SIZEOF_LONG_DOUBLE 16 +# define STIX_SIZEOF_WCHAR_T 2 + +# define STIX_SIZEOF___INT8 0 +# define STIX_SIZEOF___INT16 0 +# define STIX_SIZEOF___INT32 0 +# define STIX_SIZEOF___INT64 0 +# define STIX_SIZEOF___INT128 0 + +# define STIX_SIZEOF_OFF64_T 0 +# define STIX_SIZEOF_OFF_T 8 + +# define STIX_SIZEOF_MBSTATE_T STIX_SIZEOF_LONG +# define STIX_MBLEN_MAX 16 + + /* these two have only to be large enough */ +# define STIX_SIZEOF_STRUCT_SOCKADDR_IN 32 +# define STIX_SIZEOF_STRUCT_SOCKADDR_IN6 64 + +#elif defined(_MSC_VER) +# define STIX_SIZEOF_CHAR 1 +# define STIX_SIZEOF_SHORT 2 +# define STIX_SIZEOF_INT 4 +# define STIX_SIZEOF_LONG 4 +# if (_MSC_VER>=1310) +# define STIX_SIZEOF_LONG_LONG 8 +# else +# define STIX_SIZEOF_LONG_LONG 0 +# endif + +# if defined(_WIN64) +# define STIX_SIZEOF_VOID_P 8 +# else +# define STIX_SIZEOF_VOID_P 4 +# endif +# define STIX_SIZEOF_FLOAT 4 +# define STIX_SIZEOF_DOUBLE 8 +# define STIX_SIZEOF_LONG_DOUBLE 8 +# define STIX_SIZEOF_WCHAR_T 2 + +# define STIX_SIZEOF___INT8 1 +# define STIX_SIZEOF___INT16 2 +# define STIX_SIZEOF___INT32 4 +# define STIX_SIZEOF___INT64 8 +# define STIX_SIZEOF___INT128 0 + +# define STIX_SIZEOF_OFF64_T 0 +# define STIX_SIZEOF_OFF_T 8 + +# define STIX_SIZEOF_MBSTATE_T STIX_SIZEOF_LONG +# define STIX_MBLEN_MAX 8 + + /* these two have only to be large enough */ +# define STIX_SIZEOF_STRUCT_SOCKADDR_IN 32 +# define STIX_SIZEOF_STRUCT_SOCKADDR_IN6 64 +# define STIX_SIZEOF_SOCKLEN_T 4 + +#elif defined(__BORLANDC__) + +# define STIX_SIZEOF_CHAR 1 +# define STIX_SIZEOF_SHORT 2 +# define STIX_SIZEOF_INT 4 +# define STIX_SIZEOF_LONG 4 +# define STIX_SIZEOF_LONG_LONG 0 + +# if defined(_WIN64) +# define STIX_SIZEOF_VOID_P 8 +# else +# define STIX_SIZEOF_VOID_P 4 +# endif +# define STIX_SIZEOF_FLOAT 4 +# define STIX_SIZEOF_DOUBLE 8 +# define STIX_SIZEOF_LONG_DOUBLE 8 +# define STIX_SIZEOF_WCHAR_T 2 + +# define STIX_SIZEOF___INT8 1 +# define STIX_SIZEOF___INT16 2 +# define STIX_SIZEOF___INT32 4 +# define STIX_SIZEOF___INT64 8 +# define STIX_SIZEOF___INT128 0 + +# define STIX_SIZEOF_OFF64_T 0 +# define STIX_SIZEOF_OFF_T 8 + +# define STIX_SIZEOF_MBSTATE_T STIX_SIZEOF_LONG +# define STIX_MBLEN_MAX 8 + + /* these two have only to be large enough */ +# define STIX_SIZEOF_STRUCT_SOCKADDR_IN 32 +# define STIX_SIZEOF_STRUCT_SOCKADDR_IN6 64 +# define STIX_SIZEOF_SOCKLEN_T 4 + +#else +# error Define the size of various data types. +#endif + diff --git a/stix/lib/stix-prv.h b/stix/lib/stix-prv.h index 8fd6b45..d901ad0 100644 --- a/stix/lib/stix-prv.h +++ b/stix/lib/stix-prv.h @@ -1105,12 +1105,12 @@ stix_oop_t stix_strtoint ( /* ========================================================================= */ /* comp.c */ /* ========================================================================= */ -int stix_compile ( +STIX_EXPORT int stix_compile ( stix_t* stix, stix_io_impl_t io ); -void stix_getsynerr ( +STIX_EXPORT void stix_getsynerr ( stix_t* stix, stix_synerr_t* synerr );