¿Cómo se compara un hash de encabezado de bloque con el objetivo (bits)?

Estoy tratando de entender el proceso de minería haciendo un pequeño ejemplo de hashing de bloques.

De acuerdo con la entrada Wiki sobre la dificultad, el objetivo de un hash de bloque se puede leer en la parte de "bits" del encabezado de la siguiente manera: En este ejemplo, la parte de bits es 535f0119.

535f0119 * 2**(8*(0x1b - 3))

Mi objetivo resultante sería:

535f0119000000000000000000000000000000000000000000000000

El objetivo en decimal sería:

8780002705592212783085671453687210878315895819816253650256038723584

Digamos que el hash que obtuve con mi nonce actual es

4d47599dd86834282a8ae6f20ba454704ddbe6eb23aa31b9fdec97fc7679b559

¿Cómo puedo comparar ahora si el hash es más pequeño que el objetivo? ¿Qué tengo que hacer con el hash para poder decir "hash < target"?

Respuestas (1)

Cómo calcular el objetivo a partir de bits

Comencemos con un encabezado de bloque, siempre de 80 bytes que se ve así:

04000000b9e2784a84e5d2468cee60ad14e08d0fee5dda49a37148040000000000000000e9dd2b13157508891880ef68729a1e5ecdde58062ebfa214a89f0141e5a4717faefd2b577627061880564bec

De los 80 bytes, los bits son en realidad el byte 72 al 76:

04000000b9e2784a84e5d2468cee60ad14e08d0fee5dda49a37148040000000000000000e9dd2b13157508891880ef68729a1e5ecdde58062ebfa214a89f0141e5a4717faefd2b57**76270618**80564bec

o

76270618

Este número, sin embargo, está en little-endian, por lo que tenemos que invertir los bytes:

18062776

El primer byte es el "exponente"

e = 0x18

Los siguientes 3 bytes son el "coeficiente"

c = 0x062776

Conectas esto en una fórmula:

target = c * 2**(8*(e - 3))

En nuestro caso, eso es:

target = 0x062776 * 2**(8*(0x18 - 3))

Que resulta ser:

0000000000000000062776000000000000000000000000000000000000000000

Calculemos el hash de este encabezado de bloque usando Python 2:

from hashlib import sha256
header = "04000000b9e2784a84e5d2468cee60ad14e08d0fee5dda49a37148040000000000000000e9dd2b13157508891880ef68729a1e5ecdde58062ebfa214a89f0141e5a4717faefd2b577627061880564bec".decode('hex')
print sha256(sha256(header).digest()).digest()[::-1].encode('hex')

la salida es

0000000000000000040199a6c7b922f711ee7e98cd58863b8b981b02d2b83e13

Puedes comparar esto con el objetivo.

>>> 0x0000000000000000040199a6c7b922f711ee7e98cd58863b8b981b02d2b83e13 < 0x0000000000000000062776000000000000000000000000000000000000000000 
True

Así es como sabemos que un bloque satisface la prueba de trabajo.

Entonces, ¿podría argumentarse que la dificultad es un porcentaje? es decir, d = (hash objetivo)/(hash objetivo más difícil)
En la última línea de código, la comparación no debería ser <=en lugar de <?