Skip to content

Commit

Permalink
Fixed MemoryHeader::get_object_id.
Browse files Browse the repository at this point in the history
  • Loading branch information
brixen committed Feb 24, 2018
1 parent de5e934 commit 7978f5f
Show file tree
Hide file tree
Showing 3 changed files with 95 additions and 11 deletions.
2 changes: 1 addition & 1 deletion machine/memory/header.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ namespace rubinius {
std::atomic<uintptr_t> MemoryHeader::object_id_counter;

void MemoryHeader::bootstrap(STATE) {
object_id_counter = 0;
object_id_counter = 1;
}

void MemoryHeader::lock(STATE) {
Expand Down
80 changes: 72 additions & 8 deletions machine/memory/header.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -357,6 +357,18 @@ Object* const cUndef = reinterpret_cast<Object*>(0x22L);
return (word & type_mask()) == eObjectID;
}

uintptr_t get_object_id() const {
if(object_id_p()) {
return reinterpret_cast<uintptr_t>(word >> value_shift());
}

return 0;
}

void set_object_id(uintptr_t id) {
word = (id << value_shift()) | eObjectID;
}

bool handle_p() const {
return (word & type_mask()) == eHandle;
}
Expand Down Expand Up @@ -439,12 +451,20 @@ Object* const cUndef = reinterpret_cast<Object*>(0x22L);
return new(mem) ExtendedHeader(h, eh, eh->size());
}

static ExtendedHeader* create_object_id(const MemoryFlags h) {
return create(h);
static ExtendedHeader* create_object_id(const MemoryFlags h, uintptr_t id) {
ExtendedHeader* nh = create(h);
nh->words[0].set_object_id(id);

return nh;
}

static ExtendedHeader* create_object_id(const MemoryFlags h, const ExtendedHeader* eh) {
return create(h, eh);
static ExtendedHeader* create_object_id(
const MemoryFlags h, const ExtendedHeader* eh, uintptr_t id)
{
ExtendedHeader* nh = create(h, eh);
nh->words[eh->size()].set_object_id(id);

return nh;
}

static ExtendedHeader* create_handle(const MemoryFlags h) {
Expand Down Expand Up @@ -498,6 +518,24 @@ Object* const cUndef = reinterpret_cast<Object*>(0x22L);
return nullptr;
}

uintptr_t get_object_id() const {
for(int i = 0; i < size(); i++) {
if(uintptr_t id = words[i].get_object_id()) {
return id;
}
}

return 0;
}

void set_object_id(uintptr_t id) {
for(int i = 0; i < size(); i++) {
if(words[i].object_id_p()) {
words[i].set_object_id(id);
}
}
}

uintptr_t get_referenced() const {
for(int i = 0; i < size(); i++) {
if(uintptr_t refcount = words[i].get_referenced()) {
Expand Down Expand Up @@ -704,7 +742,7 @@ Object* const cUndef = reinterpret_cast<Object*>(0x22L);
unsigned int referenced() const {
if(extended_p()) {
ExtendedHeader* eh = extended_header();
uintptr_t refcount = referenced_field.get(extended_header()->header);
uintptr_t refcount = referenced_field.get(eh->header);

if(refcount < max_referenced()) {
return refcount;
Expand Down Expand Up @@ -763,7 +801,24 @@ Object* const cUndef = reinterpret_cast<Object*>(0x22L);
}

uintptr_t object_id() const {
return get(object_id_field);
if(extended_p()) {
ExtendedHeader* eh = extended_header();
uintptr_t id = object_id_field.get(eh->header);

if(id < max_object_id()) {
return id;
} else {
uintptr_t ext_id = eh->get_object_id();

if(ext_id > 0) {
return ext_id;
} else {
return id;
}
}
} else {
return object_id_field.get(header);
}
}

unsigned int type_specific() const {
Expand Down Expand Up @@ -795,7 +850,8 @@ Object* const cUndef = reinterpret_cast<Object*>(0x22L);
} else if(id < max_object_id()) {
eh = ExtendedHeader::create_copy(object_id_field.set(hh->header, id), hh);
} else {
eh = ExtendedHeader::create_object_id(object_id_field.set(hh->header, id), hh);
eh = ExtendedHeader::create_object_id(
object_id_field.set(hh->header, max_object_id()), hh, id);
}

MemoryFlags nh = extended_flags(eh);
Expand All @@ -806,10 +862,18 @@ Object* const cUndef = reinterpret_cast<Object*>(0x22L);
} else {
if(object_id_field.get(h) > 0) {
return object_id_field.get(h);
} else {
} else if(id < max_object_id()) {
MemoryFlags nh = object_id_field.set(h, id);

if(header.compare_exchange_strong(h, nh)) return id;
} else {
ExtendedHeader* eh = ExtendedHeader::create_object_id(
object_id_field.set(h, max_object_id()), id);
MemoryFlags nh = extended_flags(eh);

if(header.compare_exchange_strong(h, nh)) return id;

eh->delete_header();
}
}
}
Expand Down
24 changes: 22 additions & 2 deletions machine/test/test_memory_header.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ class TestMemoryHeader : public CxxTest::TestSuite, public VMTest {
h.header = 0x3ffcL;

TS_ASSERT_EQUALS(h.thread_id(), 0xfff);
TS_ASSERT_EQUALS(h.max_thread_id(), 0xfff);
TS_ASSERT_EQUALS(MemoryHeader::max_thread_id(), 0xfff);
}

void test_memory_header_region() {
Expand Down Expand Up @@ -124,6 +124,10 @@ class TestMemoryHeader : public CxxTest::TestSuite, public VMTest {
h.add_reference();

TS_ASSERT_EQUALS(h.referenced(), i+1);

if(i > 15) {
TS_ASSERT(h.extended_p());
}
}
}

Expand Down Expand Up @@ -175,7 +179,23 @@ class TestMemoryHeader : public CxxTest::TestSuite, public VMTest {
h.header = 0x3ffffc0000000000L;
TS_ASSERT_EQUALS(h.object_id(), 0xfffffL);

TS_ASSERT_EQUALS(h.max_object_id(), 0xfffffL);
TS_ASSERT_EQUALS(MemoryHeader::max_object_id(), 0xfffffL);
}

void test_memory_header_set_object_id() {
MemoryHeader::object_id_counter = 21;

h.get_object_id();

TS_ASSERT_EQUALS(h.object_id(), 0x15);

MemoryHeader::object_id_counter = MemoryHeader::max_object_id() + 10;

h.header = 0;
h.get_object_id();

TS_ASSERT(h.extended_p());
TS_ASSERT_EQUALS(h.object_id(), MemoryHeader::max_object_id() + 10);
}

void test_memory_header_type_specific() {
Expand Down

0 comments on commit 7978f5f

Please sign in to comment.