mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
zlib (rb_gzreader_getc): localize and return cbuf directly
No point in having a long-lived cbuf in "struct gzfile" since GZFILE_CBUF_CAPA is smaller than RSTRING_EMBED_LEN_MAX (even on 32-bit). We can also have rb_econv_convert write directly to the return value instead of an intermediate buffer. This brings "struct gzfile" from 264 to 256 bytes on 64-bit systems to avoid taking an additional cache line. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@63993 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
parent
f705c52908
commit
a22232cd93
1 changed files with 6 additions and 20 deletions
|
@ -2225,7 +2225,6 @@ struct gzfile {
|
||||||
rb_encoding *enc2;
|
rb_encoding *enc2;
|
||||||
rb_econv_t *ec;
|
rb_econv_t *ec;
|
||||||
VALUE ecopts;
|
VALUE ecopts;
|
||||||
char *cbuf;
|
|
||||||
VALUE path;
|
VALUE path;
|
||||||
};
|
};
|
||||||
#define GZFILE_CBUF_CAPA 10
|
#define GZFILE_CBUF_CAPA 10
|
||||||
|
@ -2275,22 +2274,13 @@ gzfile_free(void *p)
|
||||||
}
|
}
|
||||||
zstream_finalize(z);
|
zstream_finalize(z);
|
||||||
}
|
}
|
||||||
if (gz->cbuf) {
|
|
||||||
xfree(gz->cbuf);
|
|
||||||
}
|
|
||||||
xfree(gz);
|
xfree(gz);
|
||||||
}
|
}
|
||||||
|
|
||||||
static size_t
|
static size_t
|
||||||
gzfile_memsize(const void *p)
|
gzfile_memsize(const void *p)
|
||||||
{
|
{
|
||||||
const struct gzfile *gz = p;
|
return sizeof(struct gzfile);
|
||||||
size_t size = sizeof(struct gzfile);
|
|
||||||
|
|
||||||
if (gz->cbuf)
|
|
||||||
size += GZFILE_CBUF_CAPA;
|
|
||||||
|
|
||||||
return size;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static const rb_data_type_t gzfile_data_type = {
|
static const rb_data_type_t gzfile_data_type = {
|
||||||
|
@ -2319,7 +2309,6 @@ gzfile_init(struct gzfile *gz, const struct zstream_funcs *funcs, void (*endfunc
|
||||||
gz->ec = NULL;
|
gz->ec = NULL;
|
||||||
gz->ecflags = 0;
|
gz->ecflags = 0;
|
||||||
gz->ecopts = Qnil;
|
gz->ecopts = Qnil;
|
||||||
gz->cbuf = 0;
|
|
||||||
gz->path = Qnil;
|
gz->path = Qnil;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2870,22 +2859,19 @@ gzfile_getc(struct gzfile *gz)
|
||||||
if (gz->ec && rb_enc_dummy_p(gz->enc2)) {
|
if (gz->ec && rb_enc_dummy_p(gz->enc2)) {
|
||||||
const unsigned char *ss, *sp, *se;
|
const unsigned char *ss, *sp, *se;
|
||||||
unsigned char *ds, *dp, *de;
|
unsigned char *ds, *dp, *de;
|
||||||
|
VALUE cbuf = rb_enc_str_new(0, GZFILE_CBUF_CAPA, gz->enc);
|
||||||
|
|
||||||
if (!gz->cbuf) {
|
|
||||||
gz->cbuf = ALLOC_N(char, GZFILE_CBUF_CAPA);
|
|
||||||
}
|
|
||||||
ss = sp = (const unsigned char*)RSTRING_PTR(gz->z.buf);
|
ss = sp = (const unsigned char*)RSTRING_PTR(gz->z.buf);
|
||||||
se = sp + ZSTREAM_BUF_FILLED(&gz->z);
|
se = sp + ZSTREAM_BUF_FILLED(&gz->z);
|
||||||
ds = dp = (unsigned char *)gz->cbuf;
|
ds = dp = (unsigned char *)RSTRING_PTR(cbuf);
|
||||||
de = (unsigned char *)ds + GZFILE_CBUF_CAPA;
|
de = (unsigned char *)ds + GZFILE_CBUF_CAPA;
|
||||||
(void)rb_econv_convert(gz->ec, &sp, se, &dp, de, ECONV_PARTIAL_INPUT|ECONV_AFTER_OUTPUT);
|
(void)rb_econv_convert(gz->ec, &sp, se, &dp, de, ECONV_PARTIAL_INPUT|ECONV_AFTER_OUTPUT);
|
||||||
rb_econv_check_error(gz->ec);
|
rb_econv_check_error(gz->ec);
|
||||||
dst = zstream_shift_buffer(&gz->z, sp - ss);
|
dst = zstream_shift_buffer(&gz->z, sp - ss);
|
||||||
gzfile_calc_crc(gz, dst);
|
gzfile_calc_crc(gz, dst);
|
||||||
dst = rb_str_new(gz->cbuf, dp - ds);
|
rb_str_resize(cbuf, dp - ds);
|
||||||
rb_enc_associate(dst, gz->enc);
|
OBJ_TAINT(cbuf);
|
||||||
OBJ_TAINT(dst);
|
return cbuf;
|
||||||
return dst;
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
buf = gz->z.buf;
|
buf = gz->z.buf;
|
||||||
|
|
Loading…
Add table
Reference in a new issue