Skip to content

Commit

Permalink
[tool] Fix #13:将rust-crypto库采用其他的crate进行替代以解决mac下的M系兼容问题
Browse files Browse the repository at this point in the history
  • Loading branch information
tracker ming authored and tracker ming committed Jun 27, 2024
1 parent 4098683 commit 3fb8c22
Show file tree
Hide file tree
Showing 5 changed files with 162 additions and 59 deletions.
97 changes: 94 additions & 3 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 5 additions & 1 deletion tool/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@ tracing = "0.1"
tracing-subscriber = { version = "0.3", features = ["env-filter"] }
clap = { version = "4.3", features = ["derive"] }
anyhow = "1.0"
rust-crypto = "0.2.36"
secp256k1 = { version = "0.27.0", default-features = false, features = [
"global-context",
"rand-std",
Expand All @@ -39,3 +38,8 @@ csv = "1.3.0"
regex = "1.10.3"
num-traits = "0.2.18"
num-bigint = "0.4.4"
sha3 = "0.10.8"
sha2 = "0.10.8"
aes-gcm = "0.10.3"
bitcoin_hashes = "0.14.0"

36 changes: 16 additions & 20 deletions tool/src/btc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,10 @@ use crate::bip32::{derive_private_by_path, derive_public_by_path, mnemonic_to_x_
use crate::eth::get_public_key;
use anyhow::Result;
use bip32::{Prefix, PublicKey as Bip32PubKey};
use bitcoin_hashes::{ripemd160, Hash};
use bs58::{decode, encode};
use crypto::digest::Digest;
use crypto::{ripemd160, sha2::Sha256};
use secp256k1::{PublicKey, Secp256k1, SecretKey};
use sha2::{Digest, Sha256};
use std::str::FromStr;
use tracing::info;

Expand All @@ -21,20 +21,18 @@ const OP_CHECKSIG: u8 = 0xac;
// 先实现最基础的P2PKH和P2WPKH,其他的多签和script的类型暂不考虑,后续考虑优化,这里也不过多依赖第三方库
fn pub_key_to_address(public_key: PublicKey) -> String {
// sha256
let mut sha256 = Box::new(Sha256::new());
let mut sha256 = Sha256::new();
// 压缩型的地址
sha256.input(&public_key.serialize()[..]);
let mut out_1 = vec![0u8; sha256.output_bytes()];
sha256.result(&mut out_1);
sha256.update(&public_key.serialize()[..]);
let out_1 = sha256.finalize().to_vec();
// ripemd160
let mut hash = Box::new(ripemd160::Ripemd160::new());
hash.input(&out_1);
let mut out = vec![0u8; hash.output_bytes()];
hash.result(&mut out);
let mut hash = ripemd160::Hash::hash(&out_1);
let out_bytes: &[u8] = hash.as_ref();
let mut out: Vec<u8> = out_bytes.to_vec();
// P2PKH
let p2pkh = [
&[OP_DUP, OP_HASH160, out.len() as u8][..],
&out[..],
&[OP_DUP, OP_HASH160, 20][..],
&out,
&[OP_EQUALVERIFY, OP_CHECKSIG],
]
.concat();
Expand Down Expand Up @@ -84,14 +82,12 @@ pub fn get_tx_hash(raw_tx: String) -> Result<()> {
}

fn double_sha256(input: &[u8]) -> Vec<u8> {
let mut sha256 = Box::new(Sha256::new());
sha256.input(&input[..]);
let mut out = vec![0u8; sha256.output_bytes()];
sha256.result(&mut out);
let mut sha256 = Box::new(Sha256::new());
sha256.input(&out);
let mut result = vec![0u8; sha256.output_bytes()];
sha256.result(&mut result);
let mut sha256 = Sha256::new();
sha256.update(&input[..]);
let out = sha256.finalize().to_vec();
let mut sha256 = Sha256::new();
sha256.update(&out);
let result = sha256.finalize().to_vec();
result
}

Expand Down
72 changes: 43 additions & 29 deletions tool/src/encrypt_decrypt.rs
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
use crypto::aead::{AeadDecryptor, AeadEncryptor};
use crypto::{
aes::KeySize::KeySize256,
aes_gcm::AesGcm,
digest::Digest,
sha3::{Sha3, Sha3Mode},
use aes_gcm::aead::{AeadMut, Buffer};
use aes_gcm::{
aead::{Aead, AeadCore, OsRng},
Aes256Gcm, AesGcm, Key, KeyInit, Nonce,
};
use rand::prelude::*;
use sha3::{Digest, Keccak256};
use std::iter::repeat;
use std::{fmt::Write, string::String};
use tracing::info;
Expand All @@ -18,31 +17,36 @@ use crate::util::{hex_string_2_array, u8_array_convert_string};
///
fn generate_key(password: String) -> Vec<u8> {
let mut sh = Box::new(Sha3::new(Sha3Mode::Keccak256));
sh.input(&password.as_bytes());
let mut out = vec![0u8; sh.output_bytes()];
sh.result(&mut out);
let mut sh = Keccak256::new();
sh.update(&password.as_bytes());
let out = sh.finalize().to_vec();
out
}

pub fn encrypt(plaintext: String, password: String) -> anyhow::Result<()> {
info!("plaintext: {plaintext}");
let key = generate_key(password);
let mut rng = rand::thread_rng();
let mut iv = [0u8; 12];
rng.fill_bytes(&mut iv);
let mut aad = [0u8; 16];
rng.fill_bytes(&mut aad);
let mut aes_gcm = AesGcm::new(KeySize256, &key[..], &iv, &aad);
let aes_key = Key::<Aes256Gcm>::from_slice(key.as_slice());
let mut aes_gcm = Aes256Gcm::new(&aes_key);
let plaintext_array = plaintext.as_bytes();
let mut out: Vec<u8> = repeat(0)
.take((plaintext_array.len() as u64).try_into().unwrap())
.collect();
let mut out_tag: Vec<u8> = repeat(0).take(16).collect();
aes_gcm.encrypt(&plaintext_array, &mut out[..], &mut out_tag);
let out_str: String = u8_array_convert_string(&out);
let iv_str = u8_array_convert_string(&iv);
let tag_str = u8_array_convert_string(&out_tag);
let nonce = Aes256Gcm::generate_nonce(OsRng);
let mut out = aes_gcm
.encrypt(
&nonce,
aes_gcm::aead::Payload {
msg: plaintext_array,
aad: aad.as_slice(),
},
)
.unwrap();
println!("out: {:?}", out);
let index = out.len() - 16;
let out_str: String = u8_array_convert_string(&out[..index]);
let iv_str = u8_array_convert_string(&nonce.as_slice());
let tag_str = u8_array_convert_string(&out[index..]);
let aad_str = u8_array_convert_string(&aad);
info!(
"cipher: {:?}\n{:?}, \niv: {:?}\n tag:{:?}, aav: {:?}",
Expand All @@ -60,17 +64,27 @@ pub fn decrypt(
) -> anyhow::Result<()> {
info!("cipher: {cipher}");
let key = generate_key(password);
let cipher_arr = hex_string_2_array(&cipher);
let iv = hex_string_2_array(&iv);
let mut cipher_arr = hex_string_2_array(&cipher);
let mut nonce_arr = hex_string_2_array(&iv);
let tag = hex_string_2_array(&tag);
let aad = hex_string_2_array(&aad);
let mut aes_gcm = AesGcm::new(KeySize256, &key[..], &iv, &aad);
let mut out: Vec<u8> = repeat(0).take(cipher_arr.len()).collect();
let result = aes_gcm.decrypt(&cipher_arr, &mut out, &tag);
let plaintext = String::from_utf8(out.clone()).unwrap();
let aes_key = Key::<Aes256Gcm>::from_slice(key.as_slice());
let mut aes_gcm = Aes256Gcm::new(&aes_key);
cipher_arr.extend_from_slice(&tag);
let result = aes_gcm
.decrypt(
&Nonce::from_slice(nonce_arr.as_slice()),
aes_gcm::aead::Payload {
msg: cipher_arr.as_slice(),
aad: &aad,
},
)
.unwrap();
//let result = aes_gcm.decrypt(&cipher_arr, &mut out, &tag);
let plaintext = String::from_utf8(result.clone()).unwrap();
println!(
"decrypt success: {:?}, result: {:?}, plaintext: {:?}",
result, out, plaintext
"decrypt success, result: {:?}, plaintext: {:?}",
result, plaintext
);
Ok(())
}
Expand Down
Loading

0 comments on commit 3fb8c22

Please sign in to comment.