mirror of
https://github.com/JayDDee/cpuminer-opt.git
synced 2025-09-17 23:44:27 +00:00
v3.15.6
This commit is contained in:
@@ -59,7 +59,7 @@ Notes about included DLL files:
|
||||
|
||||
Downloading DLL files from alternative sources presents an inherent
|
||||
security risk if their source is unknown. All DLL files included have
|
||||
been copied from the Ubuntu-20.04 instalation or compiled by me from
|
||||
been copied from the Ubuntu-20.04 installation or compiled by me from
|
||||
source code obtained from the author's official repository. The exact
|
||||
procedure is documented in the build instructions for Windows:
|
||||
https://github.com/JayDDee/cpuminer-opt/wiki/Compiling-from-source
|
||||
|
@@ -65,6 +65,14 @@ If not what makes it happen or not happen?
|
||||
Change Log
|
||||
----------
|
||||
|
||||
v3.15.6
|
||||
|
||||
Implement keccak pre-hash optimization for x16* algos.
|
||||
Move conditional mining test to before get_new_work in miner thread.
|
||||
Add test for share reject reason when solo mining.
|
||||
Add support for floating point, as well as integer, "networkhasps" in
|
||||
RPC getmininginfo method.
|
||||
|
||||
v3.15.5
|
||||
|
||||
Fix stratum jobs lost if 2 jobs received in less than one second.
|
||||
|
@@ -419,7 +419,6 @@ void exec_hash_function( int algo, void *output, const void *pdata )
|
||||
const char* const algo_alias_map[][2] =
|
||||
{
|
||||
// alias proper
|
||||
{ "argon2d-crds", "argon2d250" },
|
||||
{ "argon2d-dyn", "argon2d500" },
|
||||
{ "argon2d-uis", "argon2d4096" },
|
||||
{ "bcd", "x13bcd" },
|
||||
|
@@ -201,6 +201,7 @@
|
||||
#define IOTA(r) XOR64_IOTA(a00, a00, r)
|
||||
|
||||
#ifdef P0
|
||||
#undef P0
|
||||
#undef P1
|
||||
#undef P2
|
||||
#undef P3
|
||||
|
@@ -16,8 +16,7 @@
|
||||
|
||||
#if defined (X16R_8WAY)
|
||||
|
||||
// Perform midstate prehash of hash functions with block size <= 64 bytes
|
||||
// and interleave 4x64 before nonce insertion for final hash.
|
||||
// Perform midstate prehash of hash functions with block size <= 72 bytes.
|
||||
|
||||
void x16r_8way_prehash( void *vdata, void *pdata )
|
||||
{
|
||||
@@ -34,6 +33,11 @@ void x16r_8way_prehash( void *vdata, void *pdata )
|
||||
jh512_8way_init( &x16r_ctx.jh );
|
||||
jh512_8way_update( &x16r_ctx.jh, vdata, 64 );
|
||||
break;
|
||||
case KECCAK:
|
||||
mm512_bswap32_intrlv80_8x64( vdata, pdata );
|
||||
keccak512_8way_init( &x16r_ctx.keccak );
|
||||
keccak512_8way_update( &x16r_ctx.keccak, vdata, 72 );
|
||||
break;
|
||||
case SKEIN:
|
||||
mm512_bswap32_intrlv80_8x64( vdata, pdata );
|
||||
skein512_8way_init( &x16r_ctx.skein );
|
||||
@@ -173,13 +177,13 @@ int x16r_8way_hash_generic( void* output, const void* input, int thrid )
|
||||
hash7, vhash );
|
||||
break;
|
||||
case KECCAK:
|
||||
keccak512_8way_init( &ctx.keccak );
|
||||
if ( i == 0 )
|
||||
keccak512_8way_update( &ctx.keccak, input, size );
|
||||
keccak512_8way_update( &ctx.keccak, input + (72<<3), 8 );
|
||||
else
|
||||
{
|
||||
intrlv_8x64( vhash, in0, in1, in2, in3, in4, in5, in6, in7,
|
||||
size<<3 );
|
||||
keccak512_8way_init( &ctx.keccak );
|
||||
keccak512_8way_update( &ctx.keccak, vhash, size );
|
||||
}
|
||||
keccak512_8way_close( &ctx.keccak, vhash );
|
||||
@@ -490,6 +494,7 @@ int scanhash_x16r_8way( struct work *work, uint32_t max_nonce,
|
||||
{
|
||||
x16_r_s_getAlgoString( (const uint8_t*)bedata1, x16r_hash_order );
|
||||
s_ntime = ntime;
|
||||
|
||||
if ( opt_debug && !thr_id )
|
||||
applog( LOG_INFO, "hash order %s (%08x)", x16r_hash_order, ntime );
|
||||
}
|
||||
@@ -533,6 +538,11 @@ void x16r_4way_prehash( void *vdata, void *pdata )
|
||||
jh512_4way_init( &x16r_ctx.jh );
|
||||
jh512_4way_update( &x16r_ctx.jh, vdata, 64 );
|
||||
break;
|
||||
case KECCAK:
|
||||
mm256_bswap32_intrlv80_4x64( vdata, pdata );
|
||||
keccak512_4way_init( &x16r_ctx.keccak );
|
||||
keccak512_4way_update( &x16r_ctx.keccak, vdata, 72 );
|
||||
break;
|
||||
case SKEIN:
|
||||
mm256_bswap32_intrlv80_4x64( vdata, pdata );
|
||||
skein512_4way_prehash64( &x16r_ctx.skein, vdata );
|
||||
@@ -646,12 +656,12 @@ int x16r_4way_hash_generic( void* output, const void* input, int thrid )
|
||||
dintrlv_4x64_512( hash0, hash1, hash2, hash3, vhash );
|
||||
break;
|
||||
case KECCAK:
|
||||
keccak512_4way_init( &ctx.keccak );
|
||||
if ( i == 0 )
|
||||
keccak512_4way_update( &ctx.keccak, input, size );
|
||||
keccak512_4way_update( &ctx.keccak, input + (72<<2), 8 );
|
||||
else
|
||||
{
|
||||
intrlv_4x64( vhash, in0, in1, in2, in3, size<<3 );
|
||||
keccak512_4way_init( &ctx.keccak );
|
||||
keccak512_4way_update( &ctx.keccak, vhash, size );
|
||||
}
|
||||
keccak512_4way_close( &ctx.keccak, vhash );
|
||||
|
20
configure
vendored
20
configure
vendored
@@ -1,6 +1,6 @@
|
||||
#! /bin/sh
|
||||
# Guess values for system-dependent variables and create Makefiles.
|
||||
# Generated by GNU Autoconf 2.69 for cpuminer-opt 3.15.5.
|
||||
# Generated by GNU Autoconf 2.69 for cpuminer-opt 3.15.6.
|
||||
#
|
||||
#
|
||||
# Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc.
|
||||
@@ -577,8 +577,8 @@ MAKEFLAGS=
|
||||
# Identity of this package.
|
||||
PACKAGE_NAME='cpuminer-opt'
|
||||
PACKAGE_TARNAME='cpuminer-opt'
|
||||
PACKAGE_VERSION='3.15.5'
|
||||
PACKAGE_STRING='cpuminer-opt 3.15.5'
|
||||
PACKAGE_VERSION='3.15.6'
|
||||
PACKAGE_STRING='cpuminer-opt 3.15.6'
|
||||
PACKAGE_BUGREPORT=''
|
||||
PACKAGE_URL=''
|
||||
|
||||
@@ -1332,7 +1332,7 @@ if test "$ac_init_help" = "long"; then
|
||||
# Omit some internal or obsolete options to make the list less imposing.
|
||||
# This message is too long to be a string in the A/UX 3.1 sh.
|
||||
cat <<_ACEOF
|
||||
\`configure' configures cpuminer-opt 3.15.5 to adapt to many kinds of systems.
|
||||
\`configure' configures cpuminer-opt 3.15.6 to adapt to many kinds of systems.
|
||||
|
||||
Usage: $0 [OPTION]... [VAR=VALUE]...
|
||||
|
||||
@@ -1404,7 +1404,7 @@ fi
|
||||
|
||||
if test -n "$ac_init_help"; then
|
||||
case $ac_init_help in
|
||||
short | recursive ) echo "Configuration of cpuminer-opt 3.15.5:";;
|
||||
short | recursive ) echo "Configuration of cpuminer-opt 3.15.6:";;
|
||||
esac
|
||||
cat <<\_ACEOF
|
||||
|
||||
@@ -1509,7 +1509,7 @@ fi
|
||||
test -n "$ac_init_help" && exit $ac_status
|
||||
if $ac_init_version; then
|
||||
cat <<\_ACEOF
|
||||
cpuminer-opt configure 3.15.5
|
||||
cpuminer-opt configure 3.15.6
|
||||
generated by GNU Autoconf 2.69
|
||||
|
||||
Copyright (C) 2012 Free Software Foundation, Inc.
|
||||
@@ -2012,7 +2012,7 @@ cat >config.log <<_ACEOF
|
||||
This file contains any messages produced by compilers while
|
||||
running configure, to aid debugging if configure makes a mistake.
|
||||
|
||||
It was created by cpuminer-opt $as_me 3.15.5, which was
|
||||
It was created by cpuminer-opt $as_me 3.15.6, which was
|
||||
generated by GNU Autoconf 2.69. Invocation command line was
|
||||
|
||||
$ $0 $@
|
||||
@@ -2993,7 +2993,7 @@ fi
|
||||
|
||||
# Define the identity of the package.
|
||||
PACKAGE='cpuminer-opt'
|
||||
VERSION='3.15.5'
|
||||
VERSION='3.15.6'
|
||||
|
||||
|
||||
cat >>confdefs.h <<_ACEOF
|
||||
@@ -6690,7 +6690,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
|
||||
# report actual input values of CONFIG_FILES etc. instead of their
|
||||
# values after options handling.
|
||||
ac_log="
|
||||
This file was extended by cpuminer-opt $as_me 3.15.5, which was
|
||||
This file was extended by cpuminer-opt $as_me 3.15.6, which was
|
||||
generated by GNU Autoconf 2.69. Invocation command line was
|
||||
|
||||
CONFIG_FILES = $CONFIG_FILES
|
||||
@@ -6756,7 +6756,7 @@ _ACEOF
|
||||
cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
|
||||
ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
|
||||
ac_cs_version="\\
|
||||
cpuminer-opt config.status 3.15.5
|
||||
cpuminer-opt config.status 3.15.6
|
||||
configured by $0, generated by GNU Autoconf 2.69,
|
||||
with options \\"\$ac_cs_config\\"
|
||||
|
||||
|
@@ -1,4 +1,4 @@
|
||||
AC_INIT([cpuminer-opt], [3.15.5])
|
||||
AC_INIT([cpuminer-opt], [3.15.6])
|
||||
|
||||
AC_PREREQ([2.59c])
|
||||
AC_CANONICAL_SYSTEM
|
||||
|
83
cpu-miner.c
83
cpu-miner.c
@@ -490,8 +490,13 @@ static bool get_mininginfo( CURL *curl, struct work *work )
|
||||
}
|
||||
|
||||
key = json_object_get( res, "networkhashps" );
|
||||
if ( key && json_is_integer( key ) )
|
||||
if ( key )
|
||||
{
|
||||
if ( json_is_integer( key ) )
|
||||
net_hashrate = (double) json_integer_value( key );
|
||||
else if ( json_is_real( key ) )
|
||||
net_hashrate = (double) json_real_value( key );
|
||||
}
|
||||
|
||||
key = json_object_get( res, "blocks" );
|
||||
if ( key && json_is_integer( key ) )
|
||||
@@ -506,26 +511,7 @@ static bool get_mininginfo( CURL *curl, struct work *work )
|
||||
// complete missing data from getwork
|
||||
work->height = (uint32_t) net_blocks + 1;
|
||||
if ( work->height > g_work.height )
|
||||
{
|
||||
restart_threads();
|
||||
|
||||
/* redundant with new block log
|
||||
if ( !opt_quiet )
|
||||
{
|
||||
char netinfo[64] = { 0 };
|
||||
char srate[32] = { 0 };
|
||||
sprintf( netinfo, "diff %.2f", net_diff );
|
||||
if ( net_hashrate )
|
||||
{
|
||||
format_hashrate( net_hashrate, srate );
|
||||
strcat( netinfo, ", net " );
|
||||
strcat( netinfo, srate );
|
||||
}
|
||||
applog( LOG_BLUE, "%s block %d, %s",
|
||||
algo_names[opt_algo], work->height, netinfo );
|
||||
}
|
||||
*/
|
||||
}
|
||||
} // res
|
||||
}
|
||||
json_decref( val );
|
||||
@@ -1078,13 +1064,12 @@ void report_summary_log( bool force )
|
||||
|
||||
if ( accepted_share_count < submitted_share_count )
|
||||
{
|
||||
double ltd = exp32 * last_targetdiff;
|
||||
double lost_ghrate = uptime.tv_sec == 0 ? 0.
|
||||
: exp32 * last_targetdiff
|
||||
* (double)(submitted_share_count - accepted_share_count )
|
||||
: ltd * (double)(submitted_share_count - accepted_share_count )
|
||||
/ (double)uptime.tv_sec;
|
||||
double lost_shrate = share_time == 0. ? 0.
|
||||
: exp32 * last_targetdiff * (double)(submits - accepts )
|
||||
/ share_time;
|
||||
: ltd * (double)(submits - accepts ) / share_time;
|
||||
char lshr_units[4] = {0};
|
||||
char lghr_units[4] = {0};
|
||||
scale_hash_for_display( &lost_shrate, lshr_units );
|
||||
@@ -1190,9 +1175,11 @@ static int share_result( int result, struct work *work,
|
||||
{
|
||||
sprintf( ares, "A%d", accepted_share_count );
|
||||
sprintf( bres, "B%d", solved_block_count );
|
||||
stale = work ? work->data[ algo_gate.ntime_index ]
|
||||
!= g_work.data[ algo_gate.ntime_index ] : false;
|
||||
if ( reason ) stale = stale || strstr( reason, "job" );
|
||||
if ( reason )
|
||||
stale = strstr( reason, "job" );
|
||||
else if ( work )
|
||||
stale = work->data[ algo_gate.ntime_index ]
|
||||
!= g_work.data[ algo_gate.ntime_index ];
|
||||
if ( stale )
|
||||
{
|
||||
stale_share_count++;
|
||||
@@ -1260,14 +1247,13 @@ static int share_result( int result, struct work *work,
|
||||
if ( unlikely( !( opt_quiet || result || stale ) ) )
|
||||
{
|
||||
uint32_t str[8];
|
||||
uint32_t *targ;
|
||||
|
||||
if ( reason )
|
||||
applog( LOG_WARNING, "Reject reason: %s", reason );
|
||||
if ( reason ) applog( LOG_WARNING, "Reject reason: %s", reason );
|
||||
|
||||
// display share hash and target for troubleshooting
|
||||
diff_to_hash( str, my_stats.share_diff );
|
||||
applog2( LOG_INFO, "Hash: %08x%08x%08x...", str[7], str[6], str[5] );
|
||||
uint32_t *targ;
|
||||
|
||||
if ( work )
|
||||
targ = work->target;
|
||||
else
|
||||
@@ -1580,6 +1566,7 @@ start:
|
||||
{
|
||||
double miner_hr = 0.;
|
||||
double net_hr = net_hashrate;
|
||||
double nd = net_diff * exp32;
|
||||
char net_hr_units[4] = {0};
|
||||
char miner_hr_units[4] = {0};
|
||||
char net_ttf[32];
|
||||
@@ -1594,11 +1581,11 @@ start:
|
||||
pthread_mutex_unlock( &stats_lock );
|
||||
|
||||
if ( net_hr > 0. )
|
||||
sprintf_et( net_ttf, ( net_diff * exp32 ) / net_hr );
|
||||
sprintf_et( net_ttf, nd / net_hr );
|
||||
else
|
||||
sprintf( net_ttf, "NA" );
|
||||
if ( miner_hr > 0. )
|
||||
sprintf_et( miner_ttf, ( net_diff * exp32 ) / miner_hr );
|
||||
sprintf_et( miner_ttf, nd / miner_hr );
|
||||
else
|
||||
sprintf( miner_ttf, "NA" );
|
||||
|
||||
@@ -1848,10 +1835,19 @@ bool submit_solution( struct work *work, const void *hash,
|
||||
work->data[ algo_gate.ntime_index ] );
|
||||
}
|
||||
|
||||
if ( unlikely( lowdiff_debug ) )
|
||||
if ( opt_debug )
|
||||
{
|
||||
uint32_t* h = (uint32_t*)hash;
|
||||
uint32_t* t = (uint32_t*)work->target;
|
||||
uint32_t* d = (uint32_t*)work->data;
|
||||
|
||||
unsigned char *xnonce2str = abin2hex( work->xnonce2,
|
||||
work->xnonce2_len );
|
||||
applog(LOG_INFO,"Thread %d, Nonce %08x, Xnonce2 %s", thr->id,
|
||||
work->data[ algo_gate.nonce_index ], xnonce2str );
|
||||
free( xnonce2str );
|
||||
applog(LOG_INFO,"Data[0:19]: %08x %08x %08x %08x %08x %08x %08x %08x %08x %08x", d[0],d[1],d[2],d[3],d[4],d[5],d[6],d[7],d[8],d[9] );
|
||||
applog(LOG_INFO," : %08x %08x %08x %08x %08x %08x %08x %08x %08x %08x", d[10],d[11],d[12],d[13],d[14],d[15],d[16],d[17],d[18],d[19]);
|
||||
applog(LOG_INFO,"Hash[7:0]: %08x %08x %08x %08x %08x %08x %08x %08x",
|
||||
h[7],h[6],h[5],h[4],h[3],h[2],h[1],h[0]);
|
||||
applog(LOG_INFO,"Targ[7:0]: %08x %08x %08x %08x %08x %08x %08x %08x",
|
||||
@@ -2066,11 +2062,12 @@ static void stratum_gen_work( struct stratum_ctx *sctx, struct work *g_work )
|
||||
|
||||
if ( likely( hr > 0. ) )
|
||||
{
|
||||
double nd = net_diff * exp32;
|
||||
char hr_units[4] = {0};
|
||||
char block_ttf[32];
|
||||
char share_ttf[32];
|
||||
|
||||
sprintf_et( block_ttf, ( net_diff * exp32 ) / hr );
|
||||
sprintf_et( block_ttf, nd / hr );
|
||||
sprintf_et( share_ttf, ( g_work->targetdiff * exp32 ) / hr );
|
||||
scale_hash_for_display ( &hr, hr_units );
|
||||
applog2( LOG_INFO, "TTF @ %.2f %sh/s: Block %s, Share %s",
|
||||
@@ -2086,7 +2083,7 @@ static void stratum_gen_work( struct stratum_ctx *sctx, struct work *g_work )
|
||||
: et.tv_sec / ( last_block_height - session_first_block );
|
||||
if ( net_diff && net_ttf )
|
||||
{
|
||||
double net_hr = net_diff * exp32 / net_ttf;
|
||||
double net_hr = nd / net_ttf;
|
||||
char net_hr_units[4] = {0};
|
||||
|
||||
scale_hash_for_display ( &net_hr, net_hr_units );
|
||||
@@ -2253,12 +2250,6 @@ static void *miner_thread( void *userdata )
|
||||
|
||||
if ( unlikely( !algo_gate.ready_to_mine( &work, &stratum, thr_id ) ) )
|
||||
continue;
|
||||
// conditional mining
|
||||
if ( unlikely( !wanna_mine( thr_id ) ) )
|
||||
{
|
||||
sleep(5);
|
||||
continue;
|
||||
}
|
||||
|
||||
// LP_SCANTIME overrides opt_scantime option, is this right?
|
||||
|
||||
@@ -2445,6 +2436,14 @@ static void *miner_thread( void *userdata )
|
||||
#endif
|
||||
}
|
||||
} // benchmark
|
||||
|
||||
// conditional mining
|
||||
if ( unlikely( !wanna_mine( thr_id ) ) )
|
||||
{
|
||||
sleep(5);
|
||||
continue;
|
||||
}
|
||||
|
||||
} // miner_thread loop
|
||||
|
||||
out:
|
||||
|
5
miner.h
5
miner.h
@@ -771,7 +771,7 @@ Options:\n\
|
||||
allium Garlicoin (GRLC)\n\
|
||||
anime Animecoin (ANI)\n\
|
||||
argon2 Argon2 Coin (AR2)\n\
|
||||
argon2d250 argon2d-crds, Credits (CRDS)\n\
|
||||
argon2d250\n\
|
||||
argon2d500 argon2d-dyn, Dynamic (DYN)\n\
|
||||
argon2d4096 argon2d-uis, Unitus (UIS)\n\
|
||||
axiom Shabal-256 MemoHash\n\
|
||||
@@ -796,7 +796,7 @@ Options:\n\
|
||||
lyra2h Hppcoin\n\
|
||||
lyra2re lyra2\n\
|
||||
lyra2rev2 lyrav2\n\
|
||||
lyra2rev3 lyrav2v3, Vertcoin\n\
|
||||
lyra2rev3 lyrav2v3\n\
|
||||
lyra2z\n\
|
||||
lyra2z330 Lyra2 330 rows\n\
|
||||
m7m Magi (XMG)\n\
|
||||
@@ -875,7 +875,6 @@ Options:\n\
|
||||
-s, --scantime=N upper bound on time spent scanning current work when\n\
|
||||
long polling is unavailable, in seconds (default: 5)\n\
|
||||
--randomize Randomize scan range start to reduce duplicates\n\
|
||||
--reset-on-stale Workaround reset stratum if too many stale shares\n\
|
||||
-f, --diff-factor Divide req. difficulty by this factor (std is 1.0)\n\
|
||||
-m, --diff-multiplier Multiply difficulty by this factor (std is 1.0)\n\
|
||||
--hash-meter Display thread hash rates\n\
|
||||
|
34
util.c
34
util.c
@@ -1048,53 +1048,51 @@ bool fulltest( const uint32_t *hash, const uint32_t *target )
|
||||
return rc;
|
||||
}
|
||||
|
||||
// Mathmatically the difficulty is simply the reciprocal of the hash.
|
||||
// Mathmatically the difficulty is simply the reciprocal of the hash: d = 1/h.
|
||||
// Both are real numbers but the hash (target) is represented as a 256 bit
|
||||
// number with the upper 32 bits representing the whole integer part and the
|
||||
// lower 224 bits representing the fractional part:
|
||||
// fixed point number with the upper 32 bits representing the whole integer
|
||||
// part and the lower 224 bits representing the fractional part:
|
||||
// target[ 255:224 ] = trunc( 1/diff )
|
||||
// target[ 223: 0 ] = frac( 1/diff )
|
||||
//
|
||||
// The 256 bit hash is exact but any floating point representation is not.
|
||||
// Stratum provides the target difficulty as double precision, inexcact, and
|
||||
// Stratum provides the target difficulty as double precision, inexcact,
|
||||
// which must be converted to a hash target. The converted hash target will
|
||||
// likely be less precise to to inexact input and conversion error.
|
||||
// converted to 256 bit hash which will also be inexact and likelyless
|
||||
// accurate to to error in conversion.
|
||||
// likely be less precise due to inexact input and conversion error.
|
||||
// On the other hand getwork provides a 256 bit hash target which is exact.
|
||||
//
|
||||
// How much precision is needed?
|
||||
//
|
||||
// 128 bit types are implemented in software by the compiler using 64 bit
|
||||
// 128 bit types are implemented in software by the compiler on 64 bit
|
||||
// hardware resulting in lower performance and more error than would be
|
||||
// expected with a hardware 128 bit implementtaion.
|
||||
// expected with a hardware 128 bit implementaion.
|
||||
// Float80 exploits the internals of the FP unit which provide a 64 bit
|
||||
// mantissa in an 80 bit register with hardware rounding. When the destination
|
||||
// is double the data is rounded to float64 format. Long double returns all
|
||||
// 80 bits without rounding and including any accumulated computation error.
|
||||
// Float80 does not fit efficiently in memory.
|
||||
//
|
||||
// Significant digits:
|
||||
// 256 bit hash: 76
|
||||
// float: 7 (float32, 80 bits with rounding to 32 bits)
|
||||
// double: 15 (float64, 80 bits with rounding to 64 bits)
|
||||
// long double 19 (float80, 80 bits with no rounding)
|
||||
// __float128 33 (128 bits with no rounding)
|
||||
// long double: 19 (float80, 80 bits with no rounding)
|
||||
// __float128: 33 (128 bits with no rounding)
|
||||
// uint32_t: 9
|
||||
// uint64_t: 19
|
||||
// uint128_t 38
|
||||
//
|
||||
// The concept of significant digits doesn't apply to the 256 bit hash
|
||||
// representation. It's fixed point making leading zeros significant
|
||||
// Leading zeros count in the 256 bit
|
||||
// representation. It's fixed point making leading zeros significant,
|
||||
// limiting its range and precision due to fewer zon-zero significant digits.
|
||||
//
|
||||
// Doing calculations with float128 and uint128 increases precision for
|
||||
// target_to_diff, but doesn't help with stratum diff being limited to
|
||||
// double precision. Is the extra precision really worth the extra cost?
|
||||
//
|
||||
// With double the error rate is 1/1e15, or one hash in every Petahash
|
||||
// with a very low difficulty, not a likely sitiation. Higher difficulty
|
||||
// increases the effective precision. Due to the floating nature of the
|
||||
// decimal point leading zeros aren't counted.
|
||||
// With float128 the error rate is 1/1e33 compared with 1/1e15 for double.
|
||||
// For double that's 1 error in every petahash with a very low difficulty,
|
||||
// not a likely situation. With higher difficulty effective precision
|
||||
// increases.
|
||||
//
|
||||
// Unfortunately I can't get float128 to work so long double (float80) is
|
||||
// as precise as it gets.
|
||||
|
Reference in New Issue
Block a user