diff --git a/scripts/generate_cl.js b/scripts/generate_cl.js index 19ed2380..68f75232 100644 --- a/scripts/generate_cl.js +++ b/scripts/generate_cl.js @@ -60,6 +60,7 @@ function rx() 'randomx_constants_wow.h', 'randomx_constants_loki.h', 'randomx_constants_arqma.h', + 'randomx_constants_klaro.h', 'aes.cl', 'blake2b.cl', 'randomx_vm.cl', diff --git a/src/backend/opencl/cl/cn/algorithm.cl b/src/backend/opencl/cl/cn/algorithm.cl index 80b57afd..1e930c9a 100644 --- a/src/backend/opencl/cl/cn/algorithm.cl +++ b/src/backend/opencl/cl/cn/algorithm.cl @@ -25,6 +25,7 @@ #define ALGO_AR2_CHUKWA 24 #define ALGO_AR2_WRKZ 25 + #define FAMILY_UNKNOWN 0 #define FAMILY_CN 1 #define FAMILY_CN_LITE 2 diff --git a/src/backend/opencl/cl/rx/randomx_constants_klaro.h b/src/backend/opencl/cl/rx/randomx_constants_klaro.h new file mode 100644 index 00000000..a8360f80 --- /dev/null +++ b/src/backend/opencl/cl/rx/randomx_constants_klaro.h @@ -0,0 +1,97 @@ +/* +Copyright (c) 2019 SChernykh + +This file is part of RandomX OpenCL. + +RandomX OpenCL is free software: you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation, either version 3 of the License, or +(at your option) any later version. + +RandomX OpenCL is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with RandomX OpenCL. If not, see . +*/ + +//Dataset base size in bytes. Must be a power of 2. +#define RANDOMX_DATASET_BASE_SIZE 2147483648 + +//Dataset extra size. Must be divisible by 64. +#define RANDOMX_DATASET_EXTRA_SIZE 33554368 + +//Scratchpad L3 size in bytes. Must be a power of 2. +#define RANDOMX_SCRATCHPAD_L3 2097152 + +//Scratchpad L2 size in bytes. Must be a power of two and less than or equal to RANDOMX_SCRATCHPAD_L3. +#define RANDOMX_SCRATCHPAD_L2 262144 + +//Scratchpad L1 size in bytes. Must be a power of two (minimum 64) and less than or equal to RANDOMX_SCRATCHPAD_L2. +#define RANDOMX_SCRATCHPAD_L1 16384 + +//Jump condition mask size in bits. +#define RANDOMX_JUMP_BITS 8 + +//Jump condition mask offset in bits. The sum of RANDOMX_JUMP_BITS and RANDOMX_JUMP_OFFSET must not exceed 16. +#define RANDOMX_JUMP_OFFSET 8 + +//Integer instructions +#define RANDOMX_FREQ_IADD_RS 15 +#define RANDOMX_FREQ_IADD_M 2 +#define RANDOMX_FREQ_ISUB_R 16 +#define RANDOMX_FREQ_ISUB_M 2 +#define RANDOMX_FREQ_IMUL_R 16 +#define RANDOMX_FREQ_IMUL_M 4 +#define RANDOMX_FREQ_IMULH_R 4 +#define RANDOMX_FREQ_IMULH_M 1 +#define RANDOMX_FREQ_ISMULH_R 4 +#define RANDOMX_FREQ_ISMULH_M 1 +#define RANDOMX_FREQ_IMUL_RCP 8 +#define RANDOMX_FREQ_INEG_R 2 +#define RANDOMX_FREQ_IXOR_R 5 +#define RANDOMX_FREQ_IXOR_M 2 +#define RANDOMX_FREQ_IROR_R 2 +#define RANDOMX_FREQ_IROL_R 2 +#define RANDOMX_FREQ_ISWAP_R 4 + +//Floating point instructions +#define RANDOMX_FREQ_FSWAP_R 4 +#define RANDOMX_FREQ_FADD_R 20 +#define RANDOMX_FREQ_FADD_M 10 +#define RANDOMX_FREQ_FSUB_R 20 +#define RANDOMX_FREQ_FSUB_M 10 +#define RANDOMX_FREQ_FSCAL_R 6 +#define RANDOMX_FREQ_FMUL_R 20 +#define RANDOMX_FREQ_FMUL2I_R 20 +#define RANDOMX_FREQ_FDIV_M 7 +#define RANDOMX_FREQ_FSQRT_R 16 + +//Control instructions +#define RANDOMX_FREQ_CBRANCH 16 +#define RANDOMX_FREQ_CFROUND 1 + +//Store instruction +#define RANDOMX_FREQ_ISTORE 16 + +//No-op instruction +#define RANDOMX_FREQ_NOP 0 + +#define RANDOMX_DATASET_ITEM_SIZE 64 + +#define RANDOMX_PROGRAM_SIZE 256 + +#define HASH_SIZE 32 +#define ENTROPY_SIZE (128 + RANDOMX_PROGRAM_SIZE * 8) +#define REGISTERS_SIZE 256 +#define IMM_BUF_SIZE (RANDOMX_PROGRAM_SIZE * 4 - REGISTERS_SIZE) +#define IMM_INDEX_COUNT ((IMM_BUF_SIZE / 4) - 2) +#define VM_STATE_SIZE (REGISTERS_SIZE + IMM_BUF_SIZE + RANDOMX_PROGRAM_SIZE * 4) +#define ROUNDING_MODE (RANDOMX_FREQ_CFROUND ? -1 : 0) + +// Scratchpad L1/L2/L3 bits +#define LOC_L1 (32 - 14) +#define LOC_L2 (32 - 18) +#define LOC_L3 (32 - 21) diff --git a/src/crypto/common/Algorithm.cpp b/src/crypto/common/Algorithm.cpp index 2a5f7d5c..68e0c03a 100644 --- a/src/crypto/common/Algorithm.cpp +++ b/src/crypto/common/Algorithm.cpp @@ -118,6 +118,8 @@ static AlgoName const algorithm_names[] = { { "RandomARQ", nullptr, Algorithm::RX_ARQ }, { "randomx/sfx", "rx/sfx", Algorithm::RX_SFX }, { "RandomSFX", nullptr, Algorithm::RX_SFX }, + { "randomx/klr", "rx/klaro", Algorithm::RX_KLARO }, + { "RandomXHFPI", nullptr, Algorithm::RX_KLARO }, # endif # ifdef XMRIG_ALGO_ARGON2 { "argon2/chukwa", nullptr, Algorithm::AR2_CHUKWA }, diff --git a/src/crypto/common/Algorithm.h b/src/crypto/common/Algorithm.h index 7f87283a..00b6a443 100644 --- a/src/crypto/common/Algorithm.h +++ b/src/crypto/common/Algorithm.h @@ -69,6 +69,7 @@ public: RX_LOKI, // "rx/loki" RandomXL (Loki). RX_ARQ, // "rx/arq" RandomARQ (Arqma). RX_SFX, // "rx/sfx" RandomSFX (Safex Cash). + RX_KLARO, // "rx/klaro" RandomHFPI (Klaro Electronic Money). AR2_CHUKWA, // "argon2/chukwa" Argon2id (Chukwa). AR2_WRKZ, // "argon2/wrkz" Argon2id (WRKZ) MAX diff --git a/src/crypto/randomx/bytecode_machine.cpp b/src/crypto/randomx/bytecode_machine.cpp index 55a63935..298b579f 100644 --- a/src/crypto/randomx/bytecode_machine.cpp +++ b/src/crypto/randomx/bytecode_machine.cpp @@ -63,6 +63,7 @@ namespace randomx { INSTR_CASE(FSUB_M) INSTR_CASE(FSCAL_R) INSTR_CASE(FMUL_R) + INSTR_CASE(FMUL2I_R) INSTR_CASE(FDIV_M) INSTR_CASE(FSQRT_R) INSTR_CASE(CBRANCH) @@ -414,6 +415,17 @@ namespace randomx { return; } + if (opcode < RandomX_CurrentConfig.CEIL_FMUL2I_R) { + auto dst = instr.dst % RegisterCountFlt; + int reg_a = (instr.getImm32() & 0xff) % RegistersCount; + int reg_b = (instr.getImm32()>>8 & 0xff) % RegistersCount; + ibc.type = InstructionType::FMUL2I_R; + ibc.fdst = &nreg->e[dst]; + ibc.isrc = &nreg->r[reg_a]; + ibc.isrc2 = &nreg->r[reg_b]; + return; + } + if (opcode < RandomX_CurrentConfig.CEIL_FDIV_M) { auto dst = instr.dst % RegisterCountFlt; auto src = instr.src % RegistersCount; diff --git a/src/crypto/randomx/bytecode_machine.hpp b/src/crypto/randomx/bytecode_machine.hpp index 8aee78d8..c9f0ca3a 100644 --- a/src/crypto/randomx/bytecode_machine.hpp +++ b/src/crypto/randomx/bytecode_machine.hpp @@ -52,6 +52,7 @@ namespace randomx { const int_reg_t* isrc; const rx_vec_f128* fsrc; }; + const int_reg_t* isrc2; union { uint64_t imm; int64_t simm; @@ -205,6 +206,14 @@ namespace randomx { *ibc.fdst = rx_mul_vec_f128(*ibc.fdst, *ibc.fsrc); } + static void exe_FMUL2I_R(RANDOMX_EXE_ARGS) { + const rx_vec_f128 a = _mm_cvtepi32_pd(_mm_set_epi64x(0, *ibc.isrc)); + *ibc.fdst = rx_mul_vec_f128(*ibc.fdst, a); + const rx_vec_f128 b = _mm_cvtepi32_pd(_mm_set_epi64x(0, *ibc.isrc2)); + *ibc.fdst = rx_mul_vec_f128(*ibc.fdst, b); + *ibc.fdst = rx_sqrt_vec_f128(*ibc.fdst); + } + static void exe_FDIV_M(RANDOMX_EXE_ARGS) { rx_vec_f128 fsrc = maskRegisterExponentMantissa( config, @@ -277,6 +286,7 @@ namespace randomx { void gen_FSUB_M(RANDOMX_GEN_ARGS); void gen_FSCAL_R(RANDOMX_GEN_ARGS); void gen_FMUL_R(RANDOMX_GEN_ARGS); + void gen_FMUL2I_R(RANDOMX_GEN_ARGS); void gen_FDIV_M(RANDOMX_GEN_ARGS); void gen_FSQRT_R(RANDOMX_GEN_ARGS); void gen_CBRANCH(RANDOMX_GEN_ARGS); diff --git a/src/crypto/randomx/instruction.hpp b/src/crypto/randomx/instruction.hpp index 446ebfa8..b286210c 100644 --- a/src/crypto/randomx/instruction.hpp +++ b/src/crypto/randomx/instruction.hpp @@ -61,12 +61,13 @@ namespace randomx { FSUB_M = 21, FSCAL_R = 22, FMUL_R = 23, - FDIV_M = 24, - FSQRT_R = 25, - CBRANCH = 26, - CFROUND = 27, - ISTORE = 28, - NOP = 29, + FMUL2I_R = 24, + FDIV_M = 25, + FSQRT_R = 26, + CBRANCH = 27, + CFROUND = 28, + ISTORE = 29, + NOP = 30, }; class Instruction { diff --git a/src/crypto/randomx/jit_compiler_x86.cpp b/src/crypto/randomx/jit_compiler_x86.cpp index 34f98cb9..889f228b 100644 --- a/src/crypto/randomx/jit_compiler_x86.cpp +++ b/src/crypto/randomx/jit_compiler_x86.cpp @@ -1038,6 +1038,33 @@ namespace randomx { codePos = pos; } + static const uint8_t MOVQ_XMM12_REX[] = { 0x66, 0x4d, 0x0f, 0x6e }; + static const uint8_t CVTDQ2PD_XMM12[] = { 0xf3, 0x45, 0x0f, 0xe6, 0xe4 }; + static const uint8_t MULPD_XMM12[] = { 0x66, 0x41, 0x0f, 0x59 }; + + void JitCompilerX86::h_FMUL2I_R(const Instruction& instr) { + uint8_t* const p = code; + int pos = codePos; + + const uint32_t dst = instr.dst % RegisterCountFlt; + int reg_a = (instr.getImm32() & 0xff) % RegistersCount; + int reg_b = (instr.getImm32()>>8 & 0xff) % RegistersCount; + emit(MOVQ_XMM12_REX, p, pos); + emitByte(0xe0 + reg_a, p, pos); + emit(CVTDQ2PD_XMM12, p, pos); + emit(MULPD_XMM12, p, pos); + emitByte(0xc4 + 8 * (dst+4), p, pos); + emit(MOVQ_XMM12_REX, p, pos); + emitByte(0xe0 + reg_b, p, pos); + emit(CVTDQ2PD_XMM12, p, pos); + emit(MULPD_XMM12, p, pos); + emitByte(0xc4 + 8 * (dst+4), p, pos); + emit(SQRTPD, p, pos); + emitByte(0xe4 + 9 * dst, p, pos); + + codePos = pos; + } + void JitCompilerX86::h_FDIV_M(const Instruction& instr) { uint8_t* const p = code; int pos = codePos; diff --git a/src/crypto/randomx/jit_compiler_x86.hpp b/src/crypto/randomx/jit_compiler_x86.hpp index a194f1af..38a4081b 100644 --- a/src/crypto/randomx/jit_compiler_x86.hpp +++ b/src/crypto/randomx/jit_compiler_x86.hpp @@ -142,6 +142,7 @@ namespace randomx { void h_FSUB_M(const Instruction&); void h_FSCAL_R(const Instruction&); void h_FMUL_R(const Instruction&); + void h_FMUL2I_R(const Instruction&); void h_FDIV_M(const Instruction&); void h_FSQRT_R(const Instruction&); void h_CBRANCH(const Instruction&); diff --git a/src/crypto/randomx/randomx.cpp b/src/crypto/randomx/randomx.cpp index 88f7b190..e1baab0d 100644 --- a/src/crypto/randomx/randomx.cpp +++ b/src/crypto/randomx/randomx.cpp @@ -99,6 +99,27 @@ RandomX_ConfigurationSafex::RandomX_ConfigurationSafex() ArgonSalt = "RandomSFX\x01"; } +RandomX_ConfigurationKlaro::RandomX_ConfigurationKlaro() +{ +RANDOMX_FREQ_IADD_RS = 15; +RANDOMX_FREQ_IADD_M = 2; +RANDOMX_FREQ_ISUB_M = 2; +RANDOMX_FREQ_IXOR_R = 5; +RANDOMX_FREQ_IXOR_M = 2; +RANDOMX_FREQ_IROR_R = 2; + +RANDOMX_FREQ_FADD_R = 20; +RANDOMX_FREQ_FADD_M = 10; +RANDOMX_FREQ_FSUB_R = 20; +RANDOMX_FREQ_FSUB_M = 10; +RANDOMX_FREQ_FMUL_R = 20; +RANDOMX_FREQ_FMUL2I_R = 20; +RANDOMX_FREQ_FDIV_M = 7; +RANDOMX_FREQ_FSQRT_R = 16; +RANDOMX_FREQ_CBRANCH = 16; + +} + RandomX_ConfigurationBase::RandomX_ConfigurationBase() : ArgonMemory(262144) , ArgonIterations(3) @@ -276,7 +297,8 @@ void RandomX_ConfigurationBase::Apply() INST_HANDLE(FSUB_M, FSUB_R); INST_HANDLE(FSCAL_R, FSUB_M); INST_HANDLE(FMUL_R, FSCAL_R); - INST_HANDLE(FDIV_M, FMUL_R); + INST_HANDLE(FMUL2I_R, FMUL_R); + INST_HANDLE(FDIV_M, FMUL2I_R); INST_HANDLE(FSQRT_R, FDIV_M); INST_HANDLE(CBRANCH, FSQRT_R); INST_HANDLE(CFROUND, CBRANCH); @@ -290,6 +312,7 @@ RandomX_ConfigurationWownero RandomX_WowneroConfig; RandomX_ConfigurationLoki RandomX_LokiConfig; RandomX_ConfigurationArqma RandomX_ArqmaConfig; RandomX_ConfigurationSafex RandomX_SafexConfig; +RandomX_ConfigurationKlaro RandomX_KlaroConfig; RandomX_ConfigurationBase RandomX_CurrentConfig; diff --git a/src/crypto/randomx/randomx.h b/src/crypto/randomx/randomx.h index 787491eb..72c16afb 100644 --- a/src/crypto/randomx/randomx.h +++ b/src/crypto/randomx/randomx.h @@ -109,6 +109,7 @@ struct RandomX_ConfigurationBase uint32_t RANDOMX_FREQ_FSUB_M; uint32_t RANDOMX_FREQ_FSCAL_R; uint32_t RANDOMX_FREQ_FMUL_R; + uint32_t RANDOMX_FREQ_FMUL2I_R; uint32_t RANDOMX_FREQ_FDIV_M; uint32_t RANDOMX_FREQ_FSQRT_R; uint32_t RANDOMX_FREQ_CBRANCH; @@ -170,6 +171,7 @@ struct RandomX_ConfigurationBase int CEIL_FSUB_M; int CEIL_FSCAL_R; int CEIL_FMUL_R; + int CEIL_FMUL2I_R; int CEIL_FDIV_M; int CEIL_FSQRT_R; int CEIL_CBRANCH; @@ -183,12 +185,14 @@ struct RandomX_ConfigurationWownero : public RandomX_ConfigurationBase { RandomX struct RandomX_ConfigurationLoki : public RandomX_ConfigurationBase { RandomX_ConfigurationLoki(); }; struct RandomX_ConfigurationArqma : public RandomX_ConfigurationBase { RandomX_ConfigurationArqma(); }; struct RandomX_ConfigurationSafex : public RandomX_ConfigurationBase { RandomX_ConfigurationSafex(); }; +struct RandomX_ConfigurationKlaro : public RandomX_ConfigurationBase { RandomX_ConfigurationKlaro(); }; extern RandomX_ConfigurationMonero RandomX_MoneroConfig; extern RandomX_ConfigurationWownero RandomX_WowneroConfig; extern RandomX_ConfigurationLoki RandomX_LokiConfig; extern RandomX_ConfigurationArqma RandomX_ArqmaConfig; extern RandomX_ConfigurationSafex RandomX_SafexConfig; +extern RandomX_ConfigurationKlaro RandomX_KlaroConfig; extern RandomX_ConfigurationBase RandomX_CurrentConfig; diff --git a/src/crypto/rx/RxAlgo.cpp b/src/crypto/rx/RxAlgo.cpp index 4630303e..d1037469 100644 --- a/src/crypto/rx/RxAlgo.cpp +++ b/src/crypto/rx/RxAlgo.cpp @@ -52,6 +52,9 @@ const RandomX_ConfigurationBase *xmrig::RxAlgo::base(Algorithm::Id algorithm) case Algorithm::RX_SFX: return &RandomX_SafexConfig; + case Algorithm::RX_KLARO: + return &RandomX_KlaroConfig; + default: break; }