比特币–通过公钥生成地址全过程

import org.ethereum.util.ByteUtil;

public class AddressUtil {
	
	public static String generateAddressFromHexPub(String hexPubKeyStr, String version) {
		//公钥sha256得到a
		String a = SHAEncrypt.SHA256WithHex(hexPubKeyStr);
		//a进行ripemd160计算后转hexString得到b
		String b = ByteUtil.toHexString(Ripemd160.getHashWithHex(a));
		//两次sha256, sha256(sha256(version + b))得到c
		String c = SHAEncrypt.SHA256WithHex(SHAEncrypt.SHA256WithHex(version + b));
		//(version + b + c的前4个字节,十六进制前八位) 得到十六进制字符串d
		String d = version + b + c.substring(0, 8);
		//对d进行base58编码得到地址
		String address = Base58.encode(ByteUtil.hexStringToBytes(d));
		return address;
	}

	public static void main(String[] args) {
		String version = "00";
		String hexPubKeyStr = "026d9a6baec4d380091b9881400dbd99ca90bae0f61e171df121dd2ff0e2ac9517";
		System.out.println(generateAddressFromHexPub(hexPubKeyStr, version));
		//1Po8pvaAHE3V9twnSGXZwEXEkwctcCtWDe
	}
}
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;

import org.ethereum.util.ByteUtil;

public class SHAEncrypt {
	public static String SHA256(final String strText)
	{
		return SHA(strText.getBytes(), "SHA-256");
	}
	public static String SHA256WithHex(final String hexStr)
	{
		return SHA(ByteUtil.hexStringToBytes(hexStr), "SHA-256");
	}

	public static String SHA512(final String strText)
	{
		return SHA(strText.getBytes(), "SHA-512");
	}

	public static String SHA512WithHex(final String hexStr)
	{
		return SHA(ByteUtil.hexStringToBytes(hexStr), "SHA-512");
	}

	private static String SHA(final byte[] text, final String strType)
	{
		String strResult = null;

		if (text != null && text.length > 0)
		{
			try
			{
				MessageDigest messageDigest = MessageDigest.getInstance(strType);
				messageDigest.update(text);
				byte byteBuffer[] = messageDigest.digest();

				StringBuffer strHexString = new StringBuffer();
				for (int i = 0; i < byteBuffer.length; i++)
				{
					String hex = Integer.toHexString(0xff & byteBuffer[i]);
					if (hex.length() == 1)
					{
						strHexString.append('0');
					}
					strHexString.append(hex);
				}
				strResult = strHexString.toString();
			}
			catch (NoSuchAlgorithmException e)
			{
				e.printStackTrace();
			}
		}

		return strResult;
	}
}
import static java.lang.Integer.rotateLeft;
import java.util.Arrays;
import java.util.Objects;

import org.ethereum.util.ByteUtil;


public final class Ripemd160 {

	private static final int BLOCK_LEN = 64;  // In bytes

	public static byte[] getHashWithHex(String hexMsg) {
		return getHash(ByteUtil.hexStringToBytes(hexMsg));
	}

	public static byte[] getHash(byte[] msg) {
		Objects.requireNonNull(msg);
		int[] state = {0x67452301, 0xEFCDAB89, 0x98BADCFE, 0x10325476, 0xC3D2E1F0};
		int off = msg.length / BLOCK_LEN * BLOCK_LEN;
		compress(state, msg, off);

		byte[] block = new byte[BLOCK_LEN];
		System.arraycopy(msg, off, block, 0, msg.length - off);
		off = msg.length % block.length;
		block[off] = (byte)0x80;
		off++;
		if (off + 8 > block.length) {
			compress(state, block, block.length);
			Arrays.fill(block, (byte)0);
		}
		long len = (long)msg.length << 3;
		for (int i = 0; i < 8; i++)
			block[block.length - 8 + i] = (byte)(len >>> (i * 8));
		compress(state, block, block.length);

		byte[] result = new byte[state.length * 4];
		for (int i = 0; i < result.length; i++)
			result[i] = (byte)(state[i / 4] >>> (i % 4 * 8));
		return result;
	}

	private static void compress(int[] state, byte[] blocks, int len) {
		if (len % BLOCK_LEN != 0)
			throw new IllegalArgumentException();
		for (int i = 0; i < len; i += BLOCK_LEN) {
			int[] schedule = new int[16];
			for (int j = 0; j < BLOCK_LEN; j++)
				schedule[j / 4] |= (blocks[i + j] & 0xFF) << (j % 4 * 8);
			int al = state[0], ar = state[0];
			int bl = state[1], br = state[1];
			int cl = state[2], cr = state[2];
			int dl = state[3], dr = state[3];
			int el = state[4], er = state[4];
			for (int j = 0; j < 80; j++) {
				int temp;
				temp = rotateLeft(al + f(j, bl, cl, dl) + schedule[RL[j]] + KL[j / 16], SL[j]) + el;
				al = el;
				el = dl;
				dl = rotateLeft(cl, 10);
				cl = bl;
				bl = temp;
				temp = rotateLeft(ar + f(79 - j, br, cr, dr) + schedule[RR[j]] + KR[j / 16], SR[j]) + er;
				ar = er;
				er = dr;
				dr = rotateLeft(cr, 10);
				cr = br;
				br = temp;
			}
			int temp = state[1] + cl + dr;
			state[1] = state[2] + dl + er;
			state[2] = state[3] + el + ar;
			state[3] = state[4] + al + br;
			state[4] = state[0] + bl + cr;
			state[0] = temp;
		}
	}


	private static int f(int i, int x, int y, int z) {
		assert 0 <= i && i < 80;
		if (i < 16) return x ^ y ^ z;
		if (i < 32) return (x & y) | (~x & z);
		if (i < 48) return (x | ~y) ^ z;
		if (i < 64) return (x & z) | (y & ~z);
		return x ^ (y | ~z);
	}

	private static final int[] KL = {0x00000000, 0x5A827999, 0x6ED9EBA1, 0x8F1BBCDC, 0xA953FD4E};  // Round constants for left line
	private static final int[] KR = {0x50A28BE6, 0x5C4DD124, 0x6D703EF3, 0x7A6D76E9, 0x00000000};  // Round constants for right line

	private static final int[] RL = {  // Message schedule for left line
			0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15,
			7,  4, 13,  1, 10,  6, 15,  3, 12,  0,  9,  5,  2, 14, 11,  8,
			3, 10, 14,  4,  9, 15,  8,  1,  2,  7,  0,  6, 13, 11,  5, 12,
			1,  9, 11, 10,  0,  8, 12,  4, 13,  3,  7, 15, 14,  5,  6,  2,
			4,  0,  5,  9,  7, 12,  2, 10, 14,  1,  3,  8, 11,  6, 15, 13};

	private static final int[] RR = {  // Message schedule for right line
			5, 14,  7,  0,  9,  2, 11,  4, 13,  6, 15,  8,  1, 10,  3, 12,
			6, 11,  3,  7,  0, 13,  5, 10, 14, 15,  8, 12,  4,  9,  1,  2,
			15,  5,  1,  3,  7, 14,  6,  9, 11,  8, 12,  2, 10,  0,  4, 13,
			8,  6,  4,  1,  3, 11, 15,  0,  5, 12,  2, 13,  9,  7, 10, 14,
			12, 15, 10,  4,  1,  5,  8,  7,  6,  2, 13, 14,  0,  3,  9, 11};

	private static final int[] SL = {  // Left-rotation for left line
			11, 14, 15, 12,  5,  8,  7,  9, 11, 13, 14, 15,  6,  7,  9,  8,
			7,  6,  8, 13, 11,  9,  7, 15,  7, 12, 15,  9, 11,  7, 13, 12,
			11, 13,  6,  7, 14,  9, 13, 15, 14,  8, 13,  6,  5, 12,  7,  5,
			11, 12, 14, 15, 14, 15,  9,  8,  9, 14,  5,  6,  8,  6,  5, 12,
			9, 15,  5, 11,  6,  8, 13, 12,  5, 12, 13, 14, 11,  8,  5,  6};

	private static final int[] SR = {  // Left-rotation for right line
			8,  9,  9, 11, 13, 15, 15,  5,  7,  7,  8, 11, 14, 14, 12,  6,
			9, 13, 15,  7, 12,  8,  9, 11,  7,  7, 12,  7,  6, 15, 13, 11,
			9,  7, 15, 11,  8,  6,  6, 14, 12, 13,  5, 14, 13, 13,  7,  5,
			15,  5,  8, 11, 14, 14,  6, 14,  6,  9, 12,  9, 12,  5, 15,  8,
			8,  5, 12,  9, 12,  5, 14,  6,  8, 13,  6,  5, 15, 13, 11, 11};



	private Ripemd160() {}  // Not instantiable

}
import java.math.BigInteger;
import java.util.Arrays;

public class Base58 {
	public static final char[] ALPHABET = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz".toCharArray();
	private static final char ENCODED_ZERO = ALPHABET[0];
	private static final int[] INDEXES = new int[128];
	static {
		Arrays.fill(INDEXES, -1);
		for (int i = 0; i < ALPHABET.length; i++) {
			INDEXES[ALPHABET[i]] = i;
		}
	}

	public static String encode(byte[] input) {
		if (input.length == 0) {
			return "";
		}
		int zeros = 0;
		while (zeros < input.length && input[zeros] == 0) {
			++zeros;
		}
		input = Arrays.copyOf(input, input.length); // since we modify it in-place
		char[] encoded = new char[input.length * 2]; // upper bound
		int outputStart = encoded.length;
		for (int inputStart = zeros; inputStart < input.length; ) {
			encoded[--outputStart] = ALPHABET[divmod(input, inputStart, 256, 58)];
			if (input[inputStart] == 0) {
				++inputStart; // optimization - skip leading zeros
			}
		}
		while (outputStart < encoded.length && encoded[outputStart] == ENCODED_ZERO) {
			++outputStart;
		}
		while (--zeros >= 0) {
			encoded[--outputStart] = ENCODED_ZERO;
		}
		return new String(encoded, outputStart, encoded.length - outputStart);
	}

	public static byte[] decode(String input) {
		if (input.length() == 0) {
			return new byte[0];
		}
		byte[] input58 = new byte[input.length()];
		for (int i = 0; i < input.length(); ++i) {
			char c = input.charAt(i);
			int digit = c < 128 ? INDEXES[c] : -1;
			if (digit < 0) {
				throw new IllegalStateException("InvalidCharacter in base 58");
			}
			input58[i] = (byte) digit;
		}
		int zeros = 0;
		while (zeros < input58.length && input58[zeros] == 0) {
			++zeros;
		}
		byte[] decoded = new byte[input.length()];
		int outputStart = decoded.length;
		for (int inputStart = zeros; inputStart < input58.length; ) {
			decoded[--outputStart] = divmod(input58, inputStart, 58, 256);
			if (input58[inputStart] == 0) {
				++inputStart; // optimization - skip leading zeros
			}
		}
		while (outputStart < decoded.length && decoded[outputStart] == 0) {
			++outputStart;
		}
		return Arrays.copyOfRange(decoded, outputStart - zeros, decoded.length);
	}

	public static BigInteger decodeToBigInteger(String input) {
		return new BigInteger(1, decode(input));
	}

	private static byte divmod(byte[] number, int firstDigit, int base, int divisor) {
		int remainder = 0;
		for (int i = firstDigit; i < number.length; i++) {
			int digit = (int) number[i] & 0xFF;
			int temp = remainder * base + digit;
			number[i] = (byte) (temp / divisor);
			remainder = temp % divisor;
		}
		return (byte) remainder;
	}
}

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
THE END
分享
二维码

)">
< <上一篇
下一篇>>