mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
* pack.c (pack_pack): use union instead of bare variable to ease
optimizations and avoid assigning x87 floating point number. [ruby-core:74496] [Bug #12209] * pack.c (pack_unpack): ditto. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@55573 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
parent
c73eb62b3f
commit
e90e916b44
2 changed files with 62 additions and 149 deletions
|
@ -1,3 +1,11 @@
|
|||
Tue Jul 5 11:07:14 2016 NARUSE, Yui <naruse@ruby-lang.org>
|
||||
|
||||
* pack.c (pack_pack): use union instead of bare variable to ease
|
||||
optimizations and avoid assigning x87 floating point number.
|
||||
[ruby-core:74496] [Bug #12209]
|
||||
|
||||
* pack.c (pack_unpack): ditto.
|
||||
|
||||
Mon Jul 4 13:56:34 2016 NARUSE, Yui <naruse@ruby-lang.org>
|
||||
|
||||
* process.c: define sig_t if not exist.
|
||||
|
|
203
pack.c
203
pack.c
|
@ -68,59 +68,18 @@ static const char endstr[] = "sSiIlLqQjJ";
|
|||
# define NATINT_LEN(type,len) ((int)sizeof(type))
|
||||
#endif
|
||||
|
||||
#define define_swapx(x, xtype) \
|
||||
static xtype \
|
||||
TOKEN_PASTE(swap,x)(xtype z) \
|
||||
{ \
|
||||
xtype r; \
|
||||
xtype *zp; \
|
||||
unsigned char *s, *t; \
|
||||
int i; \
|
||||
\
|
||||
zp = xmalloc(sizeof(xtype)); \
|
||||
*zp = z; \
|
||||
s = (unsigned char*)zp; \
|
||||
t = xmalloc(sizeof(xtype)); \
|
||||
for (i=0; i<sizeof(xtype); i++) { \
|
||||
t[sizeof(xtype)-i-1] = s[i]; \
|
||||
} \
|
||||
r = *(xtype *)t; \
|
||||
xfree(t); \
|
||||
xfree(zp); \
|
||||
return r; \
|
||||
}
|
||||
|
||||
#if SIZEOF_FLOAT == 4 && defined(HAVE_INT32_T)
|
||||
# define swapf(x) swap32(x)
|
||||
# define FLOAT_SWAPPER uint32_t
|
||||
#else
|
||||
define_swapx(f,float)
|
||||
#endif
|
||||
|
||||
#if SIZEOF_DOUBLE == 8 && defined(HAVE_INT64_T)
|
||||
# define swapd(x) swap64(x)
|
||||
# define DOUBLE_SWAPPER uint64_t
|
||||
#elif SIZEOF_DOUBLE == 8 && defined(HAVE_INT32_T)
|
||||
static double
|
||||
swapd(const double d)
|
||||
{
|
||||
double dtmp = d;
|
||||
uint32_t utmp[2];
|
||||
uint32_t utmp0;
|
||||
|
||||
utmp[0] = 0; utmp[1] = 0;
|
||||
memcpy(utmp,&dtmp,sizeof(double));
|
||||
utmp0 = utmp[0];
|
||||
utmp[0] = swap32(utmp[1]);
|
||||
utmp[1] = swap32(utmp0);
|
||||
memcpy(&dtmp,utmp,sizeof(double));
|
||||
return dtmp;
|
||||
}
|
||||
#else
|
||||
define_swapx(d, double)
|
||||
#endif
|
||||
|
||||
#undef define_swapx
|
||||
typedef union {
|
||||
float f;
|
||||
uint32_t u;
|
||||
char buf[4];
|
||||
} FLOAT_SWAPPER;
|
||||
typedef union {
|
||||
double d;
|
||||
uint64_t u;
|
||||
char buf[8];
|
||||
} DOUBLE_SWAPPER;
|
||||
#define swapf(x) swap32(x)
|
||||
#define swapd(x) swap64(x)
|
||||
|
||||
#define rb_ntohf(x) (BIGENDIAN_P()?(x):swapf(x))
|
||||
#define rb_ntohd(x) (BIGENDIAN_P()?(x):swapd(x))
|
||||
|
@ -131,57 +90,17 @@ TOKEN_PASTE(swap,x)(xtype z) \
|
|||
#define rb_vtohf(x) (BIGENDIAN_P()?swapf(x):(x))
|
||||
#define rb_vtohd(x) (BIGENDIAN_P()?swapd(x):(x))
|
||||
|
||||
#ifdef FLOAT_SWAPPER
|
||||
# define FLOAT_CONVWITH(y) FLOAT_SWAPPER y;
|
||||
# define HTONF(x,y) (memcpy(&(y),&(x),sizeof(float)), \
|
||||
(y) = rb_htonf((FLOAT_SWAPPER)(y)), \
|
||||
memcpy(&(x),&(y),sizeof(float)), \
|
||||
(x))
|
||||
# define HTOVF(x,y) (memcpy(&(y),&(x),sizeof(float)), \
|
||||
(y) = rb_htovf((FLOAT_SWAPPER)(y)), \
|
||||
memcpy(&(x),&(y),sizeof(float)), \
|
||||
(x))
|
||||
# define NTOHF(x,y) (memcpy(&(y),&(x),sizeof(float)), \
|
||||
(y) = rb_ntohf((FLOAT_SWAPPER)(y)), \
|
||||
memcpy(&(x),&(y),sizeof(float)), \
|
||||
(x))
|
||||
# define VTOHF(x,y) (memcpy(&(y),&(x),sizeof(float)), \
|
||||
(y) = rb_vtohf((FLOAT_SWAPPER)(y)), \
|
||||
memcpy(&(x),&(y),sizeof(float)), \
|
||||
(x))
|
||||
#else
|
||||
# define FLOAT_CONVWITH(y)
|
||||
# define HTONF(x,y) rb_htonf(x)
|
||||
# define HTOVF(x,y) rb_htovf(x)
|
||||
# define NTOHF(x,y) rb_ntohf(x)
|
||||
# define VTOHF(x,y) rb_vtohf(x)
|
||||
#endif
|
||||
#define FLOAT_CONVWITH(x) FLOAT_SWAPPER x;
|
||||
#define HTONF(x) ((x).u = rb_htonf((x).u))
|
||||
#define HTOVF(x) ((x).u = rb_htovf((x).u))
|
||||
#define NTOHF(x) ((x).u = rb_ntohf((x).u))
|
||||
#define VTOHF(x) ((x).u = rb_vtohf((x).u))
|
||||
|
||||
#ifdef DOUBLE_SWAPPER
|
||||
# define DOUBLE_CONVWITH(y) DOUBLE_SWAPPER y;
|
||||
# define HTOND(x,y) (memcpy(&(y),&(x),sizeof(double)), \
|
||||
(y) = rb_htond((DOUBLE_SWAPPER)(y)), \
|
||||
memcpy(&(x),&(y),sizeof(double)), \
|
||||
(x))
|
||||
# define HTOVD(x,y) (memcpy(&(y),&(x),sizeof(double)), \
|
||||
(y) = rb_htovd((DOUBLE_SWAPPER)(y)), \
|
||||
memcpy(&(x),&(y),sizeof(double)), \
|
||||
(x))
|
||||
# define NTOHD(x,y) (memcpy(&(y),&(x),sizeof(double)), \
|
||||
(y) = rb_ntohd((DOUBLE_SWAPPER)(y)), \
|
||||
memcpy(&(x),&(y),sizeof(double)), \
|
||||
(x))
|
||||
# define VTOHD(x,y) (memcpy(&(y),&(x),sizeof(double)), \
|
||||
(y) = rb_vtohd((DOUBLE_SWAPPER)(y)), \
|
||||
memcpy(&(x),&(y),sizeof(double)), \
|
||||
(x))
|
||||
#else
|
||||
# define DOUBLE_CONVWITH(y)
|
||||
# define HTOND(x,y) rb_htond(x)
|
||||
# define HTOVD(x,y) rb_htovd(x)
|
||||
# define NTOHD(x,y) rb_ntohd(x)
|
||||
# define VTOHD(x,y) rb_vtohd(x)
|
||||
#endif
|
||||
#define DOUBLE_CONVWITH(x) DOUBLE_SWAPPER x;
|
||||
#define HTOND(x) ((x).u = rb_htond((x).u))
|
||||
#define HTOVD(x) ((x).u = rb_htovd((x).u))
|
||||
#define NTOHD(x) ((x).u = rb_ntohd((x).u))
|
||||
#define VTOHD(x) ((x).u = rb_vtohd((x).u))
|
||||
|
||||
#define MAX_INTEGER_PACK_SIZE 8
|
||||
|
||||
|
@ -728,25 +647,22 @@ pack_pack(VALUE ary, VALUE fmt)
|
|||
|
||||
case 'e': /* single precision float in VAX byte-order */
|
||||
while (len-- > 0) {
|
||||
float f;
|
||||
FLOAT_CONVWITH(ftmp);
|
||||
FLOAT_CONVWITH(tmp);
|
||||
|
||||
from = NEXTFROM;
|
||||
f = (float)RFLOAT_VALUE(rb_to_float(from));
|
||||
f = HTOVF(f,ftmp);
|
||||
rb_str_buf_cat(res, (char*)&f, sizeof(float));
|
||||
tmp.f = (float)RFLOAT_VALUE(rb_to_float(from));
|
||||
HTOVF(tmp);
|
||||
rb_str_buf_cat(res, tmp.buf, sizeof(float));
|
||||
}
|
||||
break;
|
||||
|
||||
case 'E': /* double precision float in VAX byte-order */
|
||||
while (len-- > 0) {
|
||||
double d;
|
||||
DOUBLE_CONVWITH(dtmp);
|
||||
|
||||
DOUBLE_CONVWITH(tmp);
|
||||
from = NEXTFROM;
|
||||
d = RFLOAT_VALUE(rb_to_float(from));
|
||||
d = HTOVD(d,dtmp);
|
||||
rb_str_buf_cat(res, (char*)&d, sizeof(double));
|
||||
tmp.d = RFLOAT_VALUE(rb_to_float(from));
|
||||
HTOVD(tmp);
|
||||
rb_str_buf_cat(res, tmp.buf, sizeof(double));
|
||||
}
|
||||
break;
|
||||
|
||||
|
@ -763,25 +679,22 @@ pack_pack(VALUE ary, VALUE fmt)
|
|||
|
||||
case 'g': /* single precision float in network byte-order */
|
||||
while (len-- > 0) {
|
||||
float f;
|
||||
FLOAT_CONVWITH(ftmp);
|
||||
|
||||
FLOAT_CONVWITH(tmp);
|
||||
from = NEXTFROM;
|
||||
f = (float)RFLOAT_VALUE(rb_to_float(from));
|
||||
f = HTONF(f,ftmp);
|
||||
rb_str_buf_cat(res, (char*)&f, sizeof(float));
|
||||
tmp.f = (float)RFLOAT_VALUE(rb_to_float(from));
|
||||
HTONF(tmp);
|
||||
rb_str_buf_cat(res, tmp.buf, sizeof(float));
|
||||
}
|
||||
break;
|
||||
|
||||
case 'G': /* double precision float in network byte-order */
|
||||
while (len-- > 0) {
|
||||
double d;
|
||||
DOUBLE_CONVWITH(dtmp);
|
||||
DOUBLE_CONVWITH(tmp);
|
||||
|
||||
from = NEXTFROM;
|
||||
d = RFLOAT_VALUE(rb_to_float(from));
|
||||
d = HTOND(d,dtmp);
|
||||
rb_str_buf_cat(res, (char*)&d, sizeof(double));
|
||||
tmp.d = RFLOAT_VALUE(rb_to_float(from));
|
||||
HTOND(tmp);
|
||||
rb_str_buf_cat(res, tmp.buf, sizeof(double));
|
||||
}
|
||||
break;
|
||||
|
||||
|
@ -1578,13 +1491,11 @@ pack_unpack(VALUE str, VALUE fmt)
|
|||
case 'e':
|
||||
PACK_LENGTH_ADJUST_SIZE(sizeof(float));
|
||||
while (len-- > 0) {
|
||||
float tmp;
|
||||
FLOAT_CONVWITH(ftmp);
|
||||
|
||||
memcpy(&tmp, s, sizeof(float));
|
||||
FLOAT_CONVWITH(tmp);
|
||||
memcpy(tmp.buf, s, sizeof(float));
|
||||
s += sizeof(float);
|
||||
tmp = VTOHF(tmp,ftmp);
|
||||
UNPACK_PUSH(DBL2NUM((double)tmp));
|
||||
VTOHF(tmp);
|
||||
UNPACK_PUSH(DBL2NUM(tmp.f));
|
||||
}
|
||||
PACK_ITEM_ADJUST();
|
||||
break;
|
||||
|
@ -1592,13 +1503,11 @@ pack_unpack(VALUE str, VALUE fmt)
|
|||
case 'E':
|
||||
PACK_LENGTH_ADJUST_SIZE(sizeof(double));
|
||||
while (len-- > 0) {
|
||||
double tmp;
|
||||
DOUBLE_CONVWITH(dtmp);
|
||||
|
||||
memcpy(&tmp, s, sizeof(double));
|
||||
DOUBLE_CONVWITH(tmp);
|
||||
memcpy(tmp.buf, s, sizeof(double));
|
||||
s += sizeof(double);
|
||||
tmp = VTOHD(tmp,dtmp);
|
||||
UNPACK_PUSH(DBL2NUM(tmp));
|
||||
VTOHD(tmp);
|
||||
UNPACK_PUSH(DBL2NUM(tmp.d));
|
||||
}
|
||||
PACK_ITEM_ADJUST();
|
||||
break;
|
||||
|
@ -1618,13 +1527,11 @@ pack_unpack(VALUE str, VALUE fmt)
|
|||
case 'g':
|
||||
PACK_LENGTH_ADJUST_SIZE(sizeof(float));
|
||||
while (len-- > 0) {
|
||||
float tmp;
|
||||
FLOAT_CONVWITH(ftmp);
|
||||
|
||||
memcpy(&tmp, s, sizeof(float));
|
||||
FLOAT_CONVWITH(tmp);
|
||||
memcpy(tmp.buf, s, sizeof(float));
|
||||
s += sizeof(float);
|
||||
tmp = NTOHF(tmp,ftmp);
|
||||
UNPACK_PUSH(DBL2NUM((double)tmp));
|
||||
NTOHF(tmp);
|
||||
UNPACK_PUSH(DBL2NUM(tmp.f));
|
||||
}
|
||||
PACK_ITEM_ADJUST();
|
||||
break;
|
||||
|
@ -1632,13 +1539,11 @@ pack_unpack(VALUE str, VALUE fmt)
|
|||
case 'G':
|
||||
PACK_LENGTH_ADJUST_SIZE(sizeof(double));
|
||||
while (len-- > 0) {
|
||||
double tmp;
|
||||
DOUBLE_CONVWITH(dtmp);
|
||||
|
||||
memcpy(&tmp, s, sizeof(double));
|
||||
DOUBLE_CONVWITH(tmp);
|
||||
memcpy(tmp.buf, s, sizeof(double));
|
||||
s += sizeof(double);
|
||||
tmp = NTOHD(tmp,dtmp);
|
||||
UNPACK_PUSH(DBL2NUM(tmp));
|
||||
NTOHD(tmp);
|
||||
UNPACK_PUSH(DBL2NUM(tmp.d));
|
||||
}
|
||||
PACK_ITEM_ADJUST();
|
||||
break;
|
||||
|
|
Loading…
Reference in a new issue