openssl-sha256-btc-address

参考这里这里
openssl见这里


#!/bin/sh

PRIVATE_KEY="ECDSA"
PUBLIC_KEY="ECDSA.pub"
BITCOIN_PRIVATE_KEY="bitcoin"
BITCOIN_PUBLIC_KEY="bitcoin.pub"

echo "Generating private key"
openssl ecparam -genkey -name secp256k1 -rand /dev/random -out $PRIVATE_KEY

echo "Generating public key"
openssl ec -in $PRIVATE_KEY -pubout -out $PUBLIC_KEY

echo "Generating Bitcoin private key"
openssl ec -in $PRIVATE_KEY -outform DER|tail -c +8|head -c 32|xxd -p -c 32 > $BITCOIN_PRIVATE_KEY

echo "Generating Bitcoin public key"
openssl ec -in $PRIVATE_KEY -pubout -outform DER|tail -c 65|xxd -p -c 65 > $BITCOIN_PUBLIC_KEY


#! bin/bash

# private_key_into_bitcoin_wif.sh: convert secp256k1 private key in hexadicimal number (HEX) to Bitcoin Wallet Import Format (WIF)
# Examples: 
# $ bash private_key_into_bitcoin_wif.sh fffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364139 > private_key_bitcoin.wif
# $ cat priv_key.txt | xargs bash private_key_into_bitcoin_wif.sh > private_key_bitcoin.wif
# $ bash private_key_into_bitcoin_wif.sh fffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364139 | echo "$(cat) importedkeylabel false" | xargs bitcoin-cli importprivkey && bitcoin-cli getaddressesbylabel importedkeylabel
# $ openssl rand -hex 32 | xargs bash private_key_into_bitcoin_wif.sh
# $ xxd -l 32 -p -c 32 /dev/random | xargs bash private_key_into_bitcoin_wif.sh
# $ od -t x --width=32 --endian=big -A n --skip-bytes=7 --read-bytes=32 priv_key_secp256k1.openssl.der | tr -d [:blank:] | xargs bash private_key_into_bitcoin_wif.sh
# $ openssl asn1parse -in priv_key_secp256k1.der -inform der -offset=5 -length=34 | cut -d ':' -f 4 | xargs bash private_key_into_bitcoin_wif.sh
# $ openssl ec -in private_key.openssl.pem -text | grep -A 3 'priv:' | tail -n 3 | tr -d -c [:xdigit:] | xargs bash private_key_into_bitcoin_wif.sh
# $ gpg --list-packets --verbose gpg.key | grep skey | grep -o -w -m 1 '[[:xdigit:]]\{64\}' | xargs bash private_key_into_bitcoin_wif.sh

declare -a -r BASE58_CHARSET=(1 2 3 4 5 6 7 8 9 A B C D E F G H J K L M N P Q R S T U V W X Y Z a b c d e f g h i j k m n o p q r s t u v w x y z)
declare -l hex_priv_key="$1"

#######################################
# Input validation - 64 characters and within the elliptic curve secp256k1 private key limit
#######################################
if [ ${#hex_priv_key} -ne 64 ]; then
  echo "ERROR: The input priv key is not 64 characters long."
  exit 1
fi

if [ "${hex_priv_key,,}" \> "fffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364140" ]; then
  echo "ERROR: The input priv key is not within max range of fffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364140"
  exit 2
fi

#######################################
# Converstion from HEX to WIF
#######################################
declare -r PRIVATE_KEY_WIF_PREFIX="80"
declare -r COMPRESSION_FLAG_WIF_SUFFIX="01"
declare hex_annotated_priv_key="${PRIVATE_KEY_WIF_PREFIX}${hex_priv_key}${COMPRESSION_FLAG_WIF_SUFFIX}"
declare double_sha256_digest=$( echo -n ${hex_annotated_priv_key} | xxd -r -p | sha256sum -b | xxd -r -p -l 64 | sha256sum -b )
hex_annotated_priv_key="${hex_annotated_priv_key}${double_sha256_digest:0:8}"
declare dividend="${hex_annotated_priv_key}"
declare -i -r divisor=${#BASE58_CHARSET[@]}
declare -i -r divisor_length=${#divisor}
declare -i subdividend=0
declare quotient="1"
declare -i i=0
declare -i j=0
declare -i position=0
declare -i leading_zeros=0
declare -i initial_zeros_in_priv_key=0
declare -a -i b58_int_array

while ((${#dividend} >= ${divisor_length})); do
  quotient=""
  for (( position=0; position<${#dividend}; position++ )); do
    subdividend=$((subdividend*16+16#${dividend:position:1}))
    quotient=$( printf "%s%X" "${quotient}" $((subdividend/divisor)) )
    subdividend=$((subdividend%divisor))
  done
  b58_int_array[i]=${subdividend}
  subdividend=0
  for (( leading_zeros=0; leading_zeros<${#quotient}; leading_zeros++ )); do
    if [ ${quotient:leading_zeros:1} != "0" ]; then
      break
    fi
  done
  dividend=${quotient:leading_zeros}
  i=$((i+1))
done

if (( leading_zeros != ${#quotient} )); then
  b58_int_array[i]=16#${dividend}
  i=$((i+1))
fi

for (( initial_zeros_in_priv_key=0; initial_zeros_in_priv_key<${#hex_annotated_priv_key}; initial_zeros_in_priv_key=initial_zeros_in_priv_key+2 )); do
  if [[ ${hex_annotated_priv_key:initial_zeros_in_priv_key:2} == "00" ]]; then
	b58_int_array[i]="0"
    i=$((i+1))
  else
    break
  fi
done

for (( j=${#b58_int_array[@]}-1; j >= 0; j-- )); do
  dec=${b58_int_array[j]}
  printf "%s" ${BASE58_CHARSET[dec]}
done

printf "\n"

# Release date: 2022-08-23