Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions common.mk
Original file line number Diff line number Diff line change
Expand Up @@ -1750,8 +1750,8 @@ $(UNICODE_EMOJI_FILES):
$(Q) $(MAKEDIRS) "$(UNICODE_SRC_EMOJI_DATA_DIR)"
$(Q) $(UNICODE_EMOJI_DOWNLOAD) $@

$(srcdir)/lib/unicode_normalize/tables.rb: \
$(UNICODE_SRC_DATA_DIR)/$(HAVE_BASERUBY:yes=.unicode-tables.time)
$(srcdir)/lib/unicode_normalize/$(HAVE_BASERUBY:yes=tables.rb): \
$(UNICODE_SRC_DATA_DIR)/.unicode-tables.time

$(UNICODE_SRC_DATA_DIR)/$(ALWAYS_UPDATE_UNICODE:yes=.unicode-tables.time): \
$(UNICODE_FILES) $(UNICODE_PROPERTY_FILES) \
Expand Down
2 changes: 1 addition & 1 deletion ext/socket/raddrinfo.c
Original file line number Diff line number Diff line change
Expand Up @@ -752,7 +752,7 @@ rb_getnameinfo(const struct sockaddr *sa, socklen_t salen,
int err = 0, gni_errno = 0;

if (GETNAMEINFO_WONT_BLOCK(host, serv, flags)) {
return getnameinfo(sa, salen, host, hostlen, serv, servlen, flags);
return getnameinfo(sa, salen, host, (socklen_t)hostlen, serv, (socklen_t)servlen, flags);
}

start:
Expand Down
1 change: 1 addition & 0 deletions shape.h
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,7 @@ RSHAPE_LEN(shape_id_t shape_id)
static inline attr_index_t
RSHAPE_INDEX(shape_id_t shape_id)
{
RUBY_ASSERT(RSHAPE_LEN(shape_id) > 0);
return RSHAPE_LEN(shape_id) - 1;
}

Expand Down
52 changes: 47 additions & 5 deletions string.c
Original file line number Diff line number Diff line change
Expand Up @@ -9693,11 +9693,53 @@ rb_str_each_line(int argc, VALUE *argv, VALUE str)

/*
* call-seq:
* lines(Line_sep = $/, chomp: false) -> array_of_strings
*
* Forms substrings ("lines") of +self+ according to the given arguments
* (see String#each_line for details); returns the lines in an array.
*
* lines(record_separator = $/, chomp: false) -> array_of_strings
*
* Returns substrings ("lines") of +self+
* according to the given arguments:
*
* s = <<~EOT
* This is the first line.
* This is line two.
*
* This is line four.
* This is line five.
* EOT
*
* With the default argument values:
*
* $/ # => "\n"
* s.lines
* # =>
* ["This is the first line.\n",
* "This is line two.\n",
* "\n",
* "This is line four.\n",
* "This is line five.\n"]
*
* With a different +record_separator+:
*
* record_separator = ' is '
* s.lines(record_separator)
* # =>
* ["This is ",
* "the first line.\nThis is ",
* "line two.\n\nThis is ",
* "line four.\nThis is ",
* "line five.\n"]
*
* With keyword argument +chomp+ as +true+,
* removes the trailing newline from each line:
*
* s.lines(chomp: true)
* # =>
* ["This is the first line.",
* "This is line two.",
* "",
* "This is line four.",
* "This is line five."]
*
* Related: see {Converting to Non-String}[rdoc-ref:String@Converting+to+Non--5CString].
*/

static VALUE
Expand Down
134 changes: 42 additions & 92 deletions variable.c
Original file line number Diff line number Diff line change
Expand Up @@ -1895,57 +1895,8 @@ rb_obj_copy_fields_to_hash_table(VALUE obj, st_table *table)
rb_field_foreach(obj, rb_obj_copy_ivs_to_hash_table_i, (st_data_t)table, false);
}

attr_index_t
rb_obj_ivar_set(VALUE obj, ID id, VALUE val)
{
shape_id_t current_shape_id = RBASIC_SHAPE_ID(obj);

if (UNLIKELY(rb_shape_too_complex_p(current_shape_id))) {
goto too_complex;
}

attr_index_t index;
if (!rb_shape_get_iv_index(current_shape_id, id, &index)) {
index = RSHAPE_LEN(current_shape_id);
if (index >= SHAPE_MAX_FIELDS) {
rb_raise(rb_eArgError, "too many instance variables");
}

shape_id_t next_shape_id = rb_shape_transition_add_ivar(obj, id);
if (UNLIKELY(rb_shape_too_complex_p(next_shape_id))) {
current_shape_id = rb_evict_fields_to_hash(obj);
goto too_complex;
}
else if (UNLIKELY(RSHAPE_CAPACITY(next_shape_id) != RSHAPE_CAPACITY(current_shape_id))) {
RUBY_ASSERT(RSHAPE_CAPACITY(next_shape_id) > RSHAPE_CAPACITY(current_shape_id));
rb_ensure_iv_list_size(obj, RSHAPE_CAPACITY(current_shape_id), RSHAPE_CAPACITY(next_shape_id));
}

RUBY_ASSERT(RSHAPE_TYPE_P(next_shape_id, SHAPE_IVAR),
"next_shape_id: 0x%" PRIx32 " RSHAPE_TYPE(next_shape_id): %d",
next_shape_id, (int)RSHAPE_TYPE(next_shape_id));
RUBY_ASSERT(index == (RSHAPE_INDEX(next_shape_id)));
RBASIC_SET_SHAPE_ID(obj, next_shape_id);
}

VALUE *table = ROBJECT_FIELDS(obj);
RB_OBJ_WRITE(obj, &table[index], val);

return index;

too_complex:
{
RUBY_ASSERT(rb_shape_obj_too_complex_p(obj));

st_table *table = ROBJECT_FIELDS_HASH(obj);
st_insert(table, (st_data_t)id, (st_data_t)val);
RB_OBJ_WRITTEN(obj, Qundef, val);
}
return 0;
}

static void
obj_field_set(VALUE obj, shape_id_t target_shape_id, VALUE val)
static attr_index_t
obj_field_set(VALUE obj, shape_id_t target_shape_id, ID field_name, VALUE val)
{
shape_id_t current_shape_id = RBASIC_SHAPE_ID(obj);

Expand All @@ -1954,31 +1905,44 @@ obj_field_set(VALUE obj, shape_id_t target_shape_id, VALUE val)
current_shape_id = rb_evict_fields_to_hash(obj);
}

st_table *table = ROBJECT_FIELDS_HASH(obj);

if (RSHAPE_LEN(target_shape_id) > RSHAPE_LEN(current_shape_id)) {
RBASIC_SET_SHAPE_ID(obj, target_shape_id);
}

RUBY_ASSERT(RSHAPE_EDGE_NAME(target_shape_id));
st_insert(table, (st_data_t)RSHAPE_EDGE_NAME(target_shape_id), (st_data_t)val);
if (!field_name) {
field_name = RSHAPE_EDGE_NAME(target_shape_id);
RUBY_ASSERT(field_name);
}

st_insert(ROBJECT_FIELDS_HASH(obj), (st_data_t)field_name, (st_data_t)val);
RB_OBJ_WRITTEN(obj, Qundef, val);

return ATTR_INDEX_NOT_SET;
}
else {
attr_index_t index = RSHAPE_INDEX(target_shape_id);
if (index >= RSHAPE_CAPACITY(current_shape_id)) {
rb_ensure_iv_list_size(obj, RSHAPE_CAPACITY(current_shape_id), RSHAPE_CAPACITY(target_shape_id));
}

if (RSHAPE_LEN(target_shape_id) > RSHAPE_LEN(current_shape_id)) {
if (index >= RSHAPE_LEN(current_shape_id)) {
if (UNLIKELY(index >= RSHAPE_CAPACITY(current_shape_id))) {
rb_ensure_iv_list_size(obj, RSHAPE_CAPACITY(current_shape_id), RSHAPE_CAPACITY(target_shape_id));
}
RBASIC_SET_SHAPE_ID(obj, target_shape_id);
}

VALUE *table = ROBJECT_FIELDS(obj);
RB_OBJ_WRITE(obj, &table[index], val);
RB_OBJ_WRITE(obj, &ROBJECT_FIELDS(obj)[index], val);

return index;
}
}

attr_index_t
rb_obj_ivar_set(VALUE obj, ID id, VALUE val)
{
bool dontcare;
shape_id_t target_shape_id = generic_shape_ivar(obj, id, &dontcare);
return obj_field_set(obj, target_shape_id, id, val);
}

/* Set the instance variable +val+ on object +obj+ at ivar name +id+.
* This function only works with T_OBJECT objects, so make sure
* +obj+ is of type T_OBJECT before using this function.
Expand Down Expand Up @@ -2052,7 +2016,7 @@ rb_obj_field_set(VALUE obj, shape_id_t target_shape_id, ID field_name, VALUE val
{
switch (BUILTIN_TYPE(obj)) {
case T_OBJECT:
obj_field_set(obj, target_shape_id, val);
obj_field_set(obj, target_shape_id, field_name, val);
break;
case T_CLASS:
case T_MODULE:
Expand Down Expand Up @@ -4571,43 +4535,30 @@ rb_iv_set(VALUE obj, const char *name, VALUE val)
static bool
class_fields_ivar_set(VALUE klass, VALUE fields_obj, ID id, VALUE val, bool concurrent, VALUE *new_fields_obj)
{
bool existing = true;
const VALUE original_fields_obj = fields_obj;
fields_obj = original_fields_obj ? original_fields_obj : rb_imemo_fields_new(klass, 1);

shape_id_t current_shape_id = RBASIC_SHAPE_ID(fields_obj);
shape_id_t next_shape_id = current_shape_id;

if (UNLIKELY(rb_shape_too_complex_p(current_shape_id))) {
goto too_complex;
}

attr_index_t index;
if (!rb_shape_get_iv_index(current_shape_id, id, &index)) {
existing = false;

index = RSHAPE_LEN(current_shape_id);
if (index >= SHAPE_MAX_FIELDS) {
rb_raise(rb_eArgError, "too many instance variables");
}

next_shape_id = rb_shape_transition_add_ivar(fields_obj, id);
if (UNLIKELY(rb_shape_too_complex_p(next_shape_id))) {
fields_obj = imemo_fields_complex_from_obj(klass, fields_obj, next_shape_id);
goto too_complex;
}
bool new_ivar;
shape_id_t next_shape_id = generic_shape_ivar(fields_obj, id, &new_ivar);

attr_index_t next_capacity = RSHAPE_CAPACITY(next_shape_id);
attr_index_t current_capacity = RSHAPE_CAPACITY(current_shape_id);
if (UNLIKELY(rb_shape_too_complex_p(next_shape_id))) {
fields_obj = imemo_fields_complex_from_obj(klass, fields_obj, next_shape_id);
goto too_complex;
}

if (next_capacity > current_capacity) {
attr_index_t index = RSHAPE_INDEX(next_shape_id);
if (new_ivar) {
if (index >= RSHAPE_CAPACITY(current_shape_id)) {
// We allocate a new fields_obj even when concurrency isn't a concern
// so that we're embedded as long as possible.
fields_obj = imemo_fields_copy_capa(klass, fields_obj, next_capacity);
fields_obj = imemo_fields_copy_capa(klass, fields_obj, RSHAPE_CAPACITY(next_shape_id));
}

RUBY_ASSERT(RSHAPE(next_shape_id)->type == SHAPE_IVAR);
RUBY_ASSERT(index == (RSHAPE_LEN(next_shape_id) - 1));
}

VALUE *fields = rb_imemo_fields_ptr(fields_obj);
Expand All @@ -4624,12 +4575,12 @@ class_fields_ivar_set(VALUE klass, VALUE fields_obj, ID id, VALUE val, bool conc
RB_OBJ_WRITE(fields_obj, &fields[index], val);
}

if (!existing) {
if (new_ivar) {
RBASIC_SET_SHAPE_ID(fields_obj, next_shape_id);
}

*new_fields_obj = fields_obj;
return existing;
return new_ivar;

too_complex:
{
Expand All @@ -4641,7 +4592,7 @@ class_fields_ivar_set(VALUE klass, VALUE fields_obj, ID id, VALUE val, bool conc
}

st_table *table = rb_imemo_fields_complex_tbl(fields_obj);
existing = st_insert(table, (st_data_t)id, (st_data_t)val);
new_ivar = !st_insert(table, (st_data_t)id, (st_data_t)val);
RB_OBJ_WRITTEN(fields_obj, Qundef, val);

if (fields_obj != original_fields_obj) {
Expand All @@ -4650,7 +4601,7 @@ class_fields_ivar_set(VALUE klass, VALUE fields_obj, ID id, VALUE val, bool conc
}

*new_fields_obj = fields_obj;
return existing;
return new_ivar;
}

bool
Expand All @@ -4664,7 +4615,7 @@ rb_class_ivar_set(VALUE obj, ID id, VALUE val)
const VALUE original_fields_obj = RCLASS_WRITABLE_FIELDS_OBJ(obj);
VALUE new_fields_obj = 0;

bool existing = class_fields_ivar_set(obj, original_fields_obj, id, val, rb_multi_ractor_p(), &new_fields_obj);
bool new_ivar = class_fields_ivar_set(obj, original_fields_obj, id, val, rb_multi_ractor_p(), &new_fields_obj);

if (new_fields_obj != original_fields_obj) {
RCLASS_WRITABLE_SET_FIELDS_OBJ(obj, new_fields_obj);
Expand All @@ -4676,7 +4627,7 @@ rb_class_ivar_set(VALUE obj, ID id, VALUE val)
// Perhaps INVALID_SHAPE_ID?
RBASIC_SET_SHAPE_ID(obj, RBASIC_SHAPE_ID(new_fields_obj));

return !existing;
return new_ivar;
}

void
Expand Down Expand Up @@ -4713,4 +4664,3 @@ rb_const_lookup(VALUE klass, ID id)
{
return const_lookup(RCLASS_CONST_TBL(klass), id);
}

9 changes: 4 additions & 5 deletions win32/Makefile.sub
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,9 @@ tooldir = $(srcdir)/tool
MFLAGS=-l
!endif

!if "$(BASERUBY)" == ""
!if "$(HAVE_BASERUBY)" == "no"
BASERUBY =
!else if "$(BASERUBY)" == ""
# After `nmake`, just built `ruby.exe` exists in the build directory,
# and is searched first prior to $PATH. Assume that no ruby
# executable in $(tooldir).
Expand All @@ -28,7 +30,7 @@ MFLAGS=-l
! endif
! if [del baseruby.mk 2> nul]
! endif
!else if "$(BASERUBY)" == "no" || [($(BASERUBY) -eexit) > nul 2> nul]
!else if [($(BASERUBY) $(tooldir)/missing-baseruby.bat) > nul 2> nul]
BASERUBY =
!endif
!if "$(BASERUBY)" == ""
Expand Down Expand Up @@ -122,9 +124,6 @@ TOUCH = $(BASERUBY) -run -e touch --
CP = copy > nul
MV = move > nul
RM1 = del /f /q
!if !defined(BASERUBY)
BASERUBY = ruby
!endif
!if !defined(TEST_RUNNABLE)
TEST_RUNNABLE = yes
!endif
Expand Down
9 changes: 5 additions & 4 deletions win32/configure.bat
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ if "%1" == "--disable-rubygems" goto :disable-rubygems
if "%1" == "--extout" goto :extout
if "%1" == "--path" goto :path
if "%1" == "--with-baseruby" goto :baseruby
if "%1" == "--without-baseruby" goto :baseruby
if "%1" == "--without-baseruby" goto :nobaseruby
if "%1" == "--with-ntver" goto :ntver
if "%1" == "--with-libdir" goto :libdir
if "%1" == "--with-git" goto :git
Expand Down Expand Up @@ -208,14 +208,16 @@ goto :loop ;
shift
goto :loop ;
:baseruby
echo>> %config_make% HAVE_BASERUBY =
echo>> %config_make% BASERUBY = %~2
echo>>%confargs% %1=%2 \
shift
shift
goto :loop ;
:nobaseruby
echo>> %config_make% HAVE_BASERUBY = no
echo>>%confargs% %1=%2 \
echo>> %config_make% BASERUBY =
echo>>%confargs% %1 \
shift
goto :loop ;
:libdir
Expand All @@ -238,8 +240,7 @@ goto :loop ;
goto :loop ;
:gmp
echo>> %config_make% WITH_GMP = yes
echo>>%confargs% %1=1 \
shift
echo>>%confargs% %1 \
shift
goto :loop ;
:gmp-dir
Expand Down
2 changes: 1 addition & 1 deletion win32/setup.mak
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ prefix = $(prefix:\=/)
<<
@type $(config_make) >>$(MAKEFILE)
@del $(config_make) > nul
!if defined(BASERUBY)
!if "$(HAVE_BASERUBY)" != "no" && "$(BASERUBY)" != ""
$(BASERUBY:/=\) "$(srcdir)/tool/missing-baseruby.bat"
!endif
!if "$(WITH_GMP)" != "no"
Expand Down
Loading