constant_pool: Use std::span
to manage pool
Simplifies some raw pointer arithmetic and type-usage into the new `ConstantT` type.
This commit is contained in:
parent
5d9b720189
commit
a5318c775c
2 changed files with 18 additions and 14 deletions
|
@ -14,22 +14,22 @@
|
||||||
namespace Dynarmic::Backend::X64 {
|
namespace Dynarmic::Backend::X64 {
|
||||||
|
|
||||||
ConstantPool::ConstantPool(BlockOfCode& code, size_t size)
|
ConstantPool::ConstantPool(BlockOfCode& code, size_t size)
|
||||||
: code(code), pool_size(size) {
|
: code(code), insertion_point(0) {
|
||||||
code.int3();
|
code.int3();
|
||||||
code.align(align_size);
|
code.align(align_size);
|
||||||
pool_begin = reinterpret_cast<u8*>(code.AllocateFromCodeSpace(size));
|
pool = std::span<ConstantT>(
|
||||||
current_pool_ptr = pool_begin;
|
reinterpret_cast<ConstantT*>(code.AllocateFromCodeSpace(size)), size / align_size);
|
||||||
}
|
}
|
||||||
|
|
||||||
Xbyak::Address ConstantPool::GetConstant(const Xbyak::AddressFrame& frame, u64 lower, u64 upper) {
|
Xbyak::Address ConstantPool::GetConstant(const Xbyak::AddressFrame& frame, u64 lower, u64 upper) {
|
||||||
const auto constant = std::make_pair(lower, upper);
|
const auto constant = ConstantT(lower, upper);
|
||||||
auto iter = constant_info.find(constant);
|
auto iter = constant_info.find(constant);
|
||||||
if (iter == constant_info.end()) {
|
if (iter == constant_info.end()) {
|
||||||
ASSERT(static_cast<size_t>(current_pool_ptr - pool_begin) < pool_size);
|
ASSERT(insertion_point < pool.size());
|
||||||
std::memcpy(current_pool_ptr, &lower, sizeof(u64));
|
ConstantT& target_constant = pool[insertion_point];
|
||||||
std::memcpy(current_pool_ptr + sizeof(u64), &upper, sizeof(u64));
|
target_constant = constant;
|
||||||
iter = constant_info.emplace(constant, current_pool_ptr).first;
|
iter = constant_info.emplace(constant, &target_constant).first;
|
||||||
current_pool_ptr += align_size;
|
++insertion_point;
|
||||||
}
|
}
|
||||||
return frame[code.rip + iter->second];
|
return frame[code.rip + iter->second];
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,6 +6,8 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <bit>
|
#include <bit>
|
||||||
|
#include <cstddef>
|
||||||
|
#include <span>
|
||||||
#include <utility>
|
#include <utility>
|
||||||
|
|
||||||
#include <mcl/stdint.hpp>
|
#include <mcl/stdint.hpp>
|
||||||
|
@ -29,18 +31,20 @@ public:
|
||||||
private:
|
private:
|
||||||
static constexpr size_t align_size = 16; // bytes
|
static constexpr size_t align_size = 16; // bytes
|
||||||
|
|
||||||
|
using ConstantT = std::pair<u64, u64>;
|
||||||
|
static_assert(sizeof(ConstantT) == align_size);
|
||||||
|
|
||||||
struct ConstantHash {
|
struct ConstantHash {
|
||||||
std::size_t operator()(const std::pair<u64, u64>& constant) const noexcept {
|
std::size_t operator()(const ConstantT& constant) const noexcept {
|
||||||
return constant.first ^ std::rotl<u64>(constant.second, 1);
|
return constant.first ^ std::rotl<u64>(constant.second, 1);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
tsl::robin_map<std::pair<u64, u64>, void*, ConstantHash> constant_info;
|
tsl::robin_map<ConstantT, void*, ConstantHash> constant_info;
|
||||||
|
|
||||||
BlockOfCode& code;
|
BlockOfCode& code;
|
||||||
size_t pool_size;
|
std::span<ConstantT> pool;
|
||||||
u8* pool_begin;
|
std::size_t insertion_point;
|
||||||
u8* current_pool_ptr;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace Dynarmic::Backend::X64
|
} // namespace Dynarmic::Backend::X64
|
||||||
|
|
Loading…
Reference in a new issue