Commit 4d234ea8 authored by YJ's avatar YJ
Browse files

fix: merge master

parents e1363ffb eb55ff68
......@@ -44,6 +44,15 @@ public class EthkeyBridge extends ReactContextBaseJavaModule {
promise.resolve(ethkeyBrainwalletAddress(seed));
}
@ReactMethod
public void brainWalletBIP39Address(String seed, Promise promise) {
try {
promise.resolve(ethkeyBrainwalletBIP39Address(seed));
} catch (Exception e) {
promise.reject("invalid phrase", null, null);
}
}
@ReactMethod
public void brainWalletSign(String seed, String message, Promise promise) {
promise.resolve(ethkeyBrainwalletSign(seed, message));
......@@ -93,7 +102,17 @@ public class EthkeyBridge extends ReactContextBaseJavaModule {
}
}
@ReactMethod
public void qrCode(String data, Promise promise) {
try {
promise.resolve(ethkeyQrCode(data));
} catch (Exception e) {
promise.reject("failed to create QR code", null, null);
}
}
private static native String ethkeyBrainwalletAddress(String seed);
private static native String ethkeyBrainwalletBIP39Address(String seed);
private static native String ethkeyBrainwalletSign(String seed, String message);
private static native String ethkeyRlpItem(String data, int position);
private static native String ethkeyKeccak(String data);
......@@ -102,4 +121,5 @@ public class EthkeyBridge extends ReactContextBaseJavaModule {
private static native String ethkeyRandomPhrase();
private static native String ethkeyEncryptData(String data, String password);
private static native String ethkeyDecryptData(String data, String password);
private static native String ethkeyQrCode(String data);
}
//
// EthkeyBridge.swift
// NativeSigner
//
// Created by Marek Kotewicz on 19/02/2017.
// Copyright © 2017 Facebook. All rights reserved.
//
import Foundation
@objc(EthkeyBridge)
class EthkeyBridge: NSObject {
@objc func brainWalletAddress(_ seed: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var seed_ptr = seed.asPtr()
let keypair_ptr = ethkey_keypair_brainwallet(&seed_ptr)
let address_rust_str = ethkey_keypair_address(keypair_ptr)
let address_rust_str_ptr = rust_string_ptr(address_rust_str)
let address = String.fromStringPtr(ptr: address_rust_str_ptr!.pointee)
rust_string_ptr_destroy(address_rust_str_ptr)
rust_string_destroy(address_rust_str)
ethkey_keypair_destroy(keypair_ptr)
resolve(address)
}
@objc func brainWalletSecret(_ seed: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var seed_ptr = seed.asPtr()
let keypair_ptr = ethkey_keypair_brainwallet(&seed_ptr)
let secret_rust_str = ethkey_keypair_secret(keypair_ptr)
let secret_rust_str_ptr = rust_string_ptr(secret_rust_str)
let secret = String.fromStringPtr(ptr: secret_rust_str_ptr!.pointee)
rust_string_ptr_destroy(secret_rust_str_ptr)
rust_string_destroy(secret_rust_str)
ethkey_keypair_destroy(keypair_ptr)
resolve(secret)
}
@objc func brainWalletSign(_ seed: String, message: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
print(seed, " + ", message)
var seed_ptr = seed.asPtr()
var message_ptr = message.asPtr()
let keypair_ptr = ethkey_keypair_brainwallet(&seed_ptr)
let signature_rust_str = ethkey_keypair_sign(keypair_ptr, &message_ptr)
let signature_rust_str_ptr = rust_string_ptr(signature_rust_str)
let signature = String.fromStringPtr(ptr: signature_rust_str_ptr!.pointee)
rust_string_ptr_destroy(signature_rust_str_ptr)
rust_string_destroy(signature_rust_str)
ethkey_keypair_destroy(keypair_ptr)
resolve(signature)
}
@objc func rlpItem(_ rlp: String, position: UInt32, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var rlp_ptr = rlp.asPtr()
var error: UInt32 = 0
let item_rust_str = rlp_item(&rlp_ptr, position, &error)
let item_rust_str_ptr = rust_string_ptr(item_rust_str)
let item = String.fromStringPtr(ptr: item_rust_str_ptr!.pointee)
rust_string_ptr_destroy(item_rust_str_ptr)
rust_string_destroy(item_rust_str)
if (error == 0) {
resolve(item)
} else {
reject("invalid rlp", nil, nil)
}
}
@objc func keccak(_ data: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var data_ptr = data.asPtr()
let hash_rust_str = keccak256(&data_ptr)
let hash_rust_str_ptr = rust_string_ptr(hash_rust_str)
let hash = String.fromStringPtr(ptr: hash_rust_str_ptr!.pointee)
rust_string_ptr_destroy(hash_rust_str_ptr)
rust_string_destroy(hash_rust_str)
resolve(hash)
}
@objc func ethSign(_ data: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var data_ptr = data.asPtr()
let hash_rust_str = eth_sign(&data_ptr)
let hash_rust_str_ptr = rust_string_ptr(hash_rust_str)
let hash = String.fromStringPtr(ptr: hash_rust_str_ptr!.pointee)
rust_string_ptr_destroy(hash_rust_str_ptr)
rust_string_destroy(hash_rust_str)
resolve(hash)
}
@objc func blockiesIcon(_ seed: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var seed_ptr = seed.asPtr()
let icon_rust_str = blockies_icon(&seed_ptr)
let icon_rust_str_ptr = rust_string_ptr(icon_rust_str)
let icon = String.fromStringPtr(ptr: icon_rust_str_ptr!.pointee)
rust_string_ptr_destroy(icon_rust_str_ptr)
rust_string_destroy(icon_rust_str)
resolve(icon)
}
@objc func randomPhrase(resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
let words_rust_str = random_phrase()
let words_rust_str_ptr = rust_string_ptr(words_rust_str)
let words = String.fromStringPtr(ptr: words_rust_str_ptr!.pointee)
rust_string_ptr_destroy(words_rust_str_ptr)
rust_string_destroy(words_rust_str)
resolve(words)
}
@objc func encryptData(_ data: String, password: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var data_ptr = data.asPtr()
var password_ptr = password.asPtr()
let encrypted_data_rust_str = encrypt_data(&data_ptr, &password_ptr)
let encrypted_data_rust_str_ptr = rust_string_ptr(encrypted_data_rust_str)
let encrypted_data = String.fromStringPtr(ptr: encrypted_data_rust_str_ptr!.pointee)
rust_string_ptr_destroy(encrypted_data_rust_str_ptr)
rust_string_destroy(encrypted_data_rust_str)
resolve(encrypted_data)
}
@objc func decryptData(_ data: String, password: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var data_ptr = data.asPtr()
var password_ptr = password.asPtr()
var error: UInt32 = 0
let decrypted_data_rust_str = decrypt_data(&data_ptr, &password_ptr, &error)
let decrypted_data_rust_str_ptr = rust_string_ptr(decrypted_data_rust_str)
let decrypted_data = String.fromStringPtr(ptr: decrypted_data_rust_str_ptr!.pointee)
rust_string_ptr_destroy(decrypted_data_rust_str_ptr)
rust_string_destroy(decrypted_data_rust_str)
if error == 0 {
resolve(decrypted_data)
} else if error == 1{
reject("invalid data", nil, nil)
} else {
reject("invalid password", nil, nil)
}
}
}
......@@ -32,8 +32,9 @@ RCT_EXTERN_METHOD(rlpItem:(NSString*)rlp position:(NSUInteger)position resolve:(
RCT_EXTERN_METHOD(keccak:(NSString*)data resolve:(RCTPromiseResolveBlock)resolve reject:(RCTPromiseRejectBlock)reject)
RCT_EXTERN_METHOD(ethSign:(NSString*)data resolve:(RCTPromiseResolveBlock)resolve reject:(RCTPromiseRejectBlock)reject)
RCT_EXTERN_METHOD(blockiesIcon:(NSString*)seed resolve:(RCTPromiseResolveBlock)resolve reject:(RCTPromiseRejectBlock)reject)
RCT_EXTERN_METHOD(randomPhrase:(NSUInteger)words resolve:(RCTPromiseResolveBlock)resolve reject:(RCTPromiseRejectBlock)reject)
RCT_EXTERN_METHOD(randomPhrase:(RCTPromiseResolveBlock)resolve reject:(RCTPromiseRejectBlock)reject)
RCT_EXTERN_METHOD(encryptData:(NSString*)data password:(NSString*)password resolve:(RCTPromiseResolveBlock)resolve reject:(RCTPromiseRejectBlock)reject)
RCT_EXTERN_METHOD(decryptData:(NSString*)data password:(NSString*)password resolve:(RCTPromiseResolveBlock)resolve reject:(RCTPromiseRejectBlock)reject)
RCT_EXTERN_METHOD(qrCode:(NSString*)data resolve:(RCTPromiseResolveBlock)resolve reject:(RCTPromiseRejectBlock)reject)
@end
......@@ -11,40 +11,38 @@ import Foundation
@objc(EthkeyBridge)
class EthkeyBridge: NSObject {
open static func requiresMainQueueSetup() -> Bool {
public static func requiresMainQueueSetup() -> Bool {
return true;
}
@objc func brainWalletAddress(_ seed: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
var seed_ptr = seed.asPtr()
let keypair_ptr = ethkey_keypair_brainwallet(&seed_ptr)
let address_rust_str = ethkey_keypair_address(keypair_ptr)
let address_rust_str = ethkey_brainwallet_address(&error, &seed_ptr)
let address_rust_str_ptr = rust_string_ptr(address_rust_str)
let address = String.fromStringPtr(ptr: address_rust_str_ptr!.pointee)
rust_string_ptr_destroy(address_rust_str_ptr)
rust_string_destroy(address_rust_str)
ethkey_keypair_destroy(keypair_ptr)
resolve(address)
}
@objc func brainWalletSign(_ seed: String, message: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
print(seed, " + ", message)
var seed_ptr = seed.asPtr()
var message_ptr = message.asPtr()
let keypair_ptr = ethkey_keypair_brainwallet(&seed_ptr)
let signature_rust_str = ethkey_keypair_sign(keypair_ptr, &message_ptr)
let signature_rust_str = ethkey_brainwallet_sign(&error, &seed_ptr, &message_ptr)
let signature_rust_str_ptr = rust_string_ptr(signature_rust_str)
let signature = String.fromStringPtr(ptr: signature_rust_str_ptr!.pointee)
rust_string_ptr_destroy(signature_rust_str_ptr)
rust_string_destroy(signature_rust_str)
ethkey_keypair_destroy(keypair_ptr)
resolve(signature)
}
@objc func rlpItem(_ rlp: String, position: UInt32, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var rlp_ptr = rlp.asPtr()
var error: UInt32 = 0
let item_rust_str = rlp_item(&rlp_ptr, position, &error)
var rlp_ptr = rlp.asPtr()
let item_rust_str = rlp_item(&error, &rlp_ptr, position)
let item_rust_str_ptr = rust_string_ptr(item_rust_str)
let item = String.fromStringPtr(ptr: item_rust_str_ptr!.pointee)
rust_string_ptr_destroy(item_rust_str_ptr)
......@@ -57,8 +55,9 @@ class EthkeyBridge: NSObject {
}
@objc func keccak(_ data: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
var data_ptr = data.asPtr()
let hash_rust_str = keccak256(&data_ptr)
let hash_rust_str = keccak256(&error, &data_ptr)
let hash_rust_str_ptr = rust_string_ptr(hash_rust_str)
let hash = String.fromStringPtr(ptr: hash_rust_str_ptr!.pointee)
rust_string_ptr_destroy(hash_rust_str_ptr)
......@@ -67,8 +66,9 @@ class EthkeyBridge: NSObject {
}
@objc func ethSign(_ data: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
var data_ptr = data.asPtr()
let hash_rust_str = eth_sign(&data_ptr)
let hash_rust_str = eth_sign(&error, &data_ptr)
let hash_rust_str_ptr = rust_string_ptr(hash_rust_str)
let hash = String.fromStringPtr(ptr: hash_rust_str_ptr!.pointee)
rust_string_ptr_destroy(hash_rust_str_ptr)
......@@ -77,17 +77,23 @@ class EthkeyBridge: NSObject {
}
@objc func blockiesIcon(_ seed: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
var seed_ptr = seed.asPtr()
let icon_rust_str = blockies_icon(&seed_ptr)
let icon_rust_str = blockies_icon(&error, &seed_ptr)
let icon_rust_str_ptr = rust_string_ptr(icon_rust_str)
let icon = String.fromStringPtr(ptr: icon_rust_str_ptr!.pointee)
rust_string_ptr_destroy(icon_rust_str_ptr)
rust_string_destroy(icon_rust_str)
resolve(icon)
if error == 0 {
resolve(icon)
} else {
reject("Failed to generate blockies", nil, nil)
}
}
@objc func randomPhrase(resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
let words_rust_str = random_phrase()
@objc func randomPhrase(_ resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
let words_rust_str = random_phrase(&error)
let words_rust_str_ptr = rust_string_ptr(words_rust_str)
let words = String.fromStringPtr(ptr: words_rust_str_ptr!.pointee)
rust_string_ptr_destroy(words_rust_str_ptr)
......@@ -96,9 +102,10 @@ class EthkeyBridge: NSObject {
}
@objc func encryptData(_ data: String, password: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
var data_ptr = data.asPtr()
var password_ptr = password.asPtr()
let encrypted_data_rust_str = encrypt_data(&data_ptr, &password_ptr)
let encrypted_data_rust_str = encrypt_data(&error, &data_ptr, &password_ptr)
let encrypted_data_rust_str_ptr = rust_string_ptr(encrypted_data_rust_str)
let encrypted_data = String.fromStringPtr(ptr: encrypted_data_rust_str_ptr!.pointee)
rust_string_ptr_destroy(encrypted_data_rust_str_ptr)
......@@ -107,20 +114,33 @@ class EthkeyBridge: NSObject {
}
@objc func decryptData(_ data: String, password: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
var data_ptr = data.asPtr()
var password_ptr = password.asPtr()
var error: UInt32 = 0
let decrypted_data_rust_str = decrypt_data(&data_ptr, &password_ptr, &error)
let decrypted_data_rust_str = decrypt_data(&error, &data_ptr, &password_ptr)
let decrypted_data_rust_str_ptr = rust_string_ptr(decrypted_data_rust_str)
let decrypted_data = String.fromStringPtr(ptr: decrypted_data_rust_str_ptr!.pointee)
rust_string_ptr_destroy(decrypted_data_rust_str_ptr)
rust_string_destroy(decrypted_data_rust_str)
if error == 0 {
resolve(decrypted_data)
} else if error == 1{
reject("invalid data", nil, nil)
} else {
reject("invalid password", nil, nil)
}
}
@objc func qrCode(_ data: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
var error: UInt32 = 0
var data_ptr = data.asPtr()
let icon_rust_str = qrcode(&error, &data_ptr)
let icon_rust_str_ptr = rust_string_ptr(icon_rust_str)
let icon = String.fromStringPtr(ptr: icon_rust_str_ptr!.pointee)
rust_string_ptr_destroy(icon_rust_str_ptr)
rust_string_destroy(icon_rust_str)
if error == 0 {
resolve(icon)
} else {
reject("Failed to generate blockies", nil, nil)
}
}
}
......@@ -28,7 +28,7 @@ extension String {
let data = NSData(bytes: UnsafeRawPointer(ptr.ptr), length: ptr.len)
return String(data: data as Data, encoding: String.Encoding.utf8)!
}
func asPtr() -> rust_string_ptr {
let data = self.data(using: String.Encoding.utf8, allowLossyConversion: false)!
return rust_string_ptr(ptr: (data as NSData).bytes.bindMemory(to: UInt8.self, capacity: data.count), len: data.count)
......
// Copyright 2015-2017 Parity Technologies (UK) Ltd.
// This file is part of Parity.
// Parity is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
// Parity is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
// You should have received a copy of the GNU General Public License
// along with Parity. If not, see <http://www.gnu.org/licenses/>.
extern crate libc;
extern crate rustc_serialize;
extern crate tiny_keccak;
extern crate parity_wordlist as wordlist;
extern crate ethkey;
extern crate ethstore;
extern crate rlp;
extern crate blockies;
mod string;
use rustc_serialize::hex::{ToHex, FromHex};
use rustc_serialize::base64::{self, ToBase64};
use tiny_keccak::Keccak;
use ethkey::{KeyPair, Generator, Brain, Message, sign};
use ethstore::Crypto;
use rlp::UntrustedRlp;
use blockies::{Blockies, create_icon, ethereum};
use string::StringPtr;
fn blockies_icon_in_base64(seed: Vec<u8>) -> String {
let mut result = Vec::new();
let options = ethereum::Options {
size: 8,
scale: 16,
seed: seed,
color: None,
background_color: None,
spot_color: None,
};
create_icon(&mut result, Blockies::Ethereum(options)).unwrap();
result.to_base64(base64::Config {
char_set: base64::CharacterSet::Standard,
newline: base64::Newline::LF,
pad: true,
line_length: None,
})
}
// string ffi
#[no_mangle]
pub unsafe extern fn rust_string_ptr(s: *mut String) -> *mut StringPtr {
Box::into_raw(Box::new(StringPtr::from(&**s)))
}
#[no_mangle]
pub unsafe extern fn rust_string_destroy(s: *mut String) {
let _ = Box::from_raw(s);
}
#[no_mangle]
pub unsafe extern fn rust_string_ptr_destroy(s: *mut StringPtr) {
let _ = Box::from_raw(s);
}
// ethkey ffi
#[no_mangle]
pub unsafe extern fn ethkey_keypair_destroy(keypair: *mut KeyPair) {
let _ = Box::from_raw(keypair);
}
#[no_mangle]
pub unsafe extern fn ethkey_keypair_brainwallet(seed: *mut StringPtr) -> *mut KeyPair {
let generator = Brain::new((*seed).as_str().to_owned());
Box::into_raw(Box::new(generator.generate().unwrap()))
}
#[no_mangle]
pub unsafe extern fn ethkey_keypair_secret(keypair: *mut KeyPair) -> *mut String {
let secret = format!("{:?}", (*keypair).secret());
Box::into_raw(Box::new(secret))
}
#[no_mangle]
pub unsafe extern fn ethkey_keypair_address(keypair: *mut KeyPair) -> *mut String {
let address = format!("{:?}", (*keypair).address());
Box::into_raw(Box::new(address))
}
#[no_mangle]
pub unsafe extern fn ethkey_keypair_sign(keypair: *mut KeyPair, message: *mut StringPtr) -> *mut String {
let secret = (*keypair).secret();
let message: Message = (*message).as_str().parse().unwrap();
let signature = format!("{}", sign(secret, &message).unwrap());
Box::into_raw(Box::new(signature))
}
fn safe_rlp_item(rlp: &str, position: u32) -> Result<String, String> {
let hex = rlp.from_hex().map_err(| e | e.to_string())?;
let rlp = UntrustedRlp::new(&hex);
let item = rlp.at(position as usize).map_err(| e | e.to_string())?;
let data = item.data().map_err(| e | e.to_string())?;
Ok(data.to_hex())
}
#[no_mangle]
pub unsafe extern fn rlp_item(rlp: *mut StringPtr, position: u32, error: *mut u32) -> *mut String {
match safe_rlp_item((*rlp).as_str(), position) {
Ok(result) => Box::into_raw(Box::new(result)),
Err(_err) => {
*error = 1;
let s: String = "".into();
Box::into_raw(Box::new(s))
}
}
}
#[no_mangle]
pub unsafe extern fn keccak256(data: *mut StringPtr) -> *mut String {
let data = (*data).as_str();
let hex = data.from_hex().unwrap();
let mut res: [u8; 32] = [0; 32];
let mut keccak = Keccak::new_keccak256();
keccak.update(&hex);
keccak.finalize(&mut res);
Box::into_raw(Box::new(res.to_hex()))
}
#[no_mangle]
pub unsafe extern fn eth_sign(data: *mut StringPtr) -> *mut String {
let data = (*data).as_str();
let hex = data.from_hex().unwrap();
let message = format!("\x19Ethereum Signed Message:\n{}", hex.len()).into_bytes();
let mut res: [u8; 32] = [0; 32];
let mut keccak = Keccak::new_keccak256();
keccak.update(&message);
keccak.update(&hex);
keccak.finalize(&mut res);
Box::into_raw(Box::new(res.to_hex()))
}
// blockies ffi
#[no_mangle]
pub unsafe extern fn blockies_icon(blockies_seed: *mut StringPtr) -> *mut String {
let blockies_seed = (*blockies_seed).as_str();
let icon = blockies_icon_in_base64(blockies_seed.into());
Box::into_raw(Box::new(icon))
}
// random phrase ffi
#[no_mangle]
pub unsafe extern fn random_phrase(words: u32) -> *mut String {
let words = wordlist::random_phrase(words as usize);
Box::into_raw(Box::new(words))
}
// data encryption ffi
#[no_mangle]
pub unsafe extern fn encrypt_data(data: *mut StringPtr, password: *mut StringPtr) -> *mut String {
let data = (*data).as_str();
let password = (*password).as_str();
let crypto = Crypto::with_plain(data.as_bytes(), password, 10240);
Box::into_raw(Box::new(crypto.into()))
}
#[no_mangle]
pub unsafe extern fn decrypt_data(encrypted_data: *mut StringPtr, password: *mut StringPtr, error: *mut u32) -> *mut String {
let data = (*encrypted_data).as_str();
let password = (*password).as_str();
let crypto: Crypto = match data.parse() {
Ok(crypto) => crypto,
Err(_) => {
*error = 1;
return Box::into_raw(Box::new(String::new()))
}
};
match crypto.decrypt(password) {
Ok(decrypted) => {
Box::into_raw(Box::new(String::from_utf8_unchecked(decrypted)))
},
Err(_) => {
*error = 2;
Box::into_raw(Box::new(String::new()))
},
}
}
#[cfg(feature = "jni")]
#[allow(non_snake_case)]
pub mod android {
extern crate jni;
use wordlist;
use super::*;
use self::jni::JNIEnv;
use self::jni::objects::{JClass, JString, JThrowable};
use self::jni::sys::{jint, jstring};
fn new_exception<'a>(env: &'a JNIEnv<'a>) -> JThrowable<'a> {
let exception = env.find_class("java/lang/Exception").unwrap();
// javap -s java.lang.Exception
env.new_object(exception, "()V", &[]).unwrap().into()
}
#[no_mangle]
pub unsafe extern fn Java_com_nativesigner_EthkeyBridge_ethkeyBrainwalletAddress(env: JNIEnv, _: JClass, seed: JString) -> jstring {
let seed: String = env.get_string(seed).expect("Invalid seed").into();
let keypair = Brain::new(seed).generate().unwrap();
let java_address = env.new_string(format!("{:?}", keypair.address())).expect("Could not create java string");
java_address.into_inner()
}
#[no_mangle]
pub unsafe extern fn Java_com_nativesigner_EthkeyBridge_ethkeyBrainwalletSecret(env: JNIEnv, _: JClass, seed: JString) -> jstring {
let seed: String = env.get_string(seed).expect("Invalid seed").into();
let keypair = Brain::new(seed).generate().unwrap();
let java_secret = env.new_string(format!("{:?}", keypair.secret())).expect("Could not create java string");
java_secret.into_inner()
}
#[no_mangle]
pub unsafe extern fn Java_com_nativesigner_EthkeyBridge_ethkeyBrainwalletSign(env: JNIEnv, _: JClass, seed: JString, message: JString) -> jstring {
let seed: String = env.get_string(seed).expect("Invalid seed").into();
let message: String = env.get_string(message).expect("Invalid message").into();
let keypair = Brain::new(seed).generate().unwrap();
let message: Message = message.parse().unwrap();
let signature = sign(keypair.secret(), &message).unwrap();
let java_signature = env.new_string(format!("{}", signature)).expect("Could not create java string");
java_signature.into_inner()
}
#[no_mangle]
pub unsafe extern fn Java_com_nativesigner_EthkeyBridge_ethkeyRlpItem(env