Showing the changes to src/vm/vm_memory.cpp (1 of 6 files). Show all
Unified · Split
| @@ -81,13 +81,17 @@ void disvm::runtime::destroy_memory(const type_descriptor_t &type_desc, void *da · 80 unmodified lines | |||
| 81 | 81 | ||
| 82 | void disvm::runtime::inc_ref_count_in_memory(const type_descriptor_t &type_desc, void *data) | 82 | void disvm::runtime::inc_ref_count_in_memory(const type_descriptor_t &type_desc, void *data) |
| 83 | { | 83 | { |
| 84 | assert(data != nullptr); | 84 | if (type_desc.size_in_bytes == 0) |
| 85 | return; | ||
| 86 | |||
| 85 | enum_pointer_fields(type_desc, data, add_ref_pointer_field); | 87 | enum_pointer_fields(type_desc, data, add_ref_pointer_field); |
| 86 | } | 88 | } |
| 87 | 89 | ||
| 88 | void disvm::runtime::dec_ref_count_in_memory(const type_descriptor_t &type_desc, void *data) | 90 | void disvm::runtime::dec_ref_count_in_memory(const type_descriptor_t &type_desc, void *data) |
| 89 | { | 91 | { |
| 90 | assert(data != nullptr); | 92 | if (type_desc.size_in_bytes == 0) |
| 93 | return; | ||
| 94 | |||
| 91 | enum_pointer_fields(type_desc, data, dec_ref_and_free_pointer_field); | 95 | enum_pointer_fields(type_desc, data, dec_ref_and_free_pointer_field); |
| 92 | } | 96 | } |
| 93 | 97 | ||
| @@ -104,8 +108,6 @@ void disvm::runtime::dec_ref_count_and_free(vm_alloc_t *alloc) · 10 unmodified lines | |||
| 104 | void disvm::runtime::enum_pointer_fields(const type_descriptor_t &type_desc, void *data, pointer_field_callback_t callback) | 108 | void disvm::runtime::enum_pointer_fields(const type_descriptor_t &type_desc, void *data, pointer_field_callback_t callback) |
| 105 | { | 109 | { |
| 106 | assert(data != nullptr && callback != nullptr); | 110 | assert(data != nullptr && callback != nullptr); |
| 107 | if (type_desc.size_in_bytes == 0) | ||
| 108 | return; | ||
| 109 | 111 | ||
| 110 | auto offset_accum = std::size_t{ 0 }; | 112 | auto offset_accum = std::size_t{ 0 }; |
| 111 | auto memory = reinterpret_cast<word_t *>(data); | 113 | auto memory = reinterpret_cast<word_t *>(data); |
| @@ -130,6 +132,33 @@ void disvm::runtime::enum_pointer_fields(const type_descriptor_t &type_desc, voi · 18 unmodified lines | |||
| 130 | } | 132 | } |
| 131 | } | 133 | } |
| 132 | 134 | ||
| 135 | void disvm::runtime::enum_pointer_fields(const type_descriptor_t &type_desc, void *data, pointer_field_callback_ext_t callback, void *cxt) | ||
| 136 | { | ||
| 137 | assert(data != nullptr && callback != nullptr); | ||
| 138 | |||
| 139 | auto offset_accum = std::size_t{ 0 }; | ||
| 140 | auto memory = reinterpret_cast<word_t *>(data); | ||
| 141 | for (auto i = word_t{ 0 }; i < type_desc.map_in_bytes; ++i, memory += 8, offset_accum += (8 * sizeof(pointer_t))) | ||
| 142 | { | ||
| 143 | const auto words8 = type_desc.pointer_map[i]; | ||
| 144 | assert(sizeof(words8) == 1); | ||
| 145 | if (words8 == 0) | ||
| 146 | continue; | ||
| 147 | |||
| 148 | const auto flags = std::bitset<sizeof(words8) * 8>{ words8 }; | ||
| 149 | |||
| 150 | // Enumerating the flags in reverse order so memory access is sequential. | ||
| 151 | if (flags[7] && (memory[0] != runtime_constants::nil)) callback(reinterpret_cast<pointer_t>(memory[0]), cxt); | ||
| 152 | if (flags[6] && (memory[1] != runtime_constants::nil)) callback(reinterpret_cast<pointer_t>(memory[1]), cxt); | ||
| 153 | if (flags[5] && (memory[2] != runtime_constants::nil)) callback(reinterpret_cast<pointer_t>(memory[2]), cxt); | ||
| 154 | if (flags[4] && (memory[3] != runtime_constants::nil)) callback(reinterpret_cast<pointer_t>(memory[3]), cxt); | ||
| 155 | if (flags[3] && (memory[4] != runtime_constants::nil)) callback(reinterpret_cast<pointer_t>(memory[4]), cxt); | ||
| 156 | if (flags[2] && (memory[5] != runtime_constants::nil)) callback(reinterpret_cast<pointer_t>(memory[5]), cxt); | ||
| 157 | if (flags[1] && (memory[6] != runtime_constants::nil)) callback(reinterpret_cast<pointer_t>(memory[6]), cxt); | ||
| 158 | if (flags[0] && (memory[7] != runtime_constants::nil)) callback(reinterpret_cast<pointer_t>(memory[7]), cxt); | ||
| 159 | } | ||
| 160 | } | ||
| 161 | |||
| 133 | void disvm::runtime::enum_pointer_fields_with_offset(const type_descriptor_t &type_desc, void *data, pointer_field_offset_callback_t callback) | 162 | void disvm::runtime::enum_pointer_fields_with_offset(const type_descriptor_t &type_desc, void *data, pointer_field_offset_callback_t callback) |
| 134 | { | 163 | { |
| 135 | assert(data != nullptr && callback != nullptr); | 164 | assert(data != nullptr && callback != nullptr); |