Embed File::Stat objects
They are very short lived and fit in a 160B slot.
This commit is contained in:
parent
0f24ecf17a
commit
4f031a745d
75
file.c
75
file.c
@ -483,28 +483,29 @@ apply2files(int (*func)(const char *, void *), int argc, VALUE *argv, void *arg)
|
|||||||
return LONG2FIX(argc);
|
return LONG2FIX(argc);
|
||||||
}
|
}
|
||||||
|
|
||||||
static size_t
|
|
||||||
stat_memsize(const void *p)
|
|
||||||
{
|
|
||||||
return sizeof(struct stat);
|
|
||||||
}
|
|
||||||
|
|
||||||
static const rb_data_type_t stat_data_type = {
|
static const rb_data_type_t stat_data_type = {
|
||||||
"stat",
|
"stat",
|
||||||
{NULL, RUBY_TYPED_DEFAULT_FREE, stat_memsize,},
|
{
|
||||||
0, 0, RUBY_TYPED_FREE_IMMEDIATELY | RUBY_TYPED_WB_PROTECTED
|
NULL,
|
||||||
|
RUBY_TYPED_DEFAULT_FREE,
|
||||||
|
NULL, // No external memory to report
|
||||||
|
},
|
||||||
|
0, 0, RUBY_TYPED_FREE_IMMEDIATELY | RUBY_TYPED_WB_PROTECTED | RUBY_TYPED_EMBEDDABLE
|
||||||
|
};
|
||||||
|
|
||||||
|
struct rb_stat {
|
||||||
|
struct stat stat;
|
||||||
|
bool initialized;
|
||||||
};
|
};
|
||||||
|
|
||||||
static VALUE
|
static VALUE
|
||||||
stat_new_0(VALUE klass, const struct stat *st)
|
stat_new_0(VALUE klass, const struct stat *st)
|
||||||
{
|
{
|
||||||
struct stat *nst = 0;
|
struct rb_stat *rb_st;
|
||||||
VALUE obj = TypedData_Wrap_Struct(klass, &stat_data_type, 0);
|
VALUE obj = TypedData_Make_Struct(klass, struct rb_stat, &stat_data_type, rb_st);
|
||||||
|
|
||||||
if (st) {
|
if (st) {
|
||||||
nst = ALLOC(struct stat);
|
rb_st->stat = *st;
|
||||||
*nst = *st;
|
rb_st->initialized = true;
|
||||||
RTYPEDDATA_DATA(obj) = nst;
|
|
||||||
}
|
}
|
||||||
return obj;
|
return obj;
|
||||||
}
|
}
|
||||||
@ -518,10 +519,10 @@ rb_stat_new(const struct stat *st)
|
|||||||
static struct stat*
|
static struct stat*
|
||||||
get_stat(VALUE self)
|
get_stat(VALUE self)
|
||||||
{
|
{
|
||||||
struct stat* st;
|
struct rb_stat* rb_st;
|
||||||
TypedData_Get_Struct(self, struct stat, &stat_data_type, st);
|
TypedData_Get_Struct(self, struct rb_stat, &stat_data_type, rb_st);
|
||||||
if (!st) rb_raise(rb_eTypeError, "uninitialized File::Stat");
|
if (!rb_st->initialized) rb_raise(rb_eTypeError, "uninitialized File::Stat");
|
||||||
return st;
|
return &rb_st->stat;
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct timespec stat_mtimespec(const struct stat *st);
|
static struct timespec stat_mtimespec(const struct stat *st);
|
||||||
@ -1092,9 +1093,9 @@ rb_stat_inspect(VALUE self)
|
|||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
struct stat* st;
|
struct rb_stat* rb_st;
|
||||||
TypedData_Get_Struct(self, struct stat, &stat_data_type, st);
|
TypedData_Get_Struct(self, struct rb_stat, &stat_data_type, rb_st);
|
||||||
if (!st) {
|
if (!rb_st->initialized) {
|
||||||
return rb_sprintf("#<%s: uninitialized>", rb_obj_classname(self));
|
return rb_sprintf("#<%s: uninitialized>", rb_obj_classname(self));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -5557,7 +5558,7 @@ rb_stat_s_alloc(VALUE klass)
|
|||||||
static VALUE
|
static VALUE
|
||||||
rb_stat_init(VALUE obj, VALUE fname)
|
rb_stat_init(VALUE obj, VALUE fname)
|
||||||
{
|
{
|
||||||
struct stat st, *nst;
|
struct stat st;
|
||||||
|
|
||||||
FilePathValue(fname);
|
FilePathValue(fname);
|
||||||
fname = rb_str_encode_ospath(fname);
|
fname = rb_str_encode_ospath(fname);
|
||||||
@ -5565,13 +5566,11 @@ rb_stat_init(VALUE obj, VALUE fname)
|
|||||||
rb_sys_fail_path(fname);
|
rb_sys_fail_path(fname);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (DATA_PTR(obj)) {
|
struct rb_stat *rb_st;
|
||||||
xfree(DATA_PTR(obj));
|
TypedData_Get_Struct(obj, struct rb_stat, &stat_data_type, rb_st);
|
||||||
DATA_PTR(obj) = NULL;
|
|
||||||
}
|
rb_st->stat = st;
|
||||||
nst = ALLOC(struct stat);
|
rb_st->initialized = true;
|
||||||
*nst = st;
|
|
||||||
DATA_PTR(obj) = nst;
|
|
||||||
|
|
||||||
return Qnil;
|
return Qnil;
|
||||||
}
|
}
|
||||||
@ -5580,19 +5579,15 @@ rb_stat_init(VALUE obj, VALUE fname)
|
|||||||
static VALUE
|
static VALUE
|
||||||
rb_stat_init_copy(VALUE copy, VALUE orig)
|
rb_stat_init_copy(VALUE copy, VALUE orig)
|
||||||
{
|
{
|
||||||
struct stat *nst;
|
|
||||||
|
|
||||||
if (!OBJ_INIT_COPY(copy, orig)) return copy;
|
if (!OBJ_INIT_COPY(copy, orig)) return copy;
|
||||||
if (DATA_PTR(copy)) {
|
|
||||||
xfree(DATA_PTR(copy));
|
|
||||||
DATA_PTR(copy) = 0;
|
|
||||||
}
|
|
||||||
if (DATA_PTR(orig)) {
|
|
||||||
nst = ALLOC(struct stat);
|
|
||||||
*nst = *(struct stat*)DATA_PTR(orig);
|
|
||||||
DATA_PTR(copy) = nst;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
struct rb_stat *orig_rb_st;
|
||||||
|
TypedData_Get_Struct(orig, struct rb_stat, &stat_data_type, orig_rb_st);
|
||||||
|
|
||||||
|
struct rb_stat *copy_rb_st;
|
||||||
|
TypedData_Get_Struct(copy, struct rb_stat, &stat_data_type, copy_rb_st);
|
||||||
|
|
||||||
|
*copy_rb_st = *orig_rb_st;
|
||||||
return copy;
|
return copy;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user