summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog6
-rw-r--r--bignum.c11
-rw-r--r--pack.c75
3 files changed, 35 insertions, 57 deletions
diff --git a/ChangeLog b/ChangeLog
index c2be85c..ab0e896 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+Wed Nov 17 04:33:01 2004 GOTOU Yuuzou <gotoyuzo@notwork.org>
+
+ * pack.c: all features are backport from 1.9. [ruby-dev:24826]
+
+ * bignum.c (rb_big2ulong_pack): new function to pack Bignums.
+
Tue Nov 16 23:45:07 2004 Yukihiro Matsumoto <matz@ruby-lang.org>
* numeric.c (flo_divmod): protect float values from GC by
diff --git a/bignum.c b/bignum.c
index 0622841..aba88df 100644
--- a/bignum.c
+++ b/bignum.c
@@ -748,6 +748,17 @@ big2ulong(x, type)
}
unsigned long
+rb_big2ulong_pack(x)
+ VALUE x;
+{
+ unsigned long num = big2ulong(x, "unsigned long", Qfalse);
+ if (!RBIGNUM(x)->sign) {
+ return -num;
+ }
+ return num;
+}
+
+unsigned long
rb_big2ulong(x)
VALUE x;
{
diff --git a/pack.c b/pack.c
index 7bbb174..4d92705 100644
--- a/pack.c
+++ b/pack.c
@@ -331,53 +331,22 @@ endian()
#define VTOHD(x,y) vtohd(x)
#endif
-#if SIZEOF_LONG == SIZE32
-typedef long I32;
-typedef unsigned long U32;
-#define NUM2I32(x) NUM2LONG(x)
-#define NUM2U32(x) NUM2ULONG(x)
-#else
-typedef int I32;
-typedef unsigned int U32;
-# if SIZEOF_INT == SIZE32
-# define NUM2I32(x) NUM2INT(x)
-# define NUM2U32(x) NUM2UINT(x)
-# else
-
-#define I32_MAX 2147483647
-#define I32_MIN (-I32_MAX-1)
+unsigned long rb_big2ulong_pack _((VALUE x));
-static I32
+static unsigned long
num2i32(x)
VALUE x;
{
- long num = NUM2LONG(x);
-
- if (num < I32_MIN || I32_MAX < num) {
- rb_raise(rb_eRangeError, "integer %ld too big to convert to `I32'", num);
- }
- return (I32)num;
-}
-
-#define U32_MAX 4294967295
-
-static U32
-num2u32(x)
- VALUE x;
-{
- unsigned long num = NUM2ULONG(x);
+ x = rb_to_int(x); /* is nil OK? (should not) */
- if (U32_MAX < num) {
- rb_raise(rb_eRangeError, "integer %ld too big to convert to `U32'", num);
+ if (FIXNUM_P(x)) return FIX2LONG(x);
+ if (TYPE(x) == T_BIGNUM) {
+ return rb_big2ulong_pack(x);
}
- return (U32)num;
+ rb_raise(rb_eTypeError, "cannot convert %s to `integer'", rb_obj_classname(x));
+ return 0; /* not reached */
}
-# define NUM2I32(x) num2i32(x)
-# define NUM2U32(x) num2u32(x)
-# endif
-#endif
-
#if SIZEOF_LONG == SIZE32 || SIZEOF_INT == SIZE32
# define EXTEND32(x)
#else
@@ -704,7 +673,7 @@ pack_pack(ary, fmt)
char c;
from = NEXTFROM;
- c = NUM2I32(from);
+ c = num2i32(from);
rb_str_buf_cat(res, &c, sizeof(char));
}
break;
@@ -715,7 +684,7 @@ pack_pack(ary, fmt)
short s;
from = NEXTFROM;
- s = NUM2I32(from);
+ s = num2i32(from);
rb_str_buf_cat(res, OFF16(&s), NATINT_LEN(short,2));
}
break;
@@ -726,26 +695,18 @@ pack_pack(ary, fmt)
long i;
from = NEXTFROM;
- i = NUM2I32(from);
+ i = num2i32(from);
rb_str_buf_cat(res, OFF32(&i), NATINT_LEN(int,4));
}
break;
case 'l': /* signed long */
- while (len-- > 0) {
- long l;
-
- from = NEXTFROM;
- l = NUM2I32(from);
- rb_str_buf_cat(res, OFF32(&l), NATINT_LEN(long,4));
- }
- break;
case 'L': /* unsigned long */
while (len-- > 0) {
long l;
from = NEXTFROM;
- l = NUM2U32(from);
+ l = num2i32(from);
rb_str_buf_cat(res, OFF32(&l), NATINT_LEN(long,4));
}
break;
@@ -766,7 +727,7 @@ pack_pack(ary, fmt)
unsigned short s;
from = NEXTFROM;
- s = NUM2I32(from);
+ s = num2i32(from);
s = NATINT_HTONS(s);
rb_str_buf_cat(res, OFF16(&s), NATINT_LEN(short,2));
}
@@ -777,7 +738,7 @@ pack_pack(ary, fmt)
unsigned long l;
from = NEXTFROM;
- l = NUM2U32(from);
+ l = num2i32(from);
l = NATINT_HTONL(l);
rb_str_buf_cat(res, OFF32(&l), NATINT_LEN(long,4));
}
@@ -788,7 +749,7 @@ pack_pack(ary, fmt)
unsigned short s;
from = NEXTFROM;
- s = NUM2I32(from);
+ s = num2i32(from);
s = NATINT_HTOVS(s);
rb_str_buf_cat(res, OFF16(&s), NATINT_LEN(short,2));
}
@@ -799,7 +760,7 @@ pack_pack(ary, fmt)
unsigned long l;
from = NEXTFROM;
- l = NUM2U32(from);
+ l = num2i32(from);
l = NATINT_HTOVL(l);
rb_str_buf_cat(res, OFF32(&l), NATINT_LEN(long,4));
}
@@ -912,7 +873,7 @@ pack_pack(ary, fmt)
from = NEXTFROM;
from = rb_to_int(from);
- l = NUM2UINT(from);
+ l = NUM2INT(from);
if (l < 0) {
rb_raise(rb_eRangeError, "pack(U): value out of range");
}
@@ -2072,7 +2033,7 @@ uv_to_utf8(buf, uv)
buf[5] = (uv&0x3f)|0x80;
return 6;
}
- rb_raise(rb_eArgError, "pack(U): value out of range");
+ rb_raise(rb_eRangeError, "pack(U): value out of range");
}
static const long utf8_limits[] = {