Attempt to emulate reserved load/store more closely. can't do anything for stores of the same value that are done via a non-reserved store to a reserved location

uses a bitmap that splits up the memory space into 65k blocks per bit.  Currently is using the guest virtual address but should be using physical addresses instead.

Currently if a guest does a reserve on a location and then a reserved store to a totally different location we trigger a breakpoint. This should never happen
Also removed the NEGATED_MUL_blah operations. They weren't necessary, nothing special is needed for the negated result variants.

Added a log message for when watched physical memory has a race, it just would be nice to know when it happens and in what games.
This commit is contained in:
chss95cs@gmail.com
2023-04-15 16:06:07 -04:00
parent 5e0c67438c
commit 7fb4b4cd41
12 changed files with 353 additions and 187 deletions

View File

@@ -1281,6 +1281,25 @@ Value* HIRBuilder::Load(Value* address, TypeName type, uint32_t load_flags) {
return i->dest;
}
Value* HIRBuilder::LoadWithReserve(Value* address, TypeName type) {
ASSERT_ADDRESS_TYPE(address);
Instr* i = AppendInstr(OPCODE_RESERVED_LOAD_info, 0, AllocValue(type));
i->set_src1(address);
i->src2.value = i->src3.value = NULL;
return i->dest;
}
Value* HIRBuilder::StoreWithReserve(Value* address, Value* value,
TypeName type) {
ASSERT_ADDRESS_TYPE(address);
Instr* i = AppendInstr(OPCODE_RESERVED_STORE_info, 0, AllocValue(INT8_TYPE));
i->set_src1(address);
i->set_src2(value);
i->src3.value = NULL;
return i->dest;
}
void HIRBuilder::Store(Value* address, Value* value, uint32_t store_flags) {
ASSERT_ADDRESS_TYPE(address);
Instr* i = AppendInstr(OPCODE_STORE_info, store_flags);
@@ -1739,30 +1758,6 @@ Value* HIRBuilder::MulSub(Value* value1, Value* value2, Value* value3) {
return i->dest;
}
Value* HIRBuilder::NegatedMulAdd(Value* value1, Value* value2, Value* value3) {
ASSERT_TYPES_EQUAL(value1, value2);
ASSERT_TYPES_EQUAL(value1, value3);
Instr* i =
AppendInstr(OPCODE_NEGATED_MUL_ADD_info, 0, AllocValue(value1->type));
i->set_src1(value1);
i->set_src2(value2);
i->set_src3(value3);
return i->dest;
}
Value* HIRBuilder::NegatedMulSub(Value* value1, Value* value2, Value* value3) {
ASSERT_TYPES_EQUAL(value1, value2);
ASSERT_TYPES_EQUAL(value1, value3);
Instr* i =
AppendInstr(OPCODE_NEGATED_MUL_SUB_info, 0, AllocValue(value1->type));
i->set_src1(value1);
i->set_src2(value2);
i->set_src3(value3);
return i->dest;
}
Value* HIRBuilder::Neg(Value* value) {
Instr* i = AppendInstr(OPCODE_NEG_info, 0, AllocValue(value->type));
i->set_src1(value);

View File

@@ -189,6 +189,9 @@ class HIRBuilder {
uint32_t store_flags = 0);
Value* Load(Value* address, TypeName type, uint32_t load_flags = 0);
// create a reserve on an address,
Value* LoadWithReserve(Value* address, TypeName type);
Value* StoreWithReserve(Value* address, Value* value, TypeName type);
Value* LoadVectorLeft(Value* address);
Value* LoadVectorRight(Value* address);
@@ -242,10 +245,7 @@ class HIRBuilder {
Value* Div(Value* value1, Value* value2, uint32_t arithmetic_flags = 0);
Value* MulAdd(Value* value1, Value* value2, Value* value3); // (1 * 2) + 3
Value* MulSub(Value* value1, Value* value2, Value* value3); // (1 * 2) - 3
Value* NegatedMulAdd(Value* value1, Value* value2,
Value* value3); // -((1 * 2) + 3)
Value* NegatedMulSub(Value* value1, Value* value2,
Value* value3); // -((1 * 2) - 3)
Value* Neg(Value* value);
Value* Abs(Value* value);
Value* Sqrt(Value* value);

View File

@@ -248,9 +248,7 @@ enum Opcode {
OPCODE_MUL_HI, // TODO(benvanik): remove this and add INT128 type.
OPCODE_DIV,
OPCODE_MUL_ADD,
OPCODE_NEGATED_MUL_ADD,
OPCODE_MUL_SUB,
OPCODE_NEGATED_MUL_SUB,
OPCODE_NEG,
OPCODE_ABS,
OPCODE_SQRT,
@@ -292,7 +290,10 @@ enum Opcode {
// as we already have OPCODE_ROUND. round double to float (
// ppc "single" fpu instruction result rounding behavior )
OPCODE_SET_NJM,
OPCODE_DELAY_EXECUTION, //for db16cyc
OPCODE_DELAY_EXECUTION, // for db16cyc
OPCODE_RESERVED_LOAD,
OPCODE_RESERVED_STORE,
__OPCODE_MAX_VALUE, // Keep at end.
};

View File

@@ -218,7 +218,12 @@ DEFINE_OPCODE(
"context_barrier",
OPCODE_SIG_X,
0)
DEFINE_OPCODE(OPCODE_DELAY_EXECUTION, "delay_execution", OPCODE_SIG_X, 0)
DEFINE_OPCODE(
OPCODE_DELAY_EXECUTION,
"delay_execution",
OPCODE_SIG_X,
0)
DEFINE_OPCODE(
OPCODE_LOAD_MMIO,
"load_mmio",
@@ -453,19 +458,6 @@ DEFINE_OPCODE(
OPCODE_SIG_V_V_V_V,
OPCODE_FLAG_DISALLOW_CONSTANT_FOLDING)
DEFINE_OPCODE(
OPCODE_NEGATED_MUL_ADD,
"negated_mul_add",
OPCODE_SIG_V_V_V_V,
OPCODE_FLAG_DISALLOW_CONSTANT_FOLDING)
DEFINE_OPCODE(
OPCODE_NEGATED_MUL_SUB,
"negated_mul_sub",
OPCODE_SIG_V_V_V_V,
OPCODE_FLAG_DISALLOW_CONSTANT_FOLDING)
DEFINE_OPCODE(
OPCODE_NEG,
"neg",
@@ -719,3 +711,15 @@ DEFINE_OPCODE(
"storev_right",
OPCODE_SIG_X_V_V,
OPCODE_FLAG_MEMORY)
DEFINE_OPCODE(
OPCODE_RESERVED_LOAD,
"reserved_load",
OPCODE_SIG_V_V,
OPCODE_FLAG_MEMORY)
DEFINE_OPCODE(
OPCODE_RESERVED_STORE,
"reserved_store",
OPCODE_SIG_V_V_V,
OPCODE_FLAG_MEMORY)