mirror of
https://git.wownero.com/wownero/RandomWOW.git
synced 2025-01-03 05:38:54 +00:00
Implemented branches in the interpreter
Fixed x86 immediate encoding
This commit is contained in:
parent
174754cb2b
commit
007f8599b9
@ -302,13 +302,13 @@ namespace RandomX {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Instruction::h_COND_R(std::ostream& os) const {
|
void Instruction::h_COND_R(std::ostream& os) const {
|
||||||
os << "r" << (int)dst << ", " << condition((mod >> 2) & 7) << "(r" << (int)src << ", " << (int32_t)getImm32() << ")" << std::endl;
|
os << "r" << (int)dst << ", " << condition((mod >> 2) & 7) << "(r" << (int)src << ", " << (int32_t)getImm32() << "), " << (int)(mod >> 5) << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Instruction::h_COND_M(std::ostream& os) const {
|
void Instruction::h_COND_M(std::ostream& os) const {
|
||||||
os << "r" << (int)dst << ", " << condition((mod >> 2) & 7) << "(";
|
os << "r" << (int)dst << ", " << condition((mod >> 2) & 7) << "(";
|
||||||
genAddressReg(os);
|
genAddressReg(os);
|
||||||
os << ", " << (int32_t)getImm32() << ")" << std::endl;
|
os << ", " << (int32_t)getImm32() << "), " << (int)(mod >> 5) << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Instruction::h_ISTORE(std::ostream& os) const {
|
void Instruction::h_ISTORE(std::ostream& os) const {
|
||||||
|
@ -18,6 +18,7 @@ along with RandomX. If not, see<http://www.gnu.org/licenses/>.
|
|||||||
*/
|
*/
|
||||||
//#define TRACE
|
//#define TRACE
|
||||||
//#define FPUCHECK
|
//#define FPUCHECK
|
||||||
|
#define RANDOMX_JUMP
|
||||||
#include "InterpretedVirtualMachine.hpp"
|
#include "InterpretedVirtualMachine.hpp"
|
||||||
#include "dataset.hpp"
|
#include "dataset.hpp"
|
||||||
#include "Cache.hpp"
|
#include "Cache.hpp"
|
||||||
@ -45,25 +46,12 @@ constexpr bool fpuCheck = false;
|
|||||||
namespace RandomX {
|
namespace RandomX {
|
||||||
|
|
||||||
InterpretedVirtualMachine::~InterpretedVirtualMachine() {
|
InterpretedVirtualMachine::~InterpretedVirtualMachine() {
|
||||||
if (asyncWorker) {
|
|
||||||
delete mem.ds.asyncWorker;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void InterpretedVirtualMachine::setDataset(dataset_t ds, uint64_t size) {
|
void InterpretedVirtualMachine::setDataset(dataset_t ds, uint64_t size) {
|
||||||
if (asyncWorker) {
|
mem.ds = ds;
|
||||||
if (softAes) {
|
readDataset = &datasetReadLight;
|
||||||
mem.ds.asyncWorker = new LightClientAsyncWorker(ds.cache);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
mem.ds.asyncWorker = new LightClientAsyncWorker(ds.cache);
|
|
||||||
}
|
|
||||||
readDataset = &datasetReadLightAsync;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
mem.ds = ds;
|
|
||||||
readDataset = &datasetReadLight;
|
|
||||||
}
|
|
||||||
datasetRange = (size - RANDOMX_DATASET_SIZE + CacheLineSize) / CacheLineSize;
|
datasetRange = (size - RANDOMX_DATASET_SIZE + CacheLineSize) / CacheLineSize;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -75,14 +63,10 @@ namespace RandomX {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
template<int N>
|
|
||||||
void InterpretedVirtualMachine::executeBytecode(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]) {
|
void InterpretedVirtualMachine::executeBytecode(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]) {
|
||||||
executeBytecode(N, r, f, e, a);
|
for (int ic = 0; ic < RANDOMX_PROGRAM_SIZE; ++ic) {
|
||||||
executeBytecode<N + 1>(r, f, e, a);
|
executeBytecode(ic, r, f, e, a);
|
||||||
}
|
}
|
||||||
|
|
||||||
template<>
|
|
||||||
void InterpretedVirtualMachine::executeBytecode<RANDOMX_PROGRAM_SIZE>(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]) {
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void print(int_reg_t r) {
|
static void print(int_reg_t r) {
|
||||||
@ -114,8 +98,9 @@ namespace RandomX {
|
|||||||
return std::fpclassify(x) == FP_SUBNORMAL;
|
return std::fpclassify(x) == FP_SUBNORMAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
FORCE_INLINE void InterpretedVirtualMachine::executeBytecode(int i, int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]) {
|
FORCE_INLINE void InterpretedVirtualMachine::executeBytecode(int& ic, int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]) {
|
||||||
auto& ibc = byteCode[i];
|
auto& ibc = byteCode[ic];
|
||||||
|
if (trace) std::cout << std::dec << std::setw(3) << ic << " " << program(ic);
|
||||||
//if(trace) printState(r, f, e, a);
|
//if(trace) printState(r, f, e, a);
|
||||||
switch (ibc.type)
|
switch (ibc.type)
|
||||||
{
|
{
|
||||||
@ -234,10 +219,38 @@ namespace RandomX {
|
|||||||
} break;
|
} break;
|
||||||
|
|
||||||
case InstructionType::COND_R: {
|
case InstructionType::COND_R: {
|
||||||
|
#ifdef RANDOMX_JUMP
|
||||||
|
*ibc.creg += (1 << ibc.shift);
|
||||||
|
const uint64_t conditionMask = ((1ULL << RANDOMX_CONDITION_BITS) - 1) << ibc.shift;
|
||||||
|
if ((*ibc.creg & conditionMask) == 0) {
|
||||||
|
#ifdef STATS
|
||||||
|
count_JUMP_taken++;
|
||||||
|
#endif
|
||||||
|
ic = ibc.target;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
#ifdef STATS
|
||||||
|
count_JUMP_not_taken++;
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
*ibc.idst += condition(ibc.condition, *ibc.isrc, ibc.imm) ? 1 : 0;
|
*ibc.idst += condition(ibc.condition, *ibc.isrc, ibc.imm) ? 1 : 0;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case InstructionType::COND_M: {
|
case InstructionType::COND_M: {
|
||||||
|
#ifdef RANDOMX_JUMP
|
||||||
|
*ibc.creg += (1uLL << ibc.shift);
|
||||||
|
const uint64_t conditionMask = ((1ULL << RANDOMX_CONDITION_BITS) - 1) << ibc.shift;
|
||||||
|
if ((*ibc.creg & conditionMask) == 0) {
|
||||||
|
#ifdef STATS
|
||||||
|
count_JUMP_taken++;
|
||||||
|
#endif
|
||||||
|
ic = ibc.target;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
#ifdef STATS
|
||||||
|
count_JUMP_not_taken++;
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
*ibc.idst += condition(ibc.condition, load64(scratchpad + (*ibc.isrc & ibc.memMask)), ibc.imm) ? 1 : 0;
|
*ibc.idst += condition(ibc.condition, load64(scratchpad + (*ibc.isrc & ibc.memMask)), ibc.imm) ? 1 : 0;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
@ -257,7 +270,6 @@ namespace RandomX {
|
|||||||
UNREACHABLE;
|
UNREACHABLE;
|
||||||
}
|
}
|
||||||
if (trace) {
|
if (trace) {
|
||||||
std::cout << program(i);
|
|
||||||
if(ibc.type < 20 || ibc.type == 31 || ibc.type == 32)
|
if(ibc.type < 20 || ibc.type == 31 || ibc.type == 32)
|
||||||
print(*ibc.idst);
|
print(*ibc.idst);
|
||||||
else //if(ibc.type >= 20 && ibc.type <= 30)
|
else //if(ibc.type >= 20 && ibc.type <= 30)
|
||||||
@ -334,28 +346,15 @@ namespace RandomX {
|
|||||||
std::cout << "-----------------------------------" << std::endl;
|
std::cout << "-----------------------------------" << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
executeBytecode<0>(r, f, e, a);
|
executeBytecode(r, f, e, a);
|
||||||
|
|
||||||
if (asyncWorker) {
|
mem.mx ^= r[readReg2] ^ r[readReg3];
|
||||||
ILightClientAsyncWorker* aw = mem.ds.asyncWorker;
|
Cache& cache = mem.ds.cache;
|
||||||
const uint64_t* datasetLine = aw->getBlock(datasetBase + mem.ma);
|
uint64_t datasetLine[CacheLineSize / sizeof(uint64_t)];
|
||||||
for (int i = 0; i < RegistersCount; ++i)
|
initBlock(cache, (uint8_t*)datasetLine, datasetBase + mem.ma / CacheLineSize, RANDOMX_CACHE_ACCESSES / 8);
|
||||||
r[i] ^= datasetLine[i];
|
for (int i = 0; i < RegistersCount; ++i)
|
||||||
mem.mx ^= r[readReg2] ^ r[readReg3];
|
r[i] ^= datasetLine[i];
|
||||||
mem.mx &= CacheLineAlignMask; //align to cache line
|
std::swap(mem.mx, mem.ma);
|
||||||
std::swap(mem.mx, mem.ma);
|
|
||||||
aw->prepareBlock(datasetBase + mem.ma);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
mem.mx ^= r[readReg2] ^ r[readReg3];
|
|
||||||
//mem.mx &= CacheLineAlignMask;
|
|
||||||
Cache& cache = mem.ds.cache;
|
|
||||||
uint64_t datasetLine[CacheLineSize / sizeof(uint64_t)];
|
|
||||||
initBlock(cache, (uint8_t*)datasetLine, datasetBase + mem.ma / CacheLineSize, RANDOMX_CACHE_ACCESSES / 8);
|
|
||||||
for (int i = 0; i < RegistersCount; ++i)
|
|
||||||
r[i] ^= datasetLine[i];
|
|
||||||
std::swap(mem.mx, mem.ma);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (trace) {
|
if (trace) {
|
||||||
std::cout << "iteration " << std::dec << ic << std::endl;
|
std::cout << "iteration " << std::dec << ic << std::endl;
|
||||||
@ -419,9 +418,25 @@ namespace RandomX {
|
|||||||
_mm_store_pd(®.e[3].lo, e[3]);
|
_mm_store_pd(®.e[3].lo, e[3]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int getConditionRegister(int(®isterUsage)[8]) {
|
||||||
|
int min = INT_MAX;
|
||||||
|
int minIndex;
|
||||||
|
for (unsigned i = 0; i < 8; ++i) {
|
||||||
|
if (registerUsage[i] < min) {
|
||||||
|
min = registerUsage[i];
|
||||||
|
minIndex = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return minIndex;
|
||||||
|
}
|
||||||
|
|
||||||
#include "instructionWeights.hpp"
|
#include "instructionWeights.hpp"
|
||||||
|
|
||||||
void InterpretedVirtualMachine::precompileProgram(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]) {
|
void InterpretedVirtualMachine::precompileProgram(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]) {
|
||||||
|
int registerUsage[8];
|
||||||
|
for (unsigned i = 0; i < 8; ++i) {
|
||||||
|
registerUsage[i] = -1;
|
||||||
|
}
|
||||||
for (unsigned i = 0; i < RANDOMX_PROGRAM_SIZE; ++i) {
|
for (unsigned i = 0; i < RANDOMX_PROGRAM_SIZE; ++i) {
|
||||||
auto& instr = program(i);
|
auto& instr = program(i);
|
||||||
auto& ibc = byteCode[i];
|
auto& ibc = byteCode[i];
|
||||||
@ -438,6 +453,7 @@ namespace RandomX {
|
|||||||
ibc.imm = signExtend2sCompl(instr.getImm32());
|
ibc.imm = signExtend2sCompl(instr.getImm32());
|
||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IADD_M) {
|
CASE_REP(IADD_M) {
|
||||||
@ -454,6 +470,7 @@ namespace RandomX {
|
|||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
ibc.memMask = ScratchpadL3Mask;
|
ibc.memMask = ScratchpadL3Mask;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IADD_RC) {
|
CASE_REP(IADD_RC) {
|
||||||
@ -463,6 +480,7 @@ namespace RandomX {
|
|||||||
ibc.idst = &r[dst];
|
ibc.idst = &r[dst];
|
||||||
ibc.isrc = &r[src];
|
ibc.isrc = &r[src];
|
||||||
ibc.imm = signExtend2sCompl(instr.getImm32());
|
ibc.imm = signExtend2sCompl(instr.getImm32());
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(ISUB_R) {
|
CASE_REP(ISUB_R) {
|
||||||
@ -477,6 +495,7 @@ namespace RandomX {
|
|||||||
ibc.imm = signExtend2sCompl(instr.getImm32());
|
ibc.imm = signExtend2sCompl(instr.getImm32());
|
||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(ISUB_M) {
|
CASE_REP(ISUB_M) {
|
||||||
@ -493,6 +512,7 @@ namespace RandomX {
|
|||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
ibc.memMask = ScratchpadL3Mask;
|
ibc.memMask = ScratchpadL3Mask;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IMUL_9C) {
|
CASE_REP(IMUL_9C) {
|
||||||
@ -500,6 +520,7 @@ namespace RandomX {
|
|||||||
ibc.type = InstructionType::IMUL_9C;
|
ibc.type = InstructionType::IMUL_9C;
|
||||||
ibc.idst = &r[dst];
|
ibc.idst = &r[dst];
|
||||||
ibc.imm = signExtend2sCompl(instr.getImm32());
|
ibc.imm = signExtend2sCompl(instr.getImm32());
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IMUL_R) {
|
CASE_REP(IMUL_R) {
|
||||||
@ -514,6 +535,7 @@ namespace RandomX {
|
|||||||
ibc.imm = signExtend2sCompl(instr.getImm32());
|
ibc.imm = signExtend2sCompl(instr.getImm32());
|
||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IMUL_M) {
|
CASE_REP(IMUL_M) {
|
||||||
@ -530,6 +552,7 @@ namespace RandomX {
|
|||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
ibc.memMask = ScratchpadL3Mask;
|
ibc.memMask = ScratchpadL3Mask;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IMULH_R) {
|
CASE_REP(IMULH_R) {
|
||||||
@ -538,6 +561,7 @@ namespace RandomX {
|
|||||||
ibc.type = InstructionType::IMULH_R;
|
ibc.type = InstructionType::IMULH_R;
|
||||||
ibc.idst = &r[dst];
|
ibc.idst = &r[dst];
|
||||||
ibc.isrc = &r[src];
|
ibc.isrc = &r[src];
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IMULH_M) {
|
CASE_REP(IMULH_M) {
|
||||||
@ -554,6 +578,7 @@ namespace RandomX {
|
|||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
ibc.memMask = ScratchpadL3Mask;
|
ibc.memMask = ScratchpadL3Mask;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(ISMULH_R) {
|
CASE_REP(ISMULH_R) {
|
||||||
@ -562,6 +587,7 @@ namespace RandomX {
|
|||||||
ibc.type = InstructionType::ISMULH_R;
|
ibc.type = InstructionType::ISMULH_R;
|
||||||
ibc.idst = &r[dst];
|
ibc.idst = &r[dst];
|
||||||
ibc.isrc = &r[src];
|
ibc.isrc = &r[src];
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(ISMULH_M) {
|
CASE_REP(ISMULH_M) {
|
||||||
@ -578,6 +604,7 @@ namespace RandomX {
|
|||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
ibc.memMask = ScratchpadL3Mask;
|
ibc.memMask = ScratchpadL3Mask;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IMUL_RCP) {
|
CASE_REP(IMUL_RCP) {
|
||||||
@ -588,6 +615,7 @@ namespace RandomX {
|
|||||||
ibc.idst = &r[dst];
|
ibc.idst = &r[dst];
|
||||||
ibc.imm = reciprocal(divisor);
|
ibc.imm = reciprocal(divisor);
|
||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
ibc.type = InstructionType::NOP;
|
ibc.type = InstructionType::NOP;
|
||||||
@ -598,6 +626,7 @@ namespace RandomX {
|
|||||||
auto dst = instr.dst % RegistersCount;
|
auto dst = instr.dst % RegistersCount;
|
||||||
ibc.type = InstructionType::INEG_R;
|
ibc.type = InstructionType::INEG_R;
|
||||||
ibc.idst = &r[dst];
|
ibc.idst = &r[dst];
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IXOR_R) {
|
CASE_REP(IXOR_R) {
|
||||||
@ -612,6 +641,7 @@ namespace RandomX {
|
|||||||
ibc.imm = signExtend2sCompl(instr.getImm32());
|
ibc.imm = signExtend2sCompl(instr.getImm32());
|
||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IXOR_M) {
|
CASE_REP(IXOR_M) {
|
||||||
@ -628,6 +658,7 @@ namespace RandomX {
|
|||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
ibc.memMask = ScratchpadL3Mask;
|
ibc.memMask = ScratchpadL3Mask;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IROR_R) {
|
CASE_REP(IROR_R) {
|
||||||
@ -642,6 +673,7 @@ namespace RandomX {
|
|||||||
ibc.imm = instr.getImm32();
|
ibc.imm = instr.getImm32();
|
||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(IROL_R) {
|
CASE_REP(IROL_R) {
|
||||||
@ -656,6 +688,7 @@ namespace RandomX {
|
|||||||
ibc.imm = instr.getImm32();
|
ibc.imm = instr.getImm32();
|
||||||
ibc.isrc = &ibc.imm;
|
ibc.isrc = &ibc.imm;
|
||||||
}
|
}
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(ISWAP_R) {
|
CASE_REP(ISWAP_R) {
|
||||||
@ -665,6 +698,8 @@ namespace RandomX {
|
|||||||
ibc.idst = &r[dst];
|
ibc.idst = &r[dst];
|
||||||
ibc.isrc = &r[src];
|
ibc.isrc = &r[src];
|
||||||
ibc.type = InstructionType::ISWAP_R;
|
ibc.type = InstructionType::ISWAP_R;
|
||||||
|
registerUsage[instr.dst] = i;
|
||||||
|
registerUsage[instr.src] = i;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
ibc.type = InstructionType::NOP;
|
ibc.type = InstructionType::NOP;
|
||||||
@ -751,6 +786,14 @@ namespace RandomX {
|
|||||||
ibc.isrc = &r[src];
|
ibc.isrc = &r[src];
|
||||||
ibc.condition = (instr.mod >> 2) & 7;
|
ibc.condition = (instr.mod >> 2) & 7;
|
||||||
ibc.imm = instr.getImm32();
|
ibc.imm = instr.getImm32();
|
||||||
|
//jump condition
|
||||||
|
int reg = getConditionRegister(registerUsage);
|
||||||
|
ibc.target = registerUsage[reg];
|
||||||
|
ibc.shift = (instr.mod >> 5);
|
||||||
|
ibc.creg = &r[reg];
|
||||||
|
for (unsigned j = 0; j < 8; ++j) { //mark all registers as used
|
||||||
|
registerUsage[j] = i;
|
||||||
|
}
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(COND_M) {
|
CASE_REP(COND_M) {
|
||||||
@ -762,6 +805,14 @@ namespace RandomX {
|
|||||||
ibc.condition = (instr.mod >> 2) & 7;
|
ibc.condition = (instr.mod >> 2) & 7;
|
||||||
ibc.imm = instr.getImm32();
|
ibc.imm = instr.getImm32();
|
||||||
ibc.memMask = ((instr.mod % 4) ? ScratchpadL1Mask : ScratchpadL2Mask);
|
ibc.memMask = ((instr.mod % 4) ? ScratchpadL1Mask : ScratchpadL2Mask);
|
||||||
|
//jump condition
|
||||||
|
int reg = getConditionRegister(registerUsage);
|
||||||
|
ibc.target = registerUsage[reg];
|
||||||
|
ibc.shift = (instr.mod >> 5);
|
||||||
|
ibc.creg = &r[reg];
|
||||||
|
for (unsigned j = 0; j < 8; ++j) { //mark all registers as used
|
||||||
|
registerUsage[j] = i;
|
||||||
|
}
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
CASE_REP(CFROUND) {
|
CASE_REP(CFROUND) {
|
||||||
|
@ -52,9 +52,12 @@ namespace RandomX {
|
|||||||
uint64_t imm;
|
uint64_t imm;
|
||||||
int64_t simm;
|
int64_t simm;
|
||||||
};
|
};
|
||||||
uint32_t condition;
|
int_reg_t* creg;
|
||||||
|
uint16_t condition;
|
||||||
|
int16_t target;
|
||||||
uint32_t memMask;
|
uint32_t memMask;
|
||||||
uint32_t type;
|
uint16_t type;
|
||||||
|
uint16_t shift;
|
||||||
};
|
};
|
||||||
|
|
||||||
constexpr int asedwfagdewsa = sizeof(InstructionByteCode);
|
constexpr int asedwfagdewsa = sizeof(InstructionByteCode);
|
||||||
@ -70,7 +73,7 @@ namespace RandomX {
|
|||||||
void operator delete(void* ptr) {
|
void operator delete(void* ptr) {
|
||||||
_mm_free(ptr);
|
_mm_free(ptr);
|
||||||
}
|
}
|
||||||
InterpretedVirtualMachine(bool soft, bool async) : softAes(soft), asyncWorker(async) {}
|
InterpretedVirtualMachine(bool soft) : softAes(soft) {}
|
||||||
~InterpretedVirtualMachine();
|
~InterpretedVirtualMachine();
|
||||||
void setDataset(dataset_t ds, uint64_t size) override;
|
void setDataset(dataset_t ds, uint64_t size) override;
|
||||||
void initialize() override;
|
void initialize() override;
|
||||||
@ -78,7 +81,7 @@ namespace RandomX {
|
|||||||
private:
|
private:
|
||||||
static InstructionHandler engine[256];
|
static InstructionHandler engine[256];
|
||||||
DatasetReadFunc readDataset;
|
DatasetReadFunc readDataset;
|
||||||
bool softAes, asyncWorker;
|
bool softAes;
|
||||||
InstructionByteCode byteCode[RANDOMX_PROGRAM_SIZE];
|
InstructionByteCode byteCode[RANDOMX_PROGRAM_SIZE];
|
||||||
|
|
||||||
#ifdef STATS
|
#ifdef STATS
|
||||||
@ -112,10 +115,6 @@ namespace RandomX {
|
|||||||
int count_FPROUND = 0;
|
int count_FPROUND = 0;
|
||||||
int count_JUMP_taken = 0;
|
int count_JUMP_taken = 0;
|
||||||
int count_JUMP_not_taken = 0;
|
int count_JUMP_not_taken = 0;
|
||||||
int count_CALL_taken = 0;
|
|
||||||
int count_CALL_not_taken = 0;
|
|
||||||
int count_RET_stack_empty = 0;
|
|
||||||
int count_RET_taken = 0;
|
|
||||||
int count_jump_taken[8] = { 0 };
|
int count_jump_taken[8] = { 0 };
|
||||||
int count_jump_not_taken[8] = { 0 };
|
int count_jump_not_taken[8] = { 0 };
|
||||||
int count_max_stack = 0;
|
int count_max_stack = 0;
|
||||||
@ -132,8 +131,7 @@ namespace RandomX {
|
|||||||
int datasetAccess[256] = { 0 };
|
int datasetAccess[256] = { 0 };
|
||||||
#endif
|
#endif
|
||||||
void precompileProgram(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]);
|
void precompileProgram(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]);
|
||||||
template<int N>
|
|
||||||
void executeBytecode(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]);
|
void executeBytecode(int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]);
|
||||||
void executeBytecode(int i, int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]);
|
void executeBytecode(int& i, int_reg_t(&r)[8], __m128d (&f)[4], __m128d (&e)[4], __m128d (&a)[4]);
|
||||||
};
|
};
|
||||||
}
|
}
|
@ -171,7 +171,7 @@ namespace RandomX {
|
|||||||
static const uint8_t REX_ANDPS_XMM12[] = { 0x45, 0x0F, 0x54, 0xE5, 0x45, 0x0F, 0x56, 0xE6 };
|
static const uint8_t REX_ANDPS_XMM12[] = { 0x45, 0x0F, 0x54, 0xE5, 0x45, 0x0F, 0x56, 0xE6 };
|
||||||
static const uint8_t REX_PADD[] = { 0x66, 0x44, 0x0f };
|
static const uint8_t REX_PADD[] = { 0x66, 0x44, 0x0f };
|
||||||
static const uint8_t PADD_OPCODES[] = { 0xfc, 0xfd, 0xfe, 0xd4 };
|
static const uint8_t PADD_OPCODES[] = { 0xfc, 0xfd, 0xfe, 0xd4 };
|
||||||
static const uint8_t REX_ADD_I[] = { 0x49, 0x83 };
|
static const uint8_t REX_ADD_I[] = { 0x49, 0x81 };
|
||||||
static const uint8_t REX_TEST[] = { 0x49, 0xF7 };
|
static const uint8_t REX_TEST[] = { 0x49, 0xF7 };
|
||||||
static const uint8_t JZ[] = { 0x0f, 0x84 };
|
static const uint8_t JZ[] = { 0x0f, 0x84 };
|
||||||
|
|
||||||
@ -673,10 +673,9 @@ namespace RandomX {
|
|||||||
const int conditionMask = ((1 << RANDOMX_CONDITION_BITS) - 1) << shift;
|
const int conditionMask = ((1 << RANDOMX_CONDITION_BITS) - 1) << shift;
|
||||||
int reg = getConditionRegister();
|
int reg = getConditionRegister();
|
||||||
int target = registerUsage[reg] + 1;
|
int target = registerUsage[reg] + 1;
|
||||||
registerUsage[reg] = i;
|
|
||||||
emit(REX_ADD_I);
|
emit(REX_ADD_I);
|
||||||
emitByte(0xc0 + reg);
|
emitByte(0xc0 + reg);
|
||||||
emitByte(1 << shift);
|
emit32(1 << shift);
|
||||||
emit(REX_TEST);
|
emit(REX_TEST);
|
||||||
emitByte(0xc0 + reg);
|
emitByte(0xc0 + reg);
|
||||||
emit32(conditionMask);
|
emit32(conditionMask);
|
||||||
|
@ -299,7 +299,7 @@ int main(int argc, char** argv) {
|
|||||||
vm = new RandomX::CompiledVirtualMachine();
|
vm = new RandomX::CompiledVirtualMachine();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
vm = new RandomX::InterpretedVirtualMachine(softAes, async);
|
vm = new RandomX::InterpretedVirtualMachine(softAes);
|
||||||
}
|
}
|
||||||
vm->setDataset(dataset, datasetSize);
|
vm->setDataset(dataset, datasetSize);
|
||||||
vms.push_back(vm);
|
vms.push_back(vm);
|
||||||
@ -336,7 +336,7 @@ int main(int argc, char** argv) {
|
|||||||
std::cout << "Calculated result: ";
|
std::cout << "Calculated result: ";
|
||||||
result.print(std::cout);
|
result.print(std::cout);
|
||||||
if(programCount == 1000)
|
if(programCount == 1000)
|
||||||
std::cout << "Reference result: 84f37cc43cb21eabf1d5b9def462060cd24218290678dd80a8ea2f663892629e" << std::endl;
|
std::cout << "Reference result: 9e636a04a2517f37d8ed40b67a7051e02a7577e878fbba5c4352996b2c653f90" << std::endl;
|
||||||
if (!miningMode) {
|
if (!miningMode) {
|
||||||
std::cout << "Performance: " << 1000 * elapsed / programCount << " ms per hash" << std::endl;
|
std::cout << "Performance: " << 1000 * elapsed / programCount << " ms per hash" << std::endl;
|
||||||
}
|
}
|
||||||
|
@ -76,9 +76,9 @@ randomx_isn_19:
|
|||||||
; FMUL_R e1, a2
|
; FMUL_R e1, a2
|
||||||
mulpd xmm5, xmm10
|
mulpd xmm5, xmm10
|
||||||
randomx_isn_20:
|
randomx_isn_20:
|
||||||
; COND_R r6, of(r3, 1593588996)
|
; COND_R r6, of(r3, 1593588996), 1
|
||||||
add r8, 2
|
add r8, 2
|
||||||
test r8, 2
|
test r8, 254
|
||||||
jz randomx_isn_0
|
jz randomx_isn_0
|
||||||
xor ecx, ecx
|
xor ecx, ecx
|
||||||
cmp r11d, 1593588996
|
cmp r11d, 1593588996
|
||||||
@ -98,9 +98,9 @@ randomx_isn_23:
|
|||||||
; FMUL_R e2, a0
|
; FMUL_R e2, a0
|
||||||
mulpd xmm6, xmm8
|
mulpd xmm6, xmm8
|
||||||
randomx_isn_24:
|
randomx_isn_24:
|
||||||
; COND_R r6, no(r0, 149087159)
|
; COND_R r6, no(r0, 149087159), 6
|
||||||
add r8, 64
|
add r8, 64
|
||||||
test r8, 64
|
test r8, 8128
|
||||||
jz randomx_isn_21
|
jz randomx_isn_21
|
||||||
xor ecx, ecx
|
xor ecx, ecx
|
||||||
cmp r8d, 149087159
|
cmp r8d, 149087159
|
||||||
@ -197,9 +197,9 @@ randomx_isn_50:
|
|||||||
; FSUB_R f3, a0
|
; FSUB_R f3, a0
|
||||||
subpd xmm3, xmm8
|
subpd xmm3, xmm8
|
||||||
randomx_isn_51:
|
randomx_isn_51:
|
||||||
; COND_R r2, be(r3, -1975981803)
|
; COND_R r2, be(r3, -1975981803), 7
|
||||||
add r12, 128
|
add r12, 128
|
||||||
test r12, 128
|
test r12, 16256
|
||||||
jz randomx_isn_25
|
jz randomx_isn_25
|
||||||
xor ecx, ecx
|
xor ecx, ecx
|
||||||
cmp r11d, -1975981803
|
cmp r11d, -1975981803
|
||||||
@ -212,9 +212,9 @@ randomx_isn_53:
|
|||||||
; FSUB_R f2, a0
|
; FSUB_R f2, a0
|
||||||
subpd xmm2, xmm8
|
subpd xmm2, xmm8
|
||||||
randomx_isn_54:
|
randomx_isn_54:
|
||||||
; COND_R r5, ns(r1, 1917049931)
|
; COND_R r5, ns(r1, 1917049931), 6
|
||||||
add r8, 64
|
add r8, 64
|
||||||
test r8, 64
|
test r8, 8128
|
||||||
jz randomx_isn_52
|
jz randomx_isn_52
|
||||||
xor ecx, ecx
|
xor ecx, ecx
|
||||||
cmp r9d, 1917049931
|
cmp r9d, 1917049931
|
||||||
@ -288,9 +288,9 @@ randomx_isn_73:
|
|||||||
; FMUL_R e0, a0
|
; FMUL_R e0, a0
|
||||||
mulpd xmm4, xmm8
|
mulpd xmm4, xmm8
|
||||||
randomx_isn_74:
|
randomx_isn_74:
|
||||||
; COND_R r6, ns(r3, -1200328848)
|
; COND_R r6, ns(r3, -1200328848), 2
|
||||||
add r9, 4
|
add r9, 4
|
||||||
test r9, 4
|
test r9, 508
|
||||||
jz randomx_isn_55
|
jz randomx_isn_55
|
||||||
xor ecx, ecx
|
xor ecx, ecx
|
||||||
cmp r11d, -1200328848
|
cmp r11d, -1200328848
|
||||||
@ -350,9 +350,9 @@ randomx_isn_88:
|
|||||||
; IMUL_R r1, r3
|
; IMUL_R r1, r3
|
||||||
imul r9, r11
|
imul r9, r11
|
||||||
randomx_isn_89:
|
randomx_isn_89:
|
||||||
; COND_M r2, no(L1[r0], -122257389)
|
; COND_M r2, no(L1[r0], -122257389), 6
|
||||||
add r8, 64
|
add r8, 64
|
||||||
test r8, 64
|
test r8, 8128
|
||||||
jz randomx_isn_75
|
jz randomx_isn_75
|
||||||
xor ecx, ecx
|
xor ecx, ecx
|
||||||
mov eax, r8d
|
mov eax, r8d
|
||||||
@ -562,9 +562,9 @@ randomx_isn_142:
|
|||||||
; FADD_R f1, a0
|
; FADD_R f1, a0
|
||||||
addpd xmm1, xmm8
|
addpd xmm1, xmm8
|
||||||
randomx_isn_143:
|
randomx_isn_143:
|
||||||
; COND_R r5, ge(r1, 880467599)
|
; COND_R r5, ge(r1, 880467599), 2
|
||||||
add r14, 4
|
add r14, 4
|
||||||
test r14, 4
|
test r14, 508
|
||||||
jz randomx_isn_110
|
jz randomx_isn_110
|
||||||
xor ecx, ecx
|
xor ecx, ecx
|
||||||
cmp r9d, 880467599
|
cmp r9d, 880467599
|
||||||
@ -962,9 +962,9 @@ randomx_isn_246:
|
|||||||
; IMUL_9C r7, 1938400676
|
; IMUL_9C r7, 1938400676
|
||||||
lea r15, [r15+r15*8+1938400676]
|
lea r15, [r15+r15*8+1938400676]
|
||||||
randomx_isn_247:
|
randomx_isn_247:
|
||||||
; COND_M r2, be(L1[r5], -8545330)
|
; COND_M r2, be(L1[r5], -8545330), 2
|
||||||
add r9, 4
|
add r9, 4
|
||||||
test r9, 4
|
test r9, 508
|
||||||
jz randomx_isn_223
|
jz randomx_isn_223
|
||||||
xor ecx, ecx
|
xor ecx, ecx
|
||||||
mov eax, r13d
|
mov eax, r13d
|
||||||
|
Loading…
Reference in New Issue
Block a user