Python code to vb.net (2012) - help me to eliminate the errors

2

1

I wanted to convert the following bitcoin mining python code to VB.net (2012) and I tried to convert it's functionality, but it throws some errors and I'm stuck as I even can't get the resulting value of "header" variable.

and the final hash result should be 0000000000000000e067a478024addfecdc93628978aa52d91fabd4292982a50, but I'm no where near that.

why this produces errors, converting from hex to byte is not the correct method?

in python L is used to format it to long right?, so what does the <L & <LLL in the python code do? and is this ::-1 used to prevent overflow when reading the hex string?

and, in exp = bits >> 24 what does it do, bitwise operations?

import hashlib, struct

ver = 2
prev_block = "000000000000000117c80378b8da0e33559b5997f2ad55e2f7d18ec1975b9717"
mrkl_root = "871714dcbae6c8193a2bb9b2a69fe1c0440399f38d94b3a0f1b447275a29978a"
time_ = 0x53058b35 # 2014-02-20 04:57:25
bits = 0x19015f53

# https://en.bitcoin.it/wiki/Difficulty
exp = bits >> 24
mant = bits & 0xffffff
target_hexstr = '%064x' % (mant * (1<<(8*(exp - 3))))
target_str = target_hexstr.decode('hex')

nonce = 0
while nonce < 0x100000000:
    header = ( struct.pack("<L", ver) + prev_block.decode('hex')[::-1] +
          mrkl_root.decode('hex')[::-1] + struct.pack("<LLL", time_, bits, nonce))
    hash = hashlib.sha256(hashlib.sha256(header).digest()).digest()
    print nonce, hash[::-1].encode('hex')
    if hash[::-1] < target_str:
        print 'success'
        break
nonce += 1

The VB.NET code I've been coding up until now is,

Public Class Form1
Dim version As Long = 0
Dim time As Integer
Dim pblock As Byte
Dim mklroot As Byte
Dim header As String
Dim nonce As Integer = 856192328

Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
    Textbox1.Text = "2"
    Textbox2.Text = "000000000000000117c80378b8da0e33559b5997f2ad55e2f7d18ec1975b9717"
    Textbox3.Text = "871714dcbae6c8193a2bb9b2a69fe1c0440399f38d94b3a0f1b447275a29978a"
    Textbox4.Text = "0x53058b35" '2014-02-20 04:57:25
    Textbox5.Text = "0x19015f53"

    Dim n As Int32 = T2.Text.Length - 1

    version = CLng(Textbox1.Text)
    'pblock = CByte(Textbox2.Text)
    pblock = Convert.ToByte(Convert.ToInt32(Textbox2.Text, 16))
    mklroot = Convert.ToByte(Convert.ToInt32(Textbox3.Text, 16))
    time = CInt(Textbox4.Text)

    header = version & pblock & mklroot & time & nonce
    Textbox6.Text = header


   End Sub
 End Class

Pretty_Girl

Posted 2016-06-18T08:15:39.140

Reputation: 41

Answers

0

Chech this explanation..

OR

TL;DR version

Assuming you came accros this site bitcoin-mining-hard-way-algorithms. I'll show you in C# and you can convert to VB, using the same logic.

Here is the deal: All information in a bitcoin block is hexadecimal. So the header you are formming is compounded by:

var header = $"{ver}{prev_block}{mrkl_root}{timestamp}{bits}{nonce}";

Let's calculate each:

ver = 2

Must be converted to a 8 byte hexadecimal, but afterwards must be reversed. ( when reversing a hex string you reverse the pairs so "00-00-02" become "02-00-00";

A simple function to reverse can be as:

string reverse(string hex)
{
   char[] reverted = new char[hex.Length];
   for (int i = hex.Length - 1, j = 0; i > 0; i -= 2, j += 2)
   {
       reverted[j] = hex[i - 1];
       reverted[j + 1] = hex[i];
   }
   return new string(reverted);
}

So:

var ver = 2.ToString("X8"); // Returns a hex representation: 00000002
ver = reverse(ver); //02000000

Then:

prev_block = "000000000000000117c80378b8da0e33559b5997f2ad55e2f7d18ec1975b9717"

Its the previous block hash of the chain, and must be reversed too.

var prev_block = reverse("000000000000000117c80378b8da0e33559b5997f2ad55e2f7d18ec1975b9717");

Then, the mrkl_root is calculated from 99 transaction hashes. The resulting Merkle root is (If you don't know MerkleRoot take a look in this repo: diegomary/bitcoin-merkle-root-netcore):

mrkl_root = "871714dcbae6c8193a2bb9b2a69fe1c0440399f38d94b3a0f1b447275a29978a"

And again you reverse it:

var mrkl_root = reverse("871714dcbae6c8193a2bb9b2a69fe1c0440399f38d94b3a0f1b447275a29978a")

Then the timestamp is a unixtimestamp to the date "2014-02-20 04:57:25", the timestamp value of that date is 1392872245, so you convert to hexadecimal value 53058B35, and REVERSE IT = "358b0553" (I wont put the code but you get the picture, ^^)

var timestamp= "358b0553";// # 2014-02-20 04:57:25

Then the number of bits as you can see here (https://blockchain.info/block-height/286819), is 419520339, convert to hexadecimal and you get 19015F53; And reverse it: 535f0119

var bits = "535f0119";

The nonce is a arbitrary value that you will iterate over until you get the desired final hash, in this examples was a integer value 856192328. You convert to 8 bytes hexadecimal and reverse it.

var nonce = reverse(856192328.ToString("X8"));

And that's it, if you apply the SHA256 two times over this header will give you the desired result:

var header = $"{ver}{prev_block}{mrkl_root}{timestamp}{bits}{nonce}";
byte[] a1 = Enumerable.Range(0, header.Length)
                     .Where(x => x % 2 == 0)
                     .Select(x => Convert.ToByte(header.Substring(x, 2), 16))
                     .ToArray(); 
var c = a1.ToArray();
SHA256 sha256 = SHA256.Create();
byte[] firstHash = sha256.ComputeHash(c);
byte[] hashOfHash = sha256.ComputeHash(firstHash);
Console.WriteLine(BitConverter.ToString(hashOfHash).Replace("-", "").ToLower()); //Output: 0000000000000000e067a478024addfecdc93628978aa52d91fabd4292982a50

levismad

Posted 2016-06-18T08:15:39.140

Reputation: 1