0

I need to get from a biginteger to a 32 byte hex value. To use in the third parameter on this description:

getwWork documentation

My current code is not generating a valid hex value.

public static string GetTargetHex(BigInteger difficulty)
{
    // 2^256 / difficulty.
    var target = BigInteger.Divide(BigInteger.Pow(2, 256), difficulty);
    return $"0x{target.ToString("X16").ToLower()}";
}

All I have to go by for now is knowing that a value of 23142114022743 results in a hex value of '0x00000000000c29b321174712bb7ca6dd0896b050e18d4c7e13df4c1aee84f2c0'.

Erik
  • 417
  • 4
  • 14
  • 6
    Please include the description as *text* rather than as a screenshot. There's no benefit in using a screenshot here. Additionally, please give more details about what you mean by "is not generating a valid hex value" - what *is* it generating, and what did you expect? Ideally, provide a [mcve]. – Jon Skeet Jun 09 '18 at 08:59
  • 1
    Can you give us a link to the documentation you got the description from? – Andrew Morton Jun 09 '18 at 10:25
  • @AndrewMorton https://github.com/ethereum/wiki/wiki/JSON-RPC#eth_getwork. It's the boundary for Ethereum's proof of work mining. – Erik Jun 09 '18 at 13:40
  • 1
    I suspect that your example is wrong because I get 0x00000000000c29b321174712bb7ca6dd0896b050e18d4c7e13df4c1aee84f2c1 in both C# and Python. Or maybe it's a non-inclusive (<) boundary, so you need to subtract 1 to get the inclusive (<=) boundary. – Andrew Morton Jun 09 '18 at 14:08
  • @AndrewMorton sounds plausible. By what method did you get to your value in c#? – Erik Jun 10 '18 at 09:55
  • @Erik I used 23142114022743 as the value of the parameter of the function you showed in the question. (.NET Framework 4.7.2, Platform target x86/x64/Any CPU, Windows 10 x64, Intel Core i7 920.) – Andrew Morton Jun 10 '18 at 20:48
  • Thanks. That's a bit embarrassing. Just had to pad the string with 0's to get to the correct length and now my mining software is accepting the boundary/difficulty. – Erik Jun 11 '18 at 08:20

1 Answers1

0

Ethereum has their own standard for Hex encoding / decoding.

You can use Nethereum for this.

From the screen shot to get your work:

using System;
using System.Text;
using Nethereum.Hex.HexConvertors.Extensions;
using System.Threading.Tasks;
using Nethereum.Web3;
using Nethereum.RPC.Eth.Blocks;
using Nethereum.Hex.HexTypes;

public class HexDecoding
{
    private static async Task Main(string[] args)
    {
        var web3 = new Web3("your url");
        var work = await web3.Eth.Mining.GetWork.SendRequestAsync();
                Console.WriteLine(work.Length);
    }
}

And to do the calculation, depending in your endianism you can do something like this:

using System;
using System.Text;
using Nethereum.Hex.HexConvertors.Extensions;
using System.Threading.Tasks;
using Nethereum.Web3;
using Nethereum.RPC.Eth.Blocks;
using Nethereum.Hex.HexTypes;
using System.Numerics;

public class HexDecoding
{
    private static async Task Main(string[] args)
    {
         var difficulty = 23142114022743;
         var target = BigInteger.Divide(BigInteger.Pow(2, 256), difficulty);
         Console.WriteLine(target);


        // A simple check on endianism and reversing
        byte[] bytes;
        Console.WriteLine(BitConverter.IsLittleEndian);
        if (BitConverter.IsLittleEndian) 
                bytes = target.ToByteArray().Reverse().ToArray();
            else
                bytes = target.ToByteArray().ToArray();

        Console.WriteLine(bytes.ToHex());


         //Another option using .Net core now (awesome)
        Console.WriteLine(target.ToByteArray(true, true).ToHex()); // new .net core 

         //Final option if you are using Nethereum and not using .Net core
        Console.WriteLine(HexBigIntegerConvertorExtensions.ToByteArray(target, false).ToHex()); 
                //0x00000000000c29b321174712bb7ca6dd0896b050e18d4c7e13df4c1aee84f2c0

                //0x00000000000c29b321174712bb7ca6dd0896b050e18d4c7e13df4c1aee84f2c0
    }
}
Juan Blanco
  • 421
  • 2
  • 6