commit
595cd87b90
12
Cargo.toml
12
Cargo.toml
|
@ -10,19 +10,19 @@ repository = "https://github.com/ZcashFoundation/libbolt"
|
|||
license = "MIT License"
|
||||
|
||||
[dependencies]
|
||||
rand = "0.6"
|
||||
rand_core = "0.4.0"
|
||||
ff = { git = "https://github.com/boltlabs-inc/ff", branch = "master" }
|
||||
pairing = { git = "https://github.com/boltlabs-inc/pairing", branch = "master", features = ["serde"] }
|
||||
rand = "0.7"
|
||||
ff_bl = { git = "https://github.com/boltlabs-inc/ff", branch = "master" }
|
||||
pairing_bl = { git = "https://github.com/boltlabs-inc/pairing", branch = "master", features = ["serde"] }
|
||||
libc = "*"
|
||||
serde = { version = "1.0", features = ["derive"] }
|
||||
serde_json = "1.0"
|
||||
serde_with = "1.0"
|
||||
serde_bytes = "0.11.2"
|
||||
time = "*"
|
||||
secp256k1 = { version = "0.15.0", features = ["rand", "serde"] }
|
||||
secp256k1 = { version = "0.16.0", features = ["serde"] }
|
||||
sha2 = { version = "0.8", default-features = false }
|
||||
hex = "0.3.2"
|
||||
|
||||
[lib]
|
||||
crate-type = ["lib", "cdylib"]
|
||||
crate-type = ["lib", "cdylib", "staticlib"]
|
||||
|
||||
|
|
10
Makefile
10
Makefile
|
@ -4,23 +4,25 @@ all:
|
|||
export RUSTFLAGS=-Awarnings
|
||||
cargo +nightly build
|
||||
cargo +nightly test
|
||||
cargo +nightly run --example bolt_test
|
||||
cargo +nightly run --example bolt_test_bls12
|
||||
cargo +nightly run --example bolt_test_bn256
|
||||
|
||||
debug:
|
||||
export RUST_BACKTRACE=1
|
||||
cargo +nightly build
|
||||
cargo +nightly run --example bolt_test
|
||||
cargo +nightly run --example bolt_test_bls12
|
||||
|
||||
release:
|
||||
cargo +nightly build --release
|
||||
cargo +nightly run --release --example bolt_test
|
||||
cargo +nightly run --release --example bolt_test_bls12
|
||||
cargo +nightly run --release --example bolt_test_bn256
|
||||
|
||||
bench:
|
||||
cargo +nightly bench
|
||||
|
||||
test:
|
||||
# runs the unit test suite
|
||||
cargo +nightly test --release #-- --nocapture
|
||||
cargo +nightly test --release -- --nocapture
|
||||
|
||||
update:
|
||||
cargo +nightly update
|
||||
|
|
|
@ -40,9 +40,7 @@ We will switch to the stable release channel once libbolt (and dependencies) are
|
|||
|
||||
# Build & Install
|
||||
|
||||
Please ensure you have installed the libsodium library for your platform. See install instructions [here](https://download.libsodium.org/doc/installation/index.html).
|
||||
|
||||
To build the library and execute basic examples, run `make`
|
||||
To build the library in debug, execute tests and basic examples, run `make`
|
||||
|
||||
# Tests
|
||||
|
||||
|
|
|
@ -1,14 +1,13 @@
|
|||
extern crate rand;
|
||||
extern crate rand_core;
|
||||
extern crate bolt;
|
||||
extern crate ff;
|
||||
extern crate pairing;
|
||||
extern crate ff_bl as ff;
|
||||
extern crate pairing_bl as pairing;
|
||||
extern crate time;
|
||||
extern crate secp256k1;
|
||||
|
||||
use bolt::bidirectional;
|
||||
use std::time::Instant;
|
||||
use pairing::bls12_381::{Bls12};
|
||||
use pairing::bls12_381::Bls12;
|
||||
use bolt::handle_bolt_result;
|
||||
|
||||
macro_rules! measure_one_arg {
|
|
@ -0,0 +1,121 @@
|
|||
extern crate rand;
|
||||
extern crate bolt;
|
||||
extern crate ff_bl as ff;
|
||||
extern crate pairing_bl as pairing;
|
||||
extern crate time;
|
||||
extern crate secp256k1;
|
||||
|
||||
use bolt::bidirectional;
|
||||
use std::time::Instant;
|
||||
use pairing::bn256::Bn256;
|
||||
use bolt::handle_bolt_result;
|
||||
|
||||
macro_rules! measure_one_arg {
|
||||
($x: expr) => {
|
||||
{
|
||||
let s = Instant::now();
|
||||
let res = $x;
|
||||
let e = s.elapsed();
|
||||
(res, e.as_millis())
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! measure_two_arg {
|
||||
($x: expr) => {
|
||||
{
|
||||
let s = Instant::now();
|
||||
let (res1, res2) = $x;
|
||||
let e = s.elapsed();
|
||||
(res1, res2, e.as_millis())
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//macro_rules! measure_ret_mut {
|
||||
// ($x: expr) => {
|
||||
// {
|
||||
// let s = Instant::now();
|
||||
// let mut handle = $x;
|
||||
// let e = s.elapsed();
|
||||
// (handle, s.as_millis())
|
||||
// };
|
||||
// }
|
||||
//}
|
||||
|
||||
fn main() {
|
||||
println!("******************************************");
|
||||
let mut channel_state = bidirectional::ChannelState::<Bn256>::new(String::from("Channel A -> B"), false);
|
||||
let rng = &mut rand::thread_rng();
|
||||
|
||||
let b0_customer = 150;
|
||||
let b0_merchant = 10;
|
||||
let pay_inc = 20;
|
||||
let pay_inc2 = 10;
|
||||
|
||||
let (mut channel_token, mut merch_state, mut channel_state) = bidirectional::init_merchant(rng, &mut channel_state, "Merchant Bob");
|
||||
|
||||
let mut cust_state = bidirectional::init_customer(rng, &mut channel_token, b0_customer, b0_merchant, "Alice");
|
||||
|
||||
println!("{}", cust_state);
|
||||
|
||||
// lets establish the channel
|
||||
let (com, com_proof, est_time) = measure_two_arg!(bidirectional::establish_customer_generate_proof(rng, &mut channel_token, &mut cust_state));
|
||||
println!(">> Time to generate proof for establish: {} ms", est_time);
|
||||
|
||||
// obtain close token for closing out channel
|
||||
let channel_id = channel_token.compute_channel_id();
|
||||
let option = bidirectional::establish_merchant_issue_close_token(rng, &channel_state, &com, &com_proof,
|
||||
&channel_id, b0_customer, b0_merchant, &merch_state);
|
||||
let close_token= match option {
|
||||
Ok(n) => n.unwrap(),
|
||||
Err(e) => panic!("Failed - bidirectional::establish_merchant_issue_close_token(): {}", e)
|
||||
};
|
||||
|
||||
assert!(cust_state.verify_close_token(&channel_state, &close_token));
|
||||
|
||||
// wait for funding tx to be confirmed, etc
|
||||
|
||||
// obtain payment token for pay protocol
|
||||
let pay_token = bidirectional::establish_merchant_issue_pay_token(rng, &channel_state, &com, &merch_state);
|
||||
//assert!(cust_state.verify_pay_token(&channel_state, &pay_token));
|
||||
|
||||
assert!(bidirectional::establish_customer_final(&mut channel_state, &mut cust_state, &pay_token));
|
||||
println!("Channel established!");
|
||||
|
||||
let (payment, new_cust_state, pay_time) = measure_two_arg!(bidirectional::generate_payment_proof(rng, &channel_state, &cust_state, pay_inc));
|
||||
println!(">> Time to generate payment proof: {} ms", pay_time);
|
||||
|
||||
let (new_close_token, verify_time) = measure_one_arg!(bidirectional::verify_payment_proof(rng, &channel_state, &payment, &mut merch_state));
|
||||
println!(">> Time to verify payment proof: {} ms", verify_time);
|
||||
|
||||
let revoke_token = bidirectional::generate_revoke_token(&channel_state, &mut cust_state, new_cust_state, &new_close_token);
|
||||
|
||||
// send revoke token and get pay-token in response
|
||||
let new_pay_token_result = bidirectional::verify_revoke_token(&revoke_token, &mut merch_state);
|
||||
let new_pay_token = handle_bolt_result!(new_pay_token_result);
|
||||
|
||||
// verify the pay token and update internal state
|
||||
assert!(cust_state.verify_pay_token(&channel_state, &new_pay_token.unwrap()));
|
||||
|
||||
println!("******************************************");
|
||||
|
||||
let (payment2, new_cust_state2, pay_time2) = measure_two_arg!(bidirectional::generate_payment_proof(rng, &channel_state, &cust_state, pay_inc2));
|
||||
println!(">> Time to generate payment proof 2: {} ms", pay_time2);
|
||||
|
||||
let (new_close_token2, verify_time2) = measure_one_arg!(bidirectional::verify_payment_proof(rng, &channel_state, &payment2, &mut merch_state));
|
||||
println!(">> Time to verify payment proof 2: {} ms", verify_time2);
|
||||
|
||||
let revoke_token2 = bidirectional::generate_revoke_token(&channel_state, &mut cust_state, new_cust_state2, &new_close_token2);
|
||||
|
||||
// send revoke token and get pay-token in response
|
||||
let new_pay_token_result2 = bidirectional::verify_revoke_token(&revoke_token2, &mut merch_state);
|
||||
let new_pay_token2 = handle_bolt_result!(new_pay_token_result2);
|
||||
|
||||
// verify the pay token and update internal state
|
||||
assert!(cust_state.verify_pay_token(&channel_state, &new_pay_token2.unwrap()));
|
||||
|
||||
println!("Final Cust state: {}", cust_state);
|
||||
|
||||
}
|
|
@ -7,6 +7,7 @@ import "C"
|
|||
import (
|
||||
"encoding/json"
|
||||
"strings"
|
||||
"fmt"
|
||||
)
|
||||
|
||||
type setupResp struct {
|
||||
|
@ -232,7 +233,7 @@ type ZkChannelParams struct {
|
|||
}
|
||||
|
||||
func BidirectionalChannelSetup(name string, channelSupport bool) (ChannelState, error) {
|
||||
resp := C.GoString(C.ffishim_bidirectional_channel_setup(C.CString(name), C.uint(btoi(channelSupport))))
|
||||
resp := C.GoString(C.ffishim_bls12_channel_setup(C.CString(name), C.uint(btoi(channelSupport))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return ChannelState{}, err
|
||||
|
@ -247,7 +248,7 @@ func BidirectionalInitMerchant(channelState ChannelState, nameMerchant string) (
|
|||
if err != nil {
|
||||
return ChannelToken{}, MerchState{}, ChannelState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_init_merchant(C.CString(string(serChannelState)), C.CString(nameMerchant)))
|
||||
resp := C.GoString(C.ffishim_bls12_init_merchant(C.CString(string(serChannelState)), C.CString(nameMerchant)))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return ChannelToken{}, MerchState{}, ChannelState{}, err
|
||||
|
@ -271,7 +272,7 @@ func BidirectionalInitCustomer(channelToken ChannelToken, balanceCustomer int, b
|
|||
if err != nil {
|
||||
return ChannelToken{}, CustState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_init_customer(C.CString(string(serChannelToken)), C.longlong(balanceCustomer), C.longlong(balanceMerchant), C.CString(nameCustomer)))
|
||||
resp := C.GoString(C.ffishim_bls12_init_customer(C.CString(string(serChannelToken)), C.longlong(balanceCustomer), C.longlong(balanceMerchant), C.CString(nameCustomer)))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return ChannelToken{}, CustState{}, err
|
||||
|
@ -294,7 +295,7 @@ func BidirectionalEstablishCustomerGenerateProof(channelToken ChannelToken, cust
|
|||
if err != nil {
|
||||
return ChannelToken{}, CustState{}, Commitment{}, CommitmentProof{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_establish_customer_generate_proof(C.CString(string(serChannelToken)), C.CString(string(serCustState))))
|
||||
resp := C.GoString(C.ffishim_bls12_establish_customer_generate_proof(C.CString(string(serChannelToken)), C.CString(string(serCustState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return ChannelToken{}, CustState{}, Commitment{}, CommitmentProof{}, err
|
||||
|
@ -317,6 +318,24 @@ func BidirectionalEstablishCustomerGenerateProof(channelToken ChannelToken, cust
|
|||
return channelToken, custState, com, comProof, err
|
||||
}
|
||||
|
||||
|
||||
|
||||
func BidirectionalGenerateChannelID(channelToken ChannelToken) (error) {
|
||||
serChannelToken, err := json.Marshal(channelToken)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bls12_generate_channel_id(C.CString(string(serChannelToken))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
fmt.Println("channel id: ", r)
|
||||
return err
|
||||
}
|
||||
|
||||
|
||||
|
||||
func BidirectionalEstablishMerchantIssueCloseToken(channelState ChannelState, com Commitment, comProof CommitmentProof, channelId []string, initCustBal int, initMerchBal int, merchState MerchState) (Signature, error) {
|
||||
serChannelState, err := json.Marshal(channelState)
|
||||
if err != nil {
|
||||
|
@ -338,7 +357,7 @@ func BidirectionalEstablishMerchantIssueCloseToken(channelState ChannelState, co
|
|||
if err != nil {
|
||||
return Signature{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_establish_merchant_issue_close_token(C.CString(string(serChannelState)), C.CString(string(serCom)), C.CString(string(serComProof)), C.CString(string(serChannelId)), C.longlong(initCustBal), C.longlong(initMerchBal), C.CString(string(serMerchState))))
|
||||
resp := C.GoString(C.ffishim_bls12_establish_merchant_issue_close_token(C.CString(string(serChannelState)), C.CString(string(serCom)), C.CString(string(serComProof)), C.CString(string(serChannelId)), C.longlong(initCustBal), C.longlong(initMerchBal), C.CString(string(serMerchState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return Signature{}, err
|
||||
|
@ -361,7 +380,7 @@ func BidirectionalEstablishMerchantIssuePayToken(channelState ChannelState, com
|
|||
if err != nil {
|
||||
return Signature{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_establish_merchant_issue_pay_token(C.CString(string(serChannelState)), C.CString(string(serCom)), C.CString(string(serMerchState))))
|
||||
resp := C.GoString(C.ffishim_bls12_establish_merchant_issue_pay_token(C.CString(string(serChannelState)), C.CString(string(serCom)), C.CString(string(serMerchState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return Signature{}, err
|
||||
|
@ -384,7 +403,7 @@ func BidirectionalVerifyCloseToken(channelState ChannelState, custState CustStat
|
|||
if err != nil {
|
||||
return false, ChannelState{}, CustState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_verify_close_token(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.CString(string(serCloseToken))))
|
||||
resp := C.GoString(C.ffishim_bls12_verify_close_token(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.CString(string(serCloseToken))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return false, ChannelState{}, CustState{}, err
|
||||
|
@ -410,7 +429,7 @@ func BidirectionalEstablishCustomerFinal(channelState ChannelState, custState Cu
|
|||
if err != nil {
|
||||
return false, ChannelState{}, CustState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_establish_customer_final(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.CString(string(serPayToken))))
|
||||
resp := C.GoString(C.ffishim_bls12_establish_customer_final(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.CString(string(serPayToken))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return false, ChannelState{}, CustState{}, err
|
||||
|
@ -432,7 +451,7 @@ func BidirectionalPayGeneratePaymentProof(channelState ChannelState, custState C
|
|||
if err != nil {
|
||||
return Payment{}, CustState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_pay_generate_payment_proof(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.longlong(amount)))
|
||||
resp := C.GoString(C.ffishim_bls12_pay_generate_payment_proof(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.longlong(amount)))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return Payment{}, CustState{}, err
|
||||
|
@ -459,7 +478,7 @@ func BidirectionalPayVerifyPaymentProof(channelState ChannelState, payProof Paym
|
|||
if err != nil {
|
||||
return Signature{}, MerchState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_pay_verify_payment_proof(C.CString(string(serChannelState)), C.CString(string(serPayProof)), C.CString(string(serMerchState))))
|
||||
resp := C.GoString(C.ffishim_bls12_pay_verify_payment_proof(C.CString(string(serChannelState)), C.CString(string(serPayProof)), C.CString(string(serMerchState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return Signature{}, MerchState{}, err
|
||||
|
@ -490,7 +509,7 @@ func BidirectionalPayVerifyMultiplePaymentProofs(channelState ChannelState, send
|
|||
if err != nil {
|
||||
return Signature{}, Signature{}, MerchState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_pay_verify_multiple_payment_proofs(C.CString(string(serChannelState)), C.CString(string(serSenderPayProof)), C.CString(string(serReceiverPayProof)), C.CString(string(serMerchState))))
|
||||
resp := C.GoString(C.ffishim_bls12_pay_verify_multiple_payment_proofs(C.CString(string(serChannelState)), C.CString(string(serSenderPayProof)), C.CString(string(serReceiverPayProof)), C.CString(string(serMerchState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return Signature{}, Signature{}, MerchState{}, err
|
||||
|
@ -526,7 +545,7 @@ func BidirectionalPayGenerateRevokeToken(channelState ChannelState, custState Cu
|
|||
if err != nil {
|
||||
return RevokeToken{}, CustState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_pay_generate_revoke_token(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.CString(string(serNewCustState)), C.CString(string(serCloseToken))))
|
||||
resp := C.GoString(C.ffishim_bls12_pay_generate_revoke_token(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.CString(string(serNewCustState)), C.CString(string(serCloseToken))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return RevokeToken{}, CustState{}, err
|
||||
|
@ -549,7 +568,7 @@ func BidirectionalPayVerifyRevokeToken(revokeToken RevokeToken, merchState Merch
|
|||
if err != nil {
|
||||
return Signature{}, MerchState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_pay_verify_revoke_token(C.CString(string(serRevokeToken)), C.CString(string(serMerchState))))
|
||||
resp := C.GoString(C.ffishim_bls12_pay_verify_revoke_token(C.CString(string(serRevokeToken)), C.CString(string(serMerchState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return Signature{}, MerchState{}, err
|
||||
|
@ -576,7 +595,7 @@ func BidirectionalPayVerifyMultipleRevokeTokens(senderRevokeToken RevokeToken, r
|
|||
if err != nil {
|
||||
return Signature{}, Signature{}, MerchState{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_pay_verify_multiple_revoke_tokens(C.CString(string(serSenderRevokeToken)), C.CString(string(serReceiverRevokeToken)), C.CString(string(serMerchState))))
|
||||
resp := C.GoString(C.ffishim_bls12_pay_verify_multiple_revoke_tokens(C.CString(string(serSenderRevokeToken)), C.CString(string(serReceiverRevokeToken)), C.CString(string(serMerchState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return Signature{}, Signature{}, MerchState{}, err
|
||||
|
@ -608,7 +627,7 @@ func BidirectionalPayVerifyPaymentToken(channelState ChannelState, custState Cus
|
|||
if err != nil {
|
||||
return CustState{}, false, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_pay_verify_payment_token(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.CString(string(serPayToken))))
|
||||
resp := C.GoString(C.ffishim_bls12_pay_verify_payment_token(C.CString(string(serChannelState)), C.CString(string(serCustState)), C.CString(string(serPayToken))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return CustState{}, false, err
|
||||
|
@ -626,7 +645,7 @@ func BidirectionalCustomerClose(channelState ChannelState, custState CustState)
|
|||
if err != nil {
|
||||
return CustClose{}, err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_customer_close(C.CString(string(serChannelState)), C.CString(string(serCustState))))
|
||||
resp := C.GoString(C.ffishim_bls12_customer_close(C.CString(string(serChannelState)), C.CString(string(serCustState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return CustClose{}, err
|
||||
|
@ -653,7 +672,7 @@ func BidirectionalMerchantClose(channelState ChannelState, channelToken ChannelT
|
|||
if err != nil {
|
||||
return "", "", "", err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_merchant_close(C.CString(string(serChannelState)), C.CString(string(serChannelToken)), C.CString(serAddress), C.CString(string(serCustClose)), C.CString(string(serMerchState))))
|
||||
resp := C.GoString(C.ffishim_bls12_merchant_close(C.CString(string(serChannelState)), C.CString(string(serChannelToken)), C.CString(serAddress), C.CString(string(serCustClose)), C.CString(string(serMerchState))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return "", "", "", err
|
||||
|
@ -666,7 +685,7 @@ func BidirectionalWtpVerifyCustCloseMessage(channelToken ChannelToken, serWpk st
|
|||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_wtp_verify_cust_close_message(C.CString(string(serChannelToken)), C.CString(serWpk), C.CString(serCloseMsg), C.CString(string(serCloseToken))))
|
||||
resp := C.GoString(C.ffishim_bls12_wtp_verify_cust_close_message(C.CString(string(serChannelToken)), C.CString(serWpk), C.CString(serCloseMsg), C.CString(string(serCloseToken))))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return "", err
|
||||
|
@ -679,7 +698,7 @@ func BidirectionalWtpVerifyMerchCloseMessage(channelToken ChannelToken, serWpk s
|
|||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
resp := C.GoString(C.ffishim_bidirectional_wtp_verify_merch_close_message(C.CString(string(serChannelToken)), C.CString(serWpk), C.CString(serMerchClose)))
|
||||
resp := C.GoString(C.ffishim_bls12_wtp_verify_merch_close_message(C.CString(string(serChannelToken)), C.CString(serWpk), C.CString(serMerchClose)))
|
||||
r, err := processCResponse(resp)
|
||||
if err != nil {
|
||||
return "", err
|
||||
|
|
|
@ -16,35 +16,36 @@ extern "C" {
|
|||
#endif
|
||||
|
||||
// channel init
|
||||
char* ffishim_bidirectional_channel_setup(const char *channel_name, unsigned int third_party_support);
|
||||
char* ffishim_bidirectional_init_merchant(const char *ser_channel_state, const char *name_ptr);
|
||||
char* ffishim_bidirectional_init_customer(const char *ser_channel_token, long long int balance_customer, long long int balance_merchant, const char *name_ptr);
|
||||
char* ffishim_bls12_channel_setup(const char *channel_name, unsigned int third_party_support);
|
||||
char* ffishim_bls12_init_merchant(const char *ser_channel_state, const char *name_ptr);
|
||||
char* ffishim_bls12_init_customer(const char *ser_channel_token, long long int balance_customer, long long int balance_merchant, const char *name_ptr);
|
||||
|
||||
// channel establish protocol routines
|
||||
char* ffishim_bidirectional_establish_customer_generate_proof(const char *ser_channel_token, const char *ser_customer_wallet);
|
||||
char* ffishim_bidirectional_establish_merchant_issue_close_token(const char *ser_channel_state, const char *ser_com, const char *ser_com_proof, const char *ser_pk_c, long long int init_cust_bal, long long int init_merch_bal, const char *ser_merch_state);
|
||||
char* ffishim_bidirectional_establish_merchant_issue_pay_token(const char *ser_channel_state, const char *ser_com, const char *ser_merch_state);
|
||||
char* ffishim_bidirectional_verify_close_token(const char *ser_channel_state, const char *ser_customer_wallet, const char *ser_close_token);
|
||||
char* ffishim_bidirectional_establish_customer_final(const char *ser_channel_state, const char *ser_customer_wallet, const char *ser_pay_token);
|
||||
char* ffishim_bls12_establish_customer_generate_proof(const char *ser_channel_token, const char *ser_customer_wallet);
|
||||
char* ffishim_bls12_generate_channel_id(const char *ser_channel_token);
|
||||
char* ffishim_bls12_establish_merchant_issue_close_token(const char *ser_channel_state, const char *ser_com, const char *ser_com_proof, const char *ser_pk_c, long long int init_cust_bal, long long int init_merch_bal, const char *ser_merch_state);
|
||||
char* ffishim_bls12_establish_merchant_issue_pay_token(const char *ser_channel_state, const char *ser_com, const char *ser_merch_state);
|
||||
char* ffishim_bls12_verify_close_token(const char *ser_channel_state, const char *ser_customer_wallet, const char *ser_close_token);
|
||||
char* ffishim_bls12_establish_customer_final(const char *ser_channel_state, const char *ser_customer_wallet, const char *ser_pay_token);
|
||||
|
||||
// channel pay protocol routines
|
||||
char* ffishim_bidirectional_pay_generate_payment_proof(const char *ser_channel_state, const char *ser_customer_wallet, long long int amount);
|
||||
char* ffishim_bidirectional_pay_verify_payment_proof(const char *ser_channel_state, const char *ser_pay_proof, const char *ser_merch_state);
|
||||
char* ffishim_bidirectional_pay_verify_multiple_payment_proofs(const char *ser_channel_state, const char *ser_sender_pay_proof, const char *ser_receiver_pay_proof, const char *ser_merch_state);
|
||||
char* ffishim_bidirectional_pay_generate_revoke_token(const char *ser_channel_state, const char *ser_cust_state, const char *ser_new_cust_state, const char *ser_close_token);
|
||||
char* ffishim_bidirectional_pay_verify_revoke_token(const char *ser_revoke_token, const char *ser_merch_state);
|
||||
char* ffishim_bidirectional_pay_verify_multiple_revoke_tokens(const char *ser_sender_revoke_token, const char *ser_receiver_revoke_token, const char *ser_merch_state);
|
||||
char* ffishim_bidirectional_pay_verify_payment_token(const char *ser_channel_state, const char *ser_cust_state, const char *ser_pay_token);
|
||||
char* ffishim_bls12_pay_generate_payment_proof(const char *ser_channel_state, const char *ser_customer_wallet, long long int amount);
|
||||
char* ffishim_bls12_pay_verify_payment_proof(const char *ser_channel_state, const char *ser_pay_proof, const char *ser_merch_state);
|
||||
char* ffishim_bls12_pay_verify_multiple_payment_proofs(const char *ser_channel_state, const char *ser_sender_pay_proof, const char *ser_receiver_pay_proof, const char *ser_merch_state);
|
||||
char* ffishim_bls12_pay_generate_revoke_token(const char *ser_channel_state, const char *ser_cust_state, const char *ser_new_cust_state, const char *ser_close_token);
|
||||
char* ffishim_bls12_pay_verify_revoke_token(const char *ser_revoke_token, const char *ser_merch_state);
|
||||
char* ffishim_bls12_pay_verify_multiple_revoke_tokens(const char *ser_sender_revoke_token, const char *ser_receiver_revoke_token, const char *ser_merch_state);
|
||||
char* ffishim_bls12_pay_verify_payment_token(const char *ser_channel_state, const char *ser_cust_state, const char *ser_pay_token);
|
||||
|
||||
// closing routines for both sides
|
||||
char* ffishim_bidirectional_customer_close(const char *ser_channel_state, const char *ser_cust_state);
|
||||
char* ffishim_bidirectional_merchant_close(const char *ser_channel_state, const char *ser_channel_token, const char *ser_address, const char *ser_cust_close, const char *ser_merch_state);
|
||||
char* ffishim_bls12_customer_close(const char *ser_channel_state, const char *ser_cust_state);
|
||||
char* ffishim_bls12_merchant_close(const char *ser_channel_state, const char *ser_channel_token, const char *ser_address, const char *ser_cust_close, const char *ser_merch_state);
|
||||
|
||||
// WTP logic for on-chain validation of closing messages
|
||||
char* ffishim_bidirectional_wtp_verify_cust_close_message(const char *ser_channel_token, const char *ser_wpk, const char *ser_close_msg, const char *ser_close_token);
|
||||
char* ffishim_bidirectional_wtp_verify_merch_close_message(const char *ser_channel_token, const char *ser_wpk, const char *ser_merch_close);
|
||||
char* ffishim_bls12_wtp_verify_cust_close_message(const char *ser_channel_token, const char *ser_wpk, const char *ser_close_msg, const char *ser_close_token);
|
||||
char* ffishim_bls12_wtp_verify_merch_close_message(const char *ser_channel_token, const char *ser_wpk, const char *ser_merch_close);
|
||||
|
||||
char* ffishim_bidirectional_wtp_check_wpk(const char *wpk);
|
||||
char* ffishim_bls12_wtp_check_wpk(const char *wpk);
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
||||
|
@ -64,7 +65,7 @@ char* ffishim_bidirectional_wtp_check_wpk(const char *wpk);
|
|||
|
||||
int wtp_check_wpk(const char *wpk)
|
||||
{
|
||||
const char *ret = ffishim_bidirectional_wtp_check_wpk(wpk);
|
||||
const char *ret = ffishim_bls12_wtp_check_wpk(wpk);
|
||||
printf("RESULT: %s\n", ret);
|
||||
return 0;
|
||||
}
|
||||
|
@ -78,7 +79,7 @@ char* ffishim_bidirectional_wtp_check_wpk(const char *wpk);
|
|||
int wtp_verify_cust_close_message(const char *channel_token, const char *wpk, const char *cust_close, const char *close_token)
|
||||
{
|
||||
// Call rust
|
||||
const char *return_json = ffishim_bidirectional_wtp_verify_cust_close_message(channel_token, wpk, cust_close, close_token);
|
||||
const char *return_json = ffishim_bls12_wtp_verify_cust_close_message(channel_token, wpk, cust_close, close_token);
|
||||
|
||||
Document d;
|
||||
d.Parse(return_json);
|
||||
|
@ -102,7 +103,7 @@ char* ffishim_bidirectional_wtp_check_wpk(const char *wpk);
|
|||
int wtp_verify_merch_close_message(const char *channel_token, const char *wpk, const char *merch_close)
|
||||
{
|
||||
// Call into Rust
|
||||
const char* return_json = string_replace_all(ffishim_bidirectional_wtp_verify_merch_close_message(channel_token, wpk, merch_close), '\'', '\"');
|
||||
const char* return_json = string_replace_all(ffishim_bls12_wtp_verify_merch_close_message(channel_token, wpk, merch_close), '\'', '\"');
|
||||
|
||||
Document d;
|
||||
d.Parse(return_json);
|
||||
|
|
153
py/libbolt.py
153
py/libbolt.py
|
@ -15,115 +15,123 @@ class Libbolt(object):
|
|||
self.load_library_params()
|
||||
|
||||
def load_library_params(self):
|
||||
self.lib.ffishim_bidirectional_channel_setup.argtypes = (c_void_p, c_uint8)
|
||||
self.lib.ffishim_bidirectional_channel_setup.restype = c_void_p
|
||||
self.lib.ffishim_bls12_channel_setup.argtypes = (c_void_p, c_uint8)
|
||||
self.lib.ffishim_bls12_channel_setup.restype = c_void_p
|
||||
|
||||
# ESTABLISH PROTOCOL
|
||||
|
||||
self.lib.ffishim_bidirectional_init_merchant.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_init_merchant.restype = c_void_p
|
||||
self.lib.ffishim_bls12_init_merchant.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_init_merchant.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_init_customer.argtypes = (c_void_p, ctypes.c_int32, ctypes.c_int32, c_void_p)
|
||||
self.lib.ffishim_bidirectional_init_customer.restype = c_void_p
|
||||
self.lib.ffishim_bls12_init_customer.argtypes = (c_void_p, ctypes.c_int32, ctypes.c_int32, c_void_p)
|
||||
self.lib.ffishim_bls12_init_customer.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_establish_customer_generate_proof.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_establish_customer_generate_proof.restype = c_void_p
|
||||
self.lib.ffishim_bls12_establish_customer_generate_proof.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_establish_customer_generate_proof.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_establish_merchant_issue_close_token.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_establish_merchant_issue_close_token.restype = c_void_p
|
||||
self.lib.ffishim_bls12_generate_channel_id.argtypes = (c_void_p, )
|
||||
self.lib.ffishim_bls12_generate_channel_id.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_establish_merchant_issue_pay_token.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_establish_merchant_issue_pay_token.restype = c_void_p
|
||||
self.lib.ffishim_bls12_establish_merchant_issue_close_token.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_establish_merchant_issue_close_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_verify_close_token.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_verify_close_token.restype = c_void_p
|
||||
self.lib.ffishim_bls12_establish_merchant_issue_pay_token.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_establish_merchant_issue_pay_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_establish_customer_final.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_establish_customer_final.restype = c_void_p
|
||||
self.lib.ffishim_bls12_verify_close_token.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_verify_close_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bls12_establish_customer_final.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_establish_customer_final.restype = c_void_p
|
||||
|
||||
# PAY PROTOCOL
|
||||
|
||||
self.lib.ffishim_bidirectional_pay_generate_payment_proof.argtypes = (c_void_p, c_void_p, ctypes.c_int32)
|
||||
self.lib.ffishim_bidirectional_pay_generate_payment_proof.restype = c_void_p
|
||||
self.lib.ffishim_bls12_pay_generate_payment_proof.argtypes = (c_void_p, c_void_p, ctypes.c_int32)
|
||||
self.lib.ffishim_bls12_pay_generate_payment_proof.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_pay_verify_payment_proof.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_pay_verify_payment_proof.restype = c_void_p
|
||||
self.lib.ffishim_bls12_pay_verify_payment_proof.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_pay_verify_payment_proof.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_pay_verify_multiple_payment_proofs.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_pay_verify_multiple_payment_proofs.restype = c_void_p
|
||||
self.lib.ffishim_bls12_pay_verify_multiple_payment_proofs.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_pay_verify_multiple_payment_proofs.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_pay_generate_revoke_token.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_pay_generate_revoke_token.restype = c_void_p
|
||||
self.lib.ffishim_bls12_pay_generate_revoke_token.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_pay_generate_revoke_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_pay_verify_revoke_token.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_pay_verify_revoke_token.restype = c_void_p
|
||||
self.lib.ffishim_bls12_pay_verify_revoke_token.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_pay_verify_revoke_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_pay_verify_multiple_revoke_tokens.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_pay_verify_multiple_revoke_tokens.restype = c_void_p
|
||||
self.lib.ffishim_bls12_pay_verify_multiple_revoke_tokens.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_pay_verify_multiple_revoke_tokens.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_pay_verify_payment_token.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_pay_verify_payment_token.restype = c_void_p
|
||||
self.lib.ffishim_bls12_pay_verify_payment_token.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_pay_verify_payment_token.restype = c_void_p
|
||||
|
||||
# CLOSE
|
||||
|
||||
self.lib.ffishim_bidirectional_customer_close.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_customer_close.restype = c_void_p
|
||||
self.lib.ffishim_bls12_customer_close.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_customer_close.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_merchant_close.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_merchant_close.restype = c_void_p
|
||||
self.lib.ffishim_bls12_merchant_close.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_merchant_close.restype = c_void_p
|
||||
|
||||
# ON-CHAIN BOLT LOGIC / WTPs
|
||||
|
||||
self.lib.ffishim_bidirectional_wtp_verify_cust_close_message.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_wtp_verify_cust_close_message.restype = c_void_p
|
||||
self.lib.ffishim_bls12_wtp_verify_cust_close_message.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_wtp_verify_cust_close_message.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bidirectional_wtp_verify_merch_close_message.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bidirectional_wtp_verify_merch_close_message.restype = c_void_p
|
||||
self.lib.ffishim_bls12_wtp_verify_merch_close_message.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bls12_wtp_verify_merch_close_message.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_free_string.argtypes = (c_void_p, )
|
||||
|
||||
def channel_setup(self, name, third_party_support=0):
|
||||
output_string = self.lib.ffishim_bidirectional_channel_setup(name.encode(), third_party_support)
|
||||
output_string = self.lib.ffishim_bls12_channel_setup(name.encode(), third_party_support)
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('channel_state')
|
||||
|
||||
# INIT PROTOCOL
|
||||
|
||||
def bidirectional_init_merchant(self, channel_state, name):
|
||||
output_string = self.lib.ffishim_bidirectional_init_merchant(channel_state.encode(), name.encode())
|
||||
output_string = self.lib.ffishim_bls12_init_merchant(channel_state.encode(), name.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('channel_token'), output_dictionary.get('merch_state'), output_dictionary.get('channel_state')
|
||||
|
||||
def bidirectional_init_customer(self, channel_token, b0_cust, b0_merch, name):
|
||||
output_string = self.lib.ffishim_bidirectional_init_customer(channel_token.encode(), b0_cust, b0_merch, name.encode())
|
||||
output_string = self.lib.ffishim_bls12_init_customer(channel_token.encode(), b0_cust, b0_merch, name.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('channel_token'), output_dictionary.get('cust_state'))
|
||||
|
||||
# ESTABLISH PROTOCOL
|
||||
|
||||
def bidirectional_generate_channel_id(self, channel_token):
|
||||
output_string = self.lib.ffishim_bls12_generate_channel_id(channel_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('channel_id')
|
||||
|
||||
def bidirectional_establish_customer_generate_proof(self, channel_token, cust_state):
|
||||
output_string = self.lib.ffishim_bidirectional_establish_customer_generate_proof(channel_token.encode(), cust_state.encode())
|
||||
output_string = self.lib.ffishim_bls12_establish_customer_generate_proof(channel_token.encode(), cust_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('channel_token'), output_dictionary.get('cust_state'), output_dictionary.get('com'), output_dictionary.get('com_proof')
|
||||
|
||||
def bidirectional_establish_merchant_issue_close_token(self, channel_state, com, com_proof, channel_id, init_cust, init_merch, merch_state):
|
||||
output_string = self.lib.ffishim_bidirectional_establish_merchant_issue_close_token(channel_state.encode(), com.encode(), com_proof.encode(), json.dumps(channel_id).encode(), init_cust, init_merch, merch_state.encode())
|
||||
output_string = self.lib.ffishim_bls12_establish_merchant_issue_close_token(channel_state.encode(), com.encode(), com_proof.encode(), json.dumps(channel_id).encode(), init_cust, init_merch, merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('close_token')
|
||||
|
||||
def bidirectional_establish_merchant_issue_pay_token(self, channel_state, com, merch_state):
|
||||
output_string = self.lib.ffishim_bidirectional_establish_merchant_issue_pay_token(channel_state.encode(), com.encode(), merch_state.encode())
|
||||
output_string = self.lib.ffishim_bls12_establish_merchant_issue_pay_token(channel_state.encode(), com.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('pay_token')
|
||||
|
||||
def bidirectional_establish_customer_verify_close_token(self, channel_state, cust_state, close_token):
|
||||
output_string = self.lib.ffishim_bidirectional_verify_close_token(channel_state.encode(), cust_state.encode(), close_token.encode())
|
||||
output_string = self.lib.ffishim_bls12_verify_close_token(channel_state.encode(), cust_state.encode(), close_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
is_token_valid = self._convert_boolean(output_dictionary.get('is_token_valid'))
|
||||
return is_token_valid, output_dictionary.get('channel_state'), output_dictionary.get('cust_state')
|
||||
|
||||
def bidirectional_establish_customer_final(self, channel_state, cust_state, pay_token):
|
||||
output_string = self.lib.ffishim_bidirectional_establish_customer_final(channel_state.encode(), cust_state.encode(), pay_token.encode())
|
||||
output_string = self.lib.ffishim_bls12_establish_customer_final(channel_state.encode(), cust_state.encode(), pay_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
is_established = self._convert_boolean(output_dictionary.get('is_established'))
|
||||
return is_established, output_dictionary.get('channel_state'), output_dictionary.get('cust_state')
|
||||
|
@ -132,44 +140,44 @@ class Libbolt(object):
|
|||
|
||||
# generate payment proof and new cust state
|
||||
def bidirectional_pay_generate_payment_proof(self, channel_state, cust_state, amount):
|
||||
output_string = self.lib.ffishim_bidirectional_pay_generate_payment_proof(channel_state.encode(), cust_state.encode(), amount)
|
||||
output_string = self.lib.ffishim_bls12_pay_generate_payment_proof(channel_state.encode(), cust_state.encode(), amount)
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('payment'), output_dictionary.get('cust_state')
|
||||
|
||||
# verify payment proof
|
||||
def bidirectional_pay_verify_payment_proof(self, channel_state, pay_proof, merch_state):
|
||||
output_string = self.lib.ffishim_bidirectional_pay_verify_payment_proof(channel_state.encode(), pay_proof.encode(), merch_state.encode())
|
||||
output_string = self.lib.ffishim_bls12_pay_verify_payment_proof(channel_state.encode(), pay_proof.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('close_token'), output_dictionary.get('merch_state'))
|
||||
|
||||
# verify multiple payment proof
|
||||
def bidirectional_pay_verify_multiple_payment_proofs(self, channel_state, sender_pay_proof, receiver_pay_proof, merch_state):
|
||||
output_string = self.lib.ffishim_bidirectional_pay_verify_multiple_payment_proofs(channel_state.encode(), sender_pay_proof.encode(), receiver_pay_proof.encode(), merch_state.encode())
|
||||
output_string = self.lib.ffishim_bls12_pay_verify_multiple_payment_proofs(channel_state.encode(), sender_pay_proof.encode(), receiver_pay_proof.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('sender_close_token'), output_dictionary.get('receiver_cond_close_token'), output_dictionary.get('merch_state'))
|
||||
|
||||
# generate revoke token
|
||||
def bidirectional_pay_generate_revoke_token(self, channel_state, cust_state, new_cust_state, close_token):
|
||||
output_string = self.lib.ffishim_bidirectional_pay_generate_revoke_token(channel_state.encode(), cust_state.encode(),
|
||||
output_string = self.lib.ffishim_bls12_pay_generate_revoke_token(channel_state.encode(), cust_state.encode(),
|
||||
new_cust_state.encode(), close_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('revoke_token'), output_dictionary.get('cust_state')
|
||||
|
||||
# verify revoke token
|
||||
def bidirectional_pay_verify_revoke_token(self, revoke_token, merch_state):
|
||||
output_string = self.lib.ffishim_bidirectional_pay_verify_revoke_token(revoke_token.encode(), merch_state.encode())
|
||||
output_string = self.lib.ffishim_bls12_pay_verify_revoke_token(revoke_token.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('pay_token'), output_dictionary.get('merch_state'))
|
||||
|
||||
# verify multiple revoke tokens
|
||||
def bidirectional_pay_verify_multiple_revoke_tokens(self, sender_revoke_token, receiver_revoke_token, merch_state):
|
||||
output_string = self.lib.ffishim_bidirectional_pay_verify_multiple_revoke_tokens(sender_revoke_token.encode(), receiver_revoke_token.encode(), merch_state.encode())
|
||||
output_string = self.lib.ffishim_bls12_pay_verify_multiple_revoke_tokens(sender_revoke_token.encode(), receiver_revoke_token.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('sender_pay_token'), output_dictionary.get('receiver_pay_token'), output_dictionary.get('merch_state'))
|
||||
|
||||
# verify payment token
|
||||
def bidirectional_pay_verify_payment_token(self, channel_state, cust_state, pay_token):
|
||||
output_string = self.lib.ffishim_bidirectional_pay_verify_payment_token(channel_state.encode(), cust_state.encode(), pay_token.encode())
|
||||
output_string = self.lib.ffishim_bls12_pay_verify_payment_token(channel_state.encode(), cust_state.encode(), pay_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
is_pay_valid = self._convert_boolean(output_dictionary.get('is_pay_valid'))
|
||||
return (output_dictionary.get('cust_state'), is_pay_valid)
|
||||
|
@ -177,12 +185,12 @@ class Libbolt(object):
|
|||
# CLOSE
|
||||
|
||||
def bidirectional_customer_close(self, channel_state, cust_state):
|
||||
output_string = self.lib.ffishim_bidirectional_customer_close(channel_state.encode(), cust_state.encode())
|
||||
output_string = self.lib.ffishim_bls12_customer_close(channel_state.encode(), cust_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('cust_close')
|
||||
|
||||
def bidirectional_merchant_close(self, channel_state, channel_token, address, cust_close, merch_state):
|
||||
output_string = self.lib.ffishim_bidirectional_merchant_close(channel_state.encode(), channel_token.encode(),
|
||||
output_string = self.lib.ffishim_bls12_merchant_close(channel_state.encode(), channel_token.encode(),
|
||||
address.encode(), cust_close.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('wpk'), output_dictionary.get('merch_close'), output_dictionary.get('error'))
|
||||
|
@ -198,7 +206,7 @@ class Libbolt(object):
|
|||
return json.dumps(cust_close_dict.get("signature"))
|
||||
|
||||
def wtp_verify_cust_close_message(self, channel_token, wpk, cust_close_wallet, close_token):
|
||||
output_string = self.lib.ffishim_bidirectional_wtp_verify_cust_close_message(channel_token.encode(),
|
||||
output_string = self.lib.ffishim_bls12_wtp_verify_cust_close_message(channel_token.encode(),
|
||||
wpk.encode(),
|
||||
cust_close_wallet.encode(),
|
||||
close_token.encode())
|
||||
|
@ -206,7 +214,7 @@ class Libbolt(object):
|
|||
return output_dictionary.get('result')
|
||||
|
||||
def wtp_verify_merch_close_message(self, channel_token, wpk, merch_close):
|
||||
output_string = self.lib.ffishim_bidirectional_wtp_verify_merch_close_message(channel_token.encode(),
|
||||
output_string = self.lib.ffishim_bls12_wtp_verify_merch_close_message(channel_token.encode(),
|
||||
wpk.encode(),
|
||||
merch_close.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
|
@ -222,6 +230,27 @@ class Libbolt(object):
|
|||
return False
|
||||
return bool_str
|
||||
|
||||
def get_compact_channel_token(self, channel_token_str):
|
||||
ct = self._interperate_json_string_as_dictionary(channel_token_str)
|
||||
|
||||
s = ct["pk_c"]
|
||||
s += ct["pk_m"]
|
||||
s += ct["cl_pk_m"]["X"]
|
||||
s += "".join(ct["cl_pk_m"]["Y"])
|
||||
s += ct["mpk"]["g1"]
|
||||
s += ct["mpk"]["g2"]
|
||||
s += "".join(ct["comParams"]["pub_bases"])
|
||||
return s
|
||||
|
||||
def get_compact_signing_keys(self, cust_state_str):
|
||||
cust_state_str = cust_state_str.replace("null", "None")
|
||||
cust_state = self._interperate_json_string_as_dictionary(cust_state_str)
|
||||
|
||||
name = cust_state.get("name")
|
||||
(pk, sk) = cust_state.get("pk_c"), cust_state.get("sk_c")
|
||||
return name, pk, sk
|
||||
|
||||
|
||||
if platform == 'darwin':
|
||||
prefix = 'lib'
|
||||
ext = 'dylib'
|
||||
|
@ -255,10 +284,20 @@ def run_unit_test():
|
|||
print("cust_state: ", len(cust_state))
|
||||
|
||||
(channel_token, cust_state, com, com_proof) = libbolt.bidirectional_establish_customer_generate_proof(channel_token, cust_state)
|
||||
print("channel token len: => ", len(channel_token))
|
||||
print("channel token: => ", channel_token)
|
||||
#libbolt.get_compact_channel_token(channel_token)
|
||||
|
||||
print("cust state: ", cust_state)
|
||||
#libbolt.get_compact_signing_keys(cust_state)
|
||||
|
||||
print("com: ", com)
|
||||
|
||||
cust_state_dict = json.loads(cust_state)
|
||||
channel_id = libbolt.bidirectional_generate_channel_id(channel_token)
|
||||
print("channel ID: ", channel_id)
|
||||
#print("wallet chan ID: ", cust_state_dict["wallet"]["channelId"])
|
||||
|
||||
close_token = libbolt.bidirectional_establish_merchant_issue_close_token(channel_state, com, com_proof, cust_state_dict["wallet"]["channelId"], b0_cust, b0_merch, merch_state)
|
||||
print("close token: ", close_token)
|
||||
|
||||
|
|
|
@ -0,0 +1,369 @@
|
|||
from ctypes import cdll
|
||||
from sys import platform
|
||||
|
||||
import sys, ctypes
|
||||
from ctypes import c_void_p, c_uint8
|
||||
|
||||
import ast
|
||||
import json
|
||||
|
||||
class Libbolt(object):
|
||||
"""Libbolt Py/C low-level API"""
|
||||
|
||||
def __init__(self, path):
|
||||
self.lib = cdll.LoadLibrary(path)
|
||||
self.load_library_params()
|
||||
|
||||
def load_library_params(self):
|
||||
self.lib.ffishim_bn256_channel_setup.argtypes = (c_void_p, c_uint8)
|
||||
self.lib.ffishim_bn256_channel_setup.restype = c_void_p
|
||||
|
||||
# ESTABLISH PROTOCOL
|
||||
|
||||
self.lib.ffishim_bn256_init_merchant.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_init_merchant.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_init_customer.argtypes = (c_void_p, ctypes.c_int32, ctypes.c_int32, c_void_p)
|
||||
self.lib.ffishim_bn256_init_customer.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_establish_customer_generate_proof.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_establish_customer_generate_proof.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_generate_channel_id.argtypes = (c_void_p, )
|
||||
self.lib.ffishim_bn256_generate_channel_id.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_establish_merchant_issue_close_token.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_establish_merchant_issue_close_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_establish_merchant_issue_pay_token.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_establish_merchant_issue_pay_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_verify_close_token.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_verify_close_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_establish_customer_final.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_establish_customer_final.restype = c_void_p
|
||||
|
||||
# PAY PROTOCOL
|
||||
|
||||
self.lib.ffishim_bn256_pay_generate_payment_proof.argtypes = (c_void_p, c_void_p, ctypes.c_int32)
|
||||
self.lib.ffishim_bn256_pay_generate_payment_proof.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_pay_verify_payment_proof.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_pay_verify_payment_proof.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_pay_verify_multiple_payment_proofs.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_pay_verify_multiple_payment_proofs.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_pay_generate_revoke_token.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_pay_generate_revoke_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_pay_verify_revoke_token.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_pay_verify_revoke_token.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_pay_verify_multiple_revoke_tokens.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_pay_verify_multiple_revoke_tokens.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_pay_verify_payment_token.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_pay_verify_payment_token.restype = c_void_p
|
||||
|
||||
# CLOSE
|
||||
|
||||
self.lib.ffishim_bn256_customer_close.argtypes = (c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_customer_close.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_merchant_close.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_merchant_close.restype = c_void_p
|
||||
|
||||
# ON-CHAIN BOLT LOGIC / WTPs
|
||||
|
||||
self.lib.ffishim_bn256_wtp_verify_cust_close_message.argtypes = (c_void_p, c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_wtp_verify_cust_close_message.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_bn256_wtp_verify_merch_close_message.argtypes = (c_void_p, c_void_p, c_void_p)
|
||||
self.lib.ffishim_bn256_wtp_verify_merch_close_message.restype = c_void_p
|
||||
|
||||
self.lib.ffishim_free_string.argtypes = (c_void_p, )
|
||||
|
||||
def channel_setup(self, name, third_party_support=0):
|
||||
output_string = self.lib.ffishim_bn256_channel_setup(name.encode(), third_party_support)
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('channel_state')
|
||||
|
||||
# INIT PROTOCOL
|
||||
|
||||
def bidirectional_init_merchant(self, channel_state, name):
|
||||
output_string = self.lib.ffishim_bn256_init_merchant(channel_state.encode(), name.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('channel_token'), output_dictionary.get('merch_state'), output_dictionary.get('channel_state')
|
||||
|
||||
def bidirectional_init_customer(self, channel_token, b0_cust, b0_merch, name):
|
||||
output_string = self.lib.ffishim_bn256_init_customer(channel_token.encode(), b0_cust, b0_merch, name.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('channel_token'), output_dictionary.get('cust_state'))
|
||||
|
||||
# ESTABLISH PROTOCOL
|
||||
|
||||
def bidirectional_generate_channel_id(self, channel_token):
|
||||
output_string = self.lib.ffishim_bn256_generate_channel_id(channel_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('channel_id')
|
||||
|
||||
def bidirectional_establish_customer_generate_proof(self, channel_token, cust_state):
|
||||
output_string = self.lib.ffishim_bn256_establish_customer_generate_proof(channel_token.encode(), cust_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('channel_token'), output_dictionary.get('cust_state'), output_dictionary.get('com'), output_dictionary.get('com_proof')
|
||||
|
||||
def bidirectional_establish_merchant_issue_close_token(self, channel_state, com, com_proof, channel_id, init_cust, init_merch, merch_state):
|
||||
output_string = self.lib.ffishim_bn256_establish_merchant_issue_close_token(channel_state.encode(), com.encode(), com_proof.encode(), json.dumps(channel_id).encode(), init_cust, init_merch, merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('close_token')
|
||||
|
||||
def bidirectional_establish_merchant_issue_pay_token(self, channel_state, com, merch_state):
|
||||
output_string = self.lib.ffishim_bn256_establish_merchant_issue_pay_token(channel_state.encode(), com.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('pay_token')
|
||||
|
||||
def bidirectional_establish_customer_verify_close_token(self, channel_state, cust_state, close_token):
|
||||
output_string = self.lib.ffishim_bn256_verify_close_token(channel_state.encode(), cust_state.encode(), close_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
is_token_valid = self._convert_boolean(output_dictionary.get('is_token_valid'))
|
||||
return is_token_valid, output_dictionary.get('channel_state'), output_dictionary.get('cust_state')
|
||||
|
||||
def bidirectional_establish_customer_final(self, channel_state, cust_state, pay_token):
|
||||
output_string = self.lib.ffishim_bn256_establish_customer_final(channel_state.encode(), cust_state.encode(), pay_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
is_established = self._convert_boolean(output_dictionary.get('is_established'))
|
||||
return is_established, output_dictionary.get('channel_state'), output_dictionary.get('cust_state')
|
||||
|
||||
# PAY PROTOCOL
|
||||
|
||||
# generate payment proof and new cust state
|
||||
def bidirectional_pay_generate_payment_proof(self, channel_state, cust_state, amount):
|
||||
output_string = self.lib.ffishim_bn256_pay_generate_payment_proof(channel_state.encode(), cust_state.encode(), amount)
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('payment'), output_dictionary.get('cust_state')
|
||||
|
||||
# verify payment proof
|
||||
def bidirectional_pay_verify_payment_proof(self, channel_state, pay_proof, merch_state):
|
||||
output_string = self.lib.ffishim_bn256_pay_verify_payment_proof(channel_state.encode(), pay_proof.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('close_token'), output_dictionary.get('merch_state'))
|
||||
|
||||
# verify multiple payment proof
|
||||
def bidirectional_pay_verify_multiple_payment_proofs(self, channel_state, sender_pay_proof, receiver_pay_proof, merch_state):
|
||||
output_string = self.lib.ffishim_bn256_pay_verify_multiple_payment_proofs(channel_state.encode(), sender_pay_proof.encode(), receiver_pay_proof.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('sender_close_token'), output_dictionary.get('receiver_cond_close_token'), output_dictionary.get('merch_state'))
|
||||
|
||||
# generate revoke token
|
||||
def bidirectional_pay_generate_revoke_token(self, channel_state, cust_state, new_cust_state, close_token):
|
||||
output_string = self.lib.ffishim_bn256_pay_generate_revoke_token(channel_state.encode(), cust_state.encode(),
|
||||
new_cust_state.encode(), close_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('revoke_token'), output_dictionary.get('cust_state')
|
||||
|
||||
# verify revoke token
|
||||
def bidirectional_pay_verify_revoke_token(self, revoke_token, merch_state):
|
||||
output_string = self.lib.ffishim_bn256_pay_verify_revoke_token(revoke_token.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('pay_token'), output_dictionary.get('merch_state'))
|
||||
|
||||
# verify multiple revoke tokens
|
||||
def bidirectional_pay_verify_multiple_revoke_tokens(self, sender_revoke_token, receiver_revoke_token, merch_state):
|
||||
output_string = self.lib.ffishim_bn256_pay_verify_multiple_revoke_tokens(sender_revoke_token.encode(), receiver_revoke_token.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('sender_pay_token'), output_dictionary.get('receiver_pay_token'), output_dictionary.get('merch_state'))
|
||||
|
||||
# verify payment token
|
||||
def bidirectional_pay_verify_payment_token(self, channel_state, cust_state, pay_token):
|
||||
output_string = self.lib.ffishim_bn256_pay_verify_payment_token(channel_state.encode(), cust_state.encode(), pay_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
is_pay_valid = self._convert_boolean(output_dictionary.get('is_pay_valid'))
|
||||
return (output_dictionary.get('cust_state'), is_pay_valid)
|
||||
|
||||
# CLOSE
|
||||
|
||||
def bidirectional_customer_close(self, channel_state, cust_state):
|
||||
output_string = self.lib.ffishim_bn256_customer_close(channel_state.encode(), cust_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('cust_close')
|
||||
|
||||
def bidirectional_merchant_close(self, channel_state, channel_token, address, cust_close, merch_state):
|
||||
output_string = self.lib.ffishim_bn256_merchant_close(channel_state.encode(), channel_token.encode(),
|
||||
address.encode(), cust_close.encode(), merch_state.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return (output_dictionary.get('wpk'), output_dictionary.get('merch_close'), output_dictionary.get('error'))
|
||||
|
||||
# WTP logic
|
||||
|
||||
def wtp_get_wallet(self, cust_state):
|
||||
cust_state_dict = self._interperate_json_string_as_dictionary(cust_state)
|
||||
return json.dumps(cust_state_dict.get("wpk")), json.dumps(cust_state_dict.get("wallet"))
|
||||
|
||||
def wtp_get_close_token(self, cust_close):
|
||||
cust_close_dict = self._interperate_json_string_as_dictionary(cust_close)
|
||||
return json.dumps(cust_close_dict.get("signature"))
|
||||
|
||||
def wtp_verify_cust_close_message(self, channel_token, wpk, cust_close_wallet, close_token):
|
||||
output_string = self.lib.ffishim_bn256_wtp_verify_cust_close_message(channel_token.encode(),
|
||||
wpk.encode(),
|
||||
cust_close_wallet.encode(),
|
||||
close_token.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('result')
|
||||
|
||||
def wtp_verify_merch_close_message(self, channel_token, wpk, merch_close):
|
||||
output_string = self.lib.ffishim_bn256_wtp_verify_merch_close_message(channel_token.encode(),
|
||||
wpk.encode(),
|
||||
merch_close.encode())
|
||||
output_dictionary = ast.literal_eval(ctypes.cast(output_string, ctypes.c_char_p).value.decode('utf-8'))
|
||||
return output_dictionary.get('result')
|
||||
|
||||
def _interperate_json_string_as_dictionary(self, json_string):
|
||||
return ast.literal_eval(json_string)
|
||||
|
||||
def _convert_boolean(self, bool_str):
|
||||
if bool_str == "true":
|
||||
return True
|
||||
if bool_str == "false":
|
||||
return False
|
||||
return bool_str
|
||||
|
||||
if platform == 'darwin':
|
||||
prefix = 'lib'
|
||||
ext = 'dylib'
|
||||
elif platform == 'win32':
|
||||
prefix = ''
|
||||
ext = 'dll'
|
||||
else:
|
||||
prefix = 'lib'
|
||||
ext = 'so'
|
||||
|
||||
DEBUG = 'debug'
|
||||
RELEASE = 'release'
|
||||
mode = RELEASE # debug or release
|
||||
|
||||
def run_unit_test():
|
||||
libbolt = Libbolt('target/{}/{}bolt.{}'.format(mode, prefix, ext))
|
||||
|
||||
b0_cust = 100
|
||||
b0_merch = 10
|
||||
|
||||
channel_state = libbolt.channel_setup("My New Channel A")
|
||||
|
||||
print("channel state new: ", len(channel_state))
|
||||
|
||||
(channel_token, merch_state, channel_state) = libbolt.bidirectional_init_merchant(channel_state, "Bob")
|
||||
|
||||
print("merch_state: ", len(merch_state))
|
||||
#print("channel_token: ", type(_channel_token))
|
||||
|
||||
(channel_token, cust_state) = libbolt.bidirectional_init_customer(channel_token, b0_cust, b0_merch, "Alice")
|
||||
print("cust_state: ", len(cust_state))
|
||||
|
||||
(channel_token, cust_state, com, com_proof) = libbolt.bidirectional_establish_customer_generate_proof(channel_token, cust_state)
|
||||
print("channel token len: => ", len(channel_token))
|
||||
print("channel token: => ", channel_token)
|
||||
print("com: ", com)
|
||||
|
||||
cust_state_dict = json.loads(cust_state)
|
||||
channel_id = libbolt.bidirectional_generate_channel_id(channel_token)
|
||||
print("channel ID: ", channel_id)
|
||||
#print("wallet chan ID: ", cust_state_dict["wallet"]["channelId"])
|
||||
|
||||
close_token = libbolt.bidirectional_establish_merchant_issue_close_token(channel_state, com, com_proof, cust_state_dict["wallet"]["channelId"], b0_cust, b0_merch, merch_state)
|
||||
print("close token: ", close_token)
|
||||
|
||||
(is_token_valid, channel_state, cust_state) = libbolt.bidirectional_establish_customer_verify_close_token(channel_state, cust_state, close_token)
|
||||
|
||||
pay_token = libbolt.bidirectional_establish_merchant_issue_pay_token(channel_state, com, merch_state)
|
||||
print("pay token: ", pay_token)
|
||||
|
||||
(is_channel_established, channel_state, cust_state) = libbolt.bidirectional_establish_customer_final(channel_state, cust_state, pay_token)
|
||||
if is_channel_established:
|
||||
print("updated cust_state: ", cust_state)
|
||||
else:
|
||||
print("channel still not established. did you verify close token?")
|
||||
|
||||
# Pay protocol
|
||||
print("Pay protocol...")
|
||||
|
||||
# make a payment
|
||||
amount = 5
|
||||
(payment_proof, new_cust_state) = libbolt.bidirectional_pay_generate_payment_proof(channel_state, cust_state, amount)
|
||||
print("Pay proof: ", len(payment_proof))
|
||||
print("new cust wallet: ", new_cust_state)
|
||||
print("<========================================>")
|
||||
revoked_wpk, _ = libbolt.wtp_get_wallet(new_cust_state)
|
||||
|
||||
(new_close_token, merch_state) = libbolt.bidirectional_pay_verify_payment_proof(channel_state, payment_proof, merch_state)
|
||||
print("Close token: ", new_close_token)
|
||||
print("<========================================>")
|
||||
|
||||
(revoke_token, cust_state) = libbolt.bidirectional_pay_generate_revoke_token(channel_state, cust_state, new_cust_state, new_close_token)
|
||||
print("Revoke token: ", revoke_token)
|
||||
|
||||
(pay_token, merch_state) = libbolt.bidirectional_pay_verify_revoke_token(revoke_token, merch_state)
|
||||
print("Pay token: ", pay_token)
|
||||
|
||||
(cust_state, is_pay_valid) = libbolt.bidirectional_pay_verify_payment_token(channel_state, cust_state, pay_token)
|
||||
print("Pay token is valid: ", is_pay_valid)
|
||||
|
||||
old_cust_close = libbolt.bidirectional_customer_close(channel_state, cust_state)
|
||||
|
||||
# make a payment
|
||||
amount = 10
|
||||
(payment_proof2, new_cust_state2) = libbolt.bidirectional_pay_generate_payment_proof(channel_state, cust_state, amount)
|
||||
print("Pay proof 2: ", len(payment_proof2))
|
||||
print("new cust wallet 2: ", new_cust_state2)
|
||||
print("<========================================>")
|
||||
|
||||
(new_close_token2, merch_state) = libbolt.bidirectional_pay_verify_payment_proof(channel_state, payment_proof2, merch_state)
|
||||
print("Close token 2: ", new_close_token2)
|
||||
print("<========================================>")
|
||||
|
||||
(revoke_token2, cust_state) = libbolt.bidirectional_pay_generate_revoke_token(channel_state, cust_state, new_cust_state2, new_close_token2)
|
||||
print("Revoke token 2: ", revoke_token)
|
||||
|
||||
(pay_token2, merch_state) = libbolt.bidirectional_pay_verify_revoke_token(revoke_token2, merch_state)
|
||||
print("Pay token 2: ", pay_token2)
|
||||
|
||||
(cust_state, is_pay_valid) = libbolt.bidirectional_pay_verify_payment_token(channel_state, cust_state, pay_token2)
|
||||
print("Pay token is valid: ", is_pay_valid)
|
||||
|
||||
print("<========================================>")
|
||||
print("<========================================>")
|
||||
|
||||
cust_close = libbolt.bidirectional_customer_close(channel_state, cust_state)
|
||||
print("Cust close msg: ", cust_close)
|
||||
print("<========================================>")
|
||||
|
||||
# normal case: no action b/c cust close is valid
|
||||
address = "11" * 32
|
||||
merch_close = libbolt.bidirectional_merchant_close(channel_state, channel_token, address, cust_close, merch_state)
|
||||
print("Customer initiated - Merch close msg: ", merch_close)
|
||||
print("<========================================>")
|
||||
|
||||
# common case: merchant catches customer double spending
|
||||
address = "11" * 32
|
||||
merch_wpk, merch_close_msg, _ = libbolt.bidirectional_merchant_close(channel_state, channel_token, address, old_cust_close, merch_state)
|
||||
print("Double spend - Merch close msg: ", merch_close_msg)
|
||||
merch_close_valid = libbolt.wtp_verify_merch_close_message(channel_token, merch_wpk, merch_close_msg)
|
||||
print("Merchant close msg valid: ", merch_close_valid)
|
||||
print("<========================================>")
|
||||
|
||||
print("<========================================>")
|
||||
wpk, cust_close_wallet = libbolt.wtp_get_wallet(cust_state)
|
||||
print("wpk = ", wpk)
|
||||
print("close-msg wallet = ", cust_close_wallet)
|
||||
cust_close_token = libbolt.wtp_get_close_token(cust_close)
|
||||
print("close token: ", cust_close_token)
|
||||
print("Valid channel opening: ", libbolt.wtp_verify_cust_close_message(channel_token, wpk, cust_close_wallet, cust_close_token))
|
||||
# TODO: merch close when cust_close represents correct channel state
|
||||
|
||||
print("Invalid channel opening: ", libbolt.wtp_verify_cust_close_message(channel_token, revoked_wpk, cust_close_wallet, cust_close_token))
|
||||
print("<========================================>")
|
||||
|
||||
if __name__ == "__main__":
|
||||
run_unit_test()
|
|
@ -4,11 +4,9 @@ Efficient Protocols for Set Membership and Range Proofs
|
|||
Jan Camenisch, Rafik Chaabouni, and abhi shelat
|
||||
Asiacrypt 2008
|
||||
*/
|
||||
extern crate pairing;
|
||||
extern crate rand;
|
||||
|
||||
use rand::Rng;
|
||||
use super::*;
|
||||
use rand::Rng;
|
||||
use cl::{Signature, PublicParams, setup, BlindKeyPair, ProofState, SignatureProof, BlindPublicKey};
|
||||
use ped92::{Commitment, CSMultiParams};
|
||||
use pairing::{Engine, CurveProjective};
|
||||
|
|
117
src/channels.rs
117
src/channels.rs
|
@ -1,14 +1,3 @@
|
|||
/*
|
||||
* Implement for Bolt protocols:
|
||||
* - initializing channel state and generating cust/merch wallets
|
||||
* - establish protocol
|
||||
* - pay protocol
|
||||
* - channel close algorithms (WIP)
|
||||
*/
|
||||
|
||||
extern crate pairing;
|
||||
extern crate rand;
|
||||
|
||||
use super::*;
|
||||
use pairing::Engine;
|
||||
use cl::{BlindKeyPair, Signature};
|
||||
|
@ -134,8 +123,6 @@ impl<E: Engine> ChannelToken<E> {
|
|||
|
||||
// add a method to compute hash on chain: SHA256 + RIPEMD160?
|
||||
}
|
||||
// add methods to check if channel token is initialized
|
||||
// (only if
|
||||
|
||||
///
|
||||
/// Channel state for generating/loading channel parameters and generating keypairs
|
||||
|
@ -223,13 +210,20 @@ impl<E: Engine> CustomerState<E> {
|
|||
<E as pairing::Engine>::G2: serde::Serialize,
|
||||
<E as ff::ScalarEngine>::Fr: serde::Serialize
|
||||
{
|
||||
let mut kp = secp256k1::Secp256k1::new();
|
||||
kp.randomize(csprng);
|
||||
let secp = secp256k1::Secp256k1::new();
|
||||
|
||||
// generate the keypair for the channel
|
||||
let (sk_c, pk_c) = kp.generate_keypair(csprng);
|
||||
let mut seckey = [0u8; 32];
|
||||
csprng.fill_bytes(&mut seckey);
|
||||
|
||||
// generate the signing keypair for the channel
|
||||
let sk_c = secp256k1::SecretKey::from_slice(&seckey).unwrap();
|
||||
let pk_c = secp256k1::PublicKey::from_secret_key(&secp, &sk_c);
|
||||
|
||||
let mut seckey1 = [0u8; 32];
|
||||
csprng.fill_bytes(&mut seckey1);
|
||||
// generate the keypair for the initial wallet
|
||||
let (wsk, wpk) = kp.generate_keypair(csprng);
|
||||
let wsk = secp256k1::SecretKey::from_slice(&seckey1).unwrap();
|
||||
let wpk = secp256k1::PublicKey::from_secret_key(&secp, &wsk);
|
||||
// hash the wallet pub key
|
||||
let wpk_h = hash_pubkey_to_fr::<E>(&wpk);
|
||||
channel_token.set_customer_pk(&pk_c);
|
||||
|
@ -346,9 +340,14 @@ impl<E: Engine> CustomerState<E> {
|
|||
// for channel pay
|
||||
pub fn generate_payment<R: Rng>(&self, csprng: &mut R, channel: &ChannelState<E>, amount: i64) -> (NIZKProof<E>, Commitment<E>, secp256k1::PublicKey, CustomerState<E>) {
|
||||
// 1 - chooose new wpk/wsk pair
|
||||
let mut kp = secp256k1::Secp256k1::new();
|
||||
kp.randomize(csprng);
|
||||
let (new_wsk, new_wpk) = kp.generate_keypair(csprng);
|
||||
let secp = secp256k1::Secp256k1::new();
|
||||
|
||||
let mut seckey = [0u8; 32];
|
||||
csprng.fill_bytes(&mut seckey);
|
||||
|
||||
let new_wsk = secp256k1::SecretKey::from_slice(&seckey).unwrap();
|
||||
let new_wpk = secp256k1::PublicKey::from_secret_key(&secp, &new_wsk);
|
||||
// compute hash of the pubkey
|
||||
let wpk_h = hash_pubkey_to_fr::<E>(&new_wpk);
|
||||
|
||||
// 2 - form new wallet and commitment
|
||||
|
@ -489,9 +488,14 @@ impl<E: Engine> MerchantState<E> {
|
|||
pub fn new<R: Rng>(csprng: &mut R, channel: &mut ChannelState<E>, id: String) -> (Self, ChannelState<E>) {
|
||||
let l = 5;
|
||||
// generate keys here
|
||||
let mut tx_kp = secp256k1::Secp256k1::new();
|
||||
tx_kp.randomize(csprng);
|
||||
let (wsk, wpk) = tx_kp.generate_keypair(csprng);
|
||||
let secp = secp256k1::Secp256k1::new();
|
||||
// tx_kp.randomize(csprng);
|
||||
// let (wsk, wpk) = tx_kp.generate_keypair(csprng);
|
||||
let mut seckey = [0u8; 32];
|
||||
csprng.fill_bytes(&mut seckey);
|
||||
let wsk = secp256k1::SecretKey::from_slice(&seckey).unwrap();
|
||||
let wpk = secp256k1::PublicKey::from_secret_key(&secp, &wsk);
|
||||
|
||||
let mut ch = channel.clone();
|
||||
let nizkParams = NIZKSecretParams::<E>::setup(csprng, l);
|
||||
ch.cp = Some(ChannelParams::<E> { pub_params: nizkParams.pubParams.clone(), l, extra_verify: true });
|
||||
|
@ -611,9 +615,10 @@ impl<E: Engine> MerchantState<E> {
|
|||
mod tests {
|
||||
use super::*;
|
||||
use pairing::bls12_381::Bls12;
|
||||
use pairing::bn256::Bn256;
|
||||
|
||||
#[test]
|
||||
fn channel_util_works() {
|
||||
fn channel_util_works_with_Bls12() {
|
||||
let mut channel = ChannelState::<Bls12>::new(String::from("Channel A <-> B"), false);
|
||||
let rng = &mut rand::thread_rng();
|
||||
|
||||
|
@ -689,4 +694,66 @@ mod tests {
|
|||
|
||||
let _channelId = channel_token.compute_channel_id();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn channel_util_works_with_Bn256() {
|
||||
let mut channel = ChannelState::<Bn256>::new(String::from("Channel A <-> B"), false);
|
||||
let rng = &mut rand::thread_rng();
|
||||
|
||||
let b0_cust = 100;
|
||||
let b0_merch = 20;
|
||||
// each party executes the init algorithm on the agreed initial challenge balance
|
||||
// in order to derive the channel tokens
|
||||
// initialize on the merchant side with balance: b0_merch
|
||||
let (mut merch_state, mut channel) = MerchantState::<Bn256>::new(rng, &mut channel, String::from("Merchant B"));
|
||||
|
||||
// initialize the merchant wallet with the balance
|
||||
let mut channel_token = merch_state.init(&mut channel);
|
||||
|
||||
// retrieve commitment setup params (using merchant long lived pk params)
|
||||
// initialize on the customer side with balance: b0_cust
|
||||
let mut cust_state = CustomerState::<Bn256>::new(rng, &mut channel_token, b0_cust, b0_merch, String::from("Alice"));
|
||||
|
||||
// lets establish the channel
|
||||
let cust_com_proof = cust_state.generate_proof(rng, &mut channel_token);
|
||||
|
||||
// first return the close token, then wait for escrow-tx confirmation
|
||||
// then send the pay-token after confirmation
|
||||
let channelId = channel_token.compute_channel_id();
|
||||
assert_eq!(channelId, cust_state.get_wallet().channelId);
|
||||
let (close_token, pay_token) = merch_state.verify_proof(rng, &channel, &cust_state.w_com, &cust_com_proof, &channelId, b0_cust, b0_merch).unwrap();
|
||||
// unblind tokens and verify signatures
|
||||
assert!(cust_state.verify_close_token(&channel, &close_token));
|
||||
|
||||
assert!(cust_state.verify_pay_token(&channel, &pay_token));
|
||||
|
||||
// pay protocol tests
|
||||
let amount = 10;
|
||||
let (pay_proof, new_com, old_wpk, new_cw) = cust_state.generate_payment(rng, &channel, amount);
|
||||
|
||||
// new pay_token is not sent until revoke_token is obtained from the customer
|
||||
let new_close_token = merch_state.verify_payment(rng, &channel, &pay_proof, &new_com, &old_wpk, amount).unwrap();
|
||||
|
||||
//println!("1 - Updated close Token : {}", new_close_token);
|
||||
// unblind tokens and verify signatures
|
||||
|
||||
// assuming the pay_proof checks out, can go ahead and update internal state of cust_state
|
||||
assert!(cust_state.update(new_cw));
|
||||
//println!("2 - updated customer wallet!");
|
||||
|
||||
assert!(cust_state.verify_close_token(&channel, &new_close_token));
|
||||
//println!("3 - verified the close token!");
|
||||
|
||||
// invalidate the previous state only if close token checks out
|
||||
let (revoke_msg, revoke_sig) = cust_state.generate_revoke_token(&channel, &new_close_token).unwrap();
|
||||
//println!("4 - Generated revoke token successfully.");
|
||||
|
||||
//println!("5 - Revoke token => {}", revoke_token);
|
||||
|
||||
let new_pay_token = merch_state.verify_revoke_token(&revoke_sig, &revoke_msg, &old_wpk).unwrap();
|
||||
assert!(cust_state.verify_pay_token(&channel, &new_pay_token));
|
||||
|
||||
//println!("Validated revoke token!");
|
||||
}
|
||||
|
||||
}
|
||||
|
|
106
src/cl.rs
106
src/cl.rs
|
@ -1,8 +1,5 @@
|
|||
// cl.rs
|
||||
// CL Sigs - Pointcheval Sanders ('06)
|
||||
extern crate pairing;
|
||||
extern crate rand;
|
||||
|
||||
use super::*;
|
||||
use pairing::{CurveProjective, Engine};
|
||||
use ff::PrimeField;
|
||||
|
@ -12,6 +9,7 @@ use serde::{Serialize, Deserialize};
|
|||
use util;
|
||||
|
||||
#[derive(Clone, Serialize, Deserialize, Debug)]
|
||||
#[serde(bound(deserialize = "<E as pairing::Engine>::G1: serde::Deserialize<'de>, <E as pairing::Engine>::G2: serde::Deserialize<'de>"))]
|
||||
pub struct PublicParams<E: Engine> {
|
||||
pub g1: E::G1,
|
||||
pub g2: E::G2,
|
||||
|
@ -23,6 +21,18 @@ impl<E: Engine> PartialEq for PublicParams<E> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<E: Engine> PublicParams<E> {
|
||||
pub fn from_slice<'de>(ser_g1: &'de [u8], ser_g2: &'de [u8]) -> Self
|
||||
where <E as pairing::Engine>::G1: serde::Deserialize<'de>,
|
||||
<E as pairing::Engine>::G2: serde::Deserialize<'de>
|
||||
{
|
||||
// TODO: handle malformed input errors
|
||||
let g1: E::G1 = serde_json::from_slice(ser_g1).unwrap();
|
||||
let g2: E::G2 = serde_json::from_slice(ser_g2).unwrap();
|
||||
|
||||
PublicParams { g1, g2 }
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Serialize, Deserialize, Debug)]
|
||||
pub struct SecretKey<E: Engine> {
|
||||
|
@ -51,6 +61,7 @@ impl<E: Engine> PartialEq for SecretKey<E> {
|
|||
|
||||
|
||||
#[derive(Clone, Serialize, Deserialize, Debug)]
|
||||
#[serde(bound(deserialize = "<E as pairing::Engine>::G2: serde::Deserialize<'de>"))]
|
||||
pub struct PublicKey<E: Engine> {
|
||||
pub X: E::G2,
|
||||
pub Y: Vec<E::G2>,
|
||||
|
@ -75,6 +86,23 @@ impl<E: Engine> PartialEq for PublicKey<E> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<E: Engine> PublicKey<E> {
|
||||
pub fn from_slice<'de>(ser_x: &'de [u8], ser_y: &'de [u8], y_len: usize, num_elems: usize) -> Self
|
||||
where <E as pairing::Engine>::G2: serde::Deserialize<'de>
|
||||
{
|
||||
let X: E::G2 = serde_json::from_slice(ser_x).unwrap();
|
||||
let mut Y: Vec<E::G2> = Vec::new();
|
||||
let mut start_pos = 0;
|
||||
let mut end_pos = y_len;
|
||||
for _ in 0 .. num_elems {
|
||||
let y = serde_json::from_slice(&ser_y[start_pos .. end_pos]).unwrap();
|
||||
start_pos = end_pos;
|
||||
end_pos += y_len;
|
||||
Y.push(y);
|
||||
}
|
||||
PublicKey { X, Y }
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Serialize, Deserialize, Debug)]
|
||||
pub struct BlindPublicKey<E: Engine> {
|
||||
|
@ -120,6 +148,19 @@ impl<E: Engine> PartialEq for Signature<E> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<E: Engine> Signature<E> {
|
||||
pub fn from_slice<'de>(ser_h: &'de [u8], ser_H: &'de [u8]) -> Self
|
||||
where <E as pairing::Engine>::G1: serde::Deserialize<'de>
|
||||
{
|
||||
// TODO: handle malformed input errors
|
||||
let h: E::G1 = serde_json::from_slice(ser_h).unwrap();
|
||||
let H: E::G1 = serde_json::from_slice(ser_H).unwrap();
|
||||
|
||||
Signature { h, H }
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#[derive(Clone)]
|
||||
pub struct KeyPair<E: Engine> {
|
||||
pub secret: SecretKey<E>,
|
||||
|
@ -682,10 +723,10 @@ mod tests {
|
|||
let blindkeypair = BlindKeyPair::<Bls12>::generate(&mut rng, &mpk, l);
|
||||
|
||||
let serialized = serde_json::to_vec(&mpk).unwrap();
|
||||
//println!("serialized = {:?}", serialized.len());
|
||||
println!("mpk serialized len = {:?}", serialized.len());
|
||||
|
||||
let _mpk_des: PublicParams<Bls12> = serde_json::from_slice(&serialized).unwrap();
|
||||
//println!("{}", mpk_des);
|
||||
//println!("{}", _mpk_des);
|
||||
|
||||
//println!("SK => {}", &keypair.secret);
|
||||
let sk_serialized = serde_json::to_vec(&keypair.secret).unwrap();
|
||||
|
@ -697,7 +738,7 @@ mod tests {
|
|||
|
||||
//println!("PK => {}", &keypair.public);
|
||||
let pk_serialized = serde_json::to_vec(&keypair.public).unwrap();
|
||||
//println!("pk_serialized = {:?}", pk_serialized.len());
|
||||
println!("cl pk_serialized len = {:?}", pk_serialized.len());
|
||||
|
||||
let _pk_des: PublicKey<Bls12> = serde_json::from_slice(&pk_serialized).unwrap();
|
||||
//assert_eq!(pk_des, keypair.public);
|
||||
|
@ -719,5 +760,58 @@ mod tests {
|
|||
assert_eq!(upk_des, unblind_pk);
|
||||
assert_ne!(upk_des, keypair.public);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_compact_public_params_deserialize() {
|
||||
let bin_g1= vec![132, 83, 99, 124, 75, 72, 15, 109, 12, 94, 84, 103, 1, 58, 160, 232, 190, 23, 119, 195, 112, 161, 152, 141, 178, 29, 141, 61, 227, 246, 215, 157, 140, 190, 100, 18, 248, 141, 57, 222, 12, 209, 191, 158, 143, 155, 87, 255];
|
||||
let bin_g2 = vec![147, 63, 33, 190, 248, 155, 91, 211, 249, 169, 1, 147, 101, 104, 219, 88, 204, 131, 38, 167, 25, 191, 86, 67, 139, 188, 171, 101, 154, 32, 234, 92, 3, 66, 235, 159, 7, 47, 16, 83, 3, 201, 13, 227, 179, 184, 101, 102, 21, 88, 153, 208, 93, 0, 57, 108, 250, 231, 74, 192, 82, 111, 13, 211, 12, 51, 224, 198, 121, 15, 63, 129, 25, 218, 193, 47, 182, 248, 112, 185, 163, 23, 175, 169, 76, 214, 36, 184, 142, 222, 48, 212, 157, 35, 115, 181];
|
||||
|
||||
let ser_g1 = util::encode_as_hexstring(&bin_g1);
|
||||
let ser_g2 = util::encode_as_hexstring(&bin_g2);
|
||||
|
||||
let str_g1 = ser_g1.as_bytes();
|
||||
let str_g2 = ser_g2.as_bytes();
|
||||
|
||||
let rec_mpk = PublicParams::<Bls12>::from_slice(&str_g1, &str_g2);
|
||||
|
||||
println!("g1: {}", rec_mpk.g1);
|
||||
println!("g2: {}", rec_mpk.g2);
|
||||
|
||||
let rec_g1_str = serde_json::to_string(&rec_mpk.g1).unwrap();
|
||||
assert_eq!(rec_g1_str, "\"8453637c4b480f6d0c5e5467013aa0e8be1777c370a1988db21d8d3de3f6d79d8cbe6412f88d39de0cd1bf9e8f9b57ff\"");
|
||||
|
||||
let rec_g2_str = serde_json::to_string(&rec_mpk.g2).unwrap();
|
||||
assert_eq!(rec_g2_str, "\"933f21bef89b5bd3f9a901936568db58cc8326a719bf56438bbcab659a20ea5c0342eb9f072f105303c90de3b3b86566155899d05d00396cfae74ac0526f0dd30c33e0c6790f3f8119dac12fb6f870b9a317afa94cd624b88ede30d49d2373b5\"");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_compact_cl_public_key_deserialize() {
|
||||
let bin_g2_x = vec![147, 63, 33, 190, 248, 155, 91, 211, 249, 169, 1, 147, 101, 104, 219, 88, 204, 131, 38, 167, 25, 191, 86, 67, 139, 188, 171, 101, 154, 32, 234, 92, 3, 66, 235, 159, 7, 47, 16, 83, 3, 201, 13, 227, 179, 184, 101, 102, 21, 88, 153, 208, 93, 0, 57, 108, 250, 231, 74, 192, 82, 111, 13, 211, 12, 51, 224, 198, 121, 15, 63, 129, 25, 218, 193, 47, 182, 248, 112, 185, 163, 23, 175, 169, 76, 214, 36, 184, 142, 222, 48, 212, 157, 35, 115, 181];
|
||||
let bin_g2_y1 = vec![143, 76, 112, 7, 35, 99, 254, 7, 255, 225, 69, 13, 99, 32, 92, 186, 234, 175, 230, 0, 202, 144, 1, 216, 187, 248, 152, 76, 229, 74, 156, 94, 4, 16, 132, 119, 157, 172, 231, 164, 207, 88, 41, 6, 234, 78, 73, 58, 19, 104, 236, 127, 5, 231, 248, 150, 53, 197, 85, 194, 110, 93, 1, 73, 24, 96, 149, 133, 109, 194, 16, 190, 244, 184, 254, 192, 52, 21, 205, 109, 18, 83, 189, 175, 208, 147, 74, 32, 181, 126, 224, 136, 250, 126, 224, 186];
|
||||
let bin_g2_y2 = vec![150, 132, 45, 236, 146, 135, 127, 242, 61, 55, 73, 100, 151, 12, 51, 134, 151, 42, 138, 227, 105, 54, 121, 7, 0, 27, 205, 139, 186, 69, 139, 143, 41, 132, 35, 33, 168, 35, 31, 52, 65, 5, 73, 153, 203, 25, 178, 196, 4, 9, 218, 130, 22, 64, 98, 152, 225, 212, 27, 202, 245, 234, 138, 34, 82, 102, 40, 72, 211, 248, 16, 221, 54, 154, 186, 95, 246, 132, 54, 0, 128, 170, 111, 94, 155, 166, 27, 225, 51, 31, 107, 223, 139, 0, 209, 236];
|
||||
|
||||
let ser_g2_x = util::encode_as_hexstring(&bin_g2_x);
|
||||
let ser_g2_y1 = util::encode_as_hexstring(&bin_g2_y1);
|
||||
let ser_g2_y2 = util::encode_as_hexstring(&bin_g2_y2);
|
||||
|
||||
let str_g2_x = ser_g2_x.as_bytes();
|
||||
let str_g2_y1 = ser_g2_y1.as_bytes();
|
||||
let str_g2_y2 = ser_g2_y2.as_bytes();
|
||||
|
||||
let mut vec = Vec::new();
|
||||
vec.extend(str_g2_y1);
|
||||
vec.extend(str_g2_y2);
|
||||
|
||||
let rec_cl_pk = PublicKey::<Bls12>::from_slice(&str_g2_x, &vec.as_slice(), ser_g2_y1.len(), 2);
|
||||
|
||||
let rec_x_str = serde_json::to_string(&rec_cl_pk.X).unwrap();
|
||||
assert_eq!(rec_x_str, "\"933f21bef89b5bd3f9a901936568db58cc8326a719bf56438bbcab659a20ea5c0342eb9f072f105303c90de3b3b86566155899d05d00396cfae74ac0526f0dd30c33e0c6790f3f8119dac12fb6f870b9a317afa94cd624b88ede30d49d2373b5\"");
|
||||
|
||||
let rec_y1_str = serde_json::to_string(&rec_cl_pk.Y[0]).unwrap();
|
||||
assert_eq!(rec_y1_str, "\"8f4c70072363fe07ffe1450d63205cbaeaafe600ca9001d8bbf8984ce54a9c5e041084779dace7a4cf582906ea4e493a1368ec7f05e7f89635c555c26e5d0149186095856dc210bef4b8fec03415cd6d1253bdafd0934a20b57ee088fa7ee0ba\"");
|
||||
|
||||
let rec_y2_str = serde_json::to_string(&rec_cl_pk.Y[1]).unwrap();
|
||||
assert_eq!(rec_y2_str, "\"96842dec92877ff23d374964970c3386972a8ae369367907001bcd8bba458b8f29842321a8231f3441054999cb19b2c40409da8216406298e1d41bcaf5ea8a2252662848d3f810dd369aba5ff684360080aa6f5e9ba61be1331f6bdf8b00d1ec\"");
|
||||
}
|
||||
}
|
||||
|
||||
|
|
168
src/ffishim.rs
168
src/ffishim.rs
|
@ -11,7 +11,6 @@ pub mod ffishim {
|
|||
use libc::c_char;
|
||||
use std::ffi::{CStr, CString};
|
||||
use std::str;
|
||||
// use channels::{ChannelcloseM, ResultBoltType, BoltError};
|
||||
|
||||
fn error_message(s: String) -> *mut c_char {
|
||||
let ser = ["{\'error\':\'", &s, "\'}"].concat();
|
||||
|
@ -34,24 +33,7 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
pub type ResultSerdeType<T> = Result<T, serde_json::error::Error>;
|
||||
|
||||
// fn deserialize_object<'a, T>(serialized: *mut c_char) -> T
|
||||
// where
|
||||
// T: Deserialize<'a>,
|
||||
// {
|
||||
// let bytes = unsafe { CStr::from_ptr(serialized).to_bytes() };
|
||||
// let string: &str = str::from_utf8(bytes).unwrap(); // make sure the bytes are UTF-8
|
||||
// serde_json::from_str(&string).unwrap()
|
||||
// }
|
||||
//
|
||||
// fn deserialize_optional_object<'a, T>(serialized: *mut c_char) -> Option<T>
|
||||
// where
|
||||
// T: Deserialize<'a>,
|
||||
// {
|
||||
// let bytes = unsafe { CStr::from_ptr(serialized).to_bytes() };
|
||||
// let string: &str = str::from_utf8(bytes).unwrap(); // make sure the bytes are UTF-8
|
||||
// Some(serde_json::from_str(&string).unwrap())
|
||||
// }
|
||||
type CURVE = Bls12;
|
||||
|
||||
fn deserialize_result_object<'a, T>(serialized: *mut c_char) -> ResultSerdeType<T>
|
||||
where
|
||||
|
@ -71,7 +53,7 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_wtp_check_wpk(ser_wpk: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_wtp_check_wpk(ser_wpk: *mut c_char) -> *mut c_char {
|
||||
let wpk_result: ResultSerdeType<secp256k1::PublicKey> = deserialize_result_object(ser_wpk);
|
||||
let _wpk = handle_errors!(wpk_result);
|
||||
|
||||
|
@ -82,7 +64,7 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_channel_setup(channel_name: *const c_char, third_party_support: u32) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_channel_setup(channel_name: *const c_char, third_party_support: u32) -> *mut c_char {
|
||||
let bytes = unsafe { CStr::from_ptr(channel_name).to_bytes() };
|
||||
let name: &str = str::from_utf8(bytes).unwrap(); // make sure the bytes are UTF-8
|
||||
|
||||
|
@ -90,7 +72,7 @@ pub mod ffishim {
|
|||
if third_party_support > 1 {
|
||||
tps = true;
|
||||
}
|
||||
let channel_state = bidirectional::ChannelState::<Bls12>::new(name.to_string(), tps);
|
||||
let channel_state = bidirectional::ChannelState::<CURVE>::new(name.to_string(), tps);
|
||||
|
||||
let ser = ["{\'channel_state\':\'", serde_json::to_string(&channel_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
|
@ -100,9 +82,9 @@ pub mod ffishim {
|
|||
// INIT
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_init_merchant(ser_channel_state: *mut c_char, name_ptr: *const c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_init_merchant(ser_channel_state: *mut c_char, name_ptr: *const c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let mut channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
let bytes = unsafe { CStr::from_ptr(name_ptr).to_bytes() };
|
||||
|
@ -117,10 +99,10 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_init_customer(ser_channel_token: *mut c_char, balance_customer: i64, balance_merchant: i64, name_ptr: *const c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_init_customer(ser_channel_token: *mut c_char, balance_customer: i64, balance_merchant: i64, name_ptr: *const c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<Bls12>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let mut channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the name
|
||||
|
@ -136,15 +118,15 @@ pub mod ffishim {
|
|||
|
||||
// ESTABLISH
|
||||
|
||||
#[no_mangle] // bidirectional::establish_customer_generate_proof(rng, &mut channel_token, &mut cust_state);
|
||||
pub extern fn ffishim_bidirectional_establish_customer_generate_proof(ser_channel_token: *mut c_char, ser_customer_state: *mut c_char) -> *mut c_char {
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bls12_establish_customer_generate_proof(ser_channel_token: *mut c_char, ser_customer_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<Bls12>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let mut channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<Bls12>> = deserialize_result_object(ser_customer_state);
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_customer_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
let (com, com_proof) = bidirectional::establish_customer_generate_proof(rng, &mut channel_token, &mut cust_state);
|
||||
|
@ -159,26 +141,38 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_establish_merchant_issue_close_token(ser_channel_state: *mut c_char, ser_com: *mut c_char, ser_com_proof: *mut c_char, ser_channel_id: *mut c_char, init_cust_bal: i64, init_merch_bal: i64, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_generate_channel_id(ser_channel_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
let id = channel_token.compute_channel_id();
|
||||
let ser = ["{\'channel_id\':\'", serde_json::to_string(&id).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bls12_establish_merchant_issue_close_token(ser_channel_state: *mut c_char, ser_com: *mut c_char, ser_com_proof: *mut c_char, ser_channel_id: *mut c_char, init_cust_bal: i64, init_merch_bal: i64, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the com proof
|
||||
let com_result: ResultSerdeType<bidirectional::Commitment<Bls12>> = deserialize_result_object(ser_com);
|
||||
let com_result: ResultSerdeType<bidirectional::Commitment<CURVE>> = deserialize_result_object(ser_com);
|
||||
let com = handle_errors!(com_result);
|
||||
|
||||
// Deserialize the com proof
|
||||
let com_proof_result: ResultSerdeType<bidirectional::CommitmentProof<Bls12>> = deserialize_result_object(ser_com_proof);
|
||||
let com_proof_result: ResultSerdeType<bidirectional::CommitmentProof<CURVE>> = deserialize_result_object(ser_com_proof);
|
||||
let com_proof = handle_errors!(com_proof_result);
|
||||
|
||||
// Deserialize the merchant state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<Bls12>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
// Deserialize the pk_c
|
||||
let channel_id_result: ResultSerdeType<<Bls12 as ScalarEngine>::Fr> = deserialize_result_object(ser_channel_id);
|
||||
let channel_id_result: ResultSerdeType<<CURVE as ScalarEngine>::Fr> = deserialize_result_object(ser_channel_id);
|
||||
let channel_id_fr = handle_errors!(channel_id_result);
|
||||
|
||||
let close_token = bolt_try!(bidirectional::establish_merchant_issue_close_token(rng, &channel_state, &com, &com_proof, &channel_id_fr, init_cust_bal, init_merch_bal, &merch_state));
|
||||
|
@ -189,18 +183,18 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_establish_merchant_issue_pay_token(ser_channel_state: *mut c_char, ser_com: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_establish_merchant_issue_pay_token(ser_channel_state: *mut c_char, ser_com: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the commitment
|
||||
let com_result: ResultSerdeType<bidirectional::Commitment<Bls12>> = deserialize_result_object(ser_com);
|
||||
let com_result: ResultSerdeType<bidirectional::Commitment<CURVE>> = deserialize_result_object(ser_com);
|
||||
let com = handle_errors!(com_result);
|
||||
|
||||
// Deserialize the merchant state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<Bls12>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
let pay_token = bidirectional::establish_merchant_issue_pay_token(rng, &channel_state, &com, &merch_state);
|
||||
|
@ -211,17 +205,17 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_verify_close_token(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_verify_close_token(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let mut channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<Bls12>> = deserialize_result_object(ser_customer_state);
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_customer_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Deserialize the close token
|
||||
let close_result: ResultSerdeType<bidirectional::Signature<Bls12>> = deserialize_result_object(ser_close_token);
|
||||
let close_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_close_token);
|
||||
let close_token = handle_errors!(close_result);
|
||||
|
||||
let is_close_token_valid = cust_state.verify_close_token(&mut channel_state, &close_token);
|
||||
|
@ -235,17 +229,17 @@ pub mod ffishim {
|
|||
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_establish_customer_final(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, ser_pay_token: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_establish_customer_final(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, ser_pay_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let mut channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<Bls12>> = deserialize_result_object(ser_customer_state);
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_customer_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Deserialize the custdata
|
||||
let pay_token_result: ResultSerdeType<bidirectional::Signature<Bls12>> = deserialize_result_object(ser_pay_token);
|
||||
let pay_token_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_pay_token);
|
||||
let pay_token = handle_errors!(pay_token_result);
|
||||
|
||||
let is_channel_established = bidirectional::establish_customer_final(&mut channel_state, &mut cust_state, &pay_token);
|
||||
|
@ -260,14 +254,14 @@ pub mod ffishim {
|
|||
// PAY
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_pay_generate_payment_proof(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, amount: i64) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_pay_generate_payment_proof(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, amount: i64) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<Bls12>> = deserialize_result_object(ser_customer_state);
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_customer_state);
|
||||
let cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Generate the payment proof
|
||||
|
@ -280,18 +274,18 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_pay_verify_payment_proof(ser_channel_state: *mut c_char, ser_pay_proof: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_pay_verify_payment_proof(ser_channel_state: *mut c_char, ser_pay_proof: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the payment proof
|
||||
let payment_result: ResultSerdeType<bidirectional::Payment<Bls12>> = deserialize_result_object(ser_pay_proof);
|
||||
let payment_result: ResultSerdeType<bidirectional::Payment<CURVE>> = deserialize_result_object(ser_pay_proof);
|
||||
let payment = handle_errors!(payment_result);
|
||||
|
||||
// Deserialize the merch state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<Bls12>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let mut merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
let close_token = bidirectional::verify_payment_proof(rng, &channel_state, &payment, &mut merch_state);
|
||||
|
@ -302,21 +296,21 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_pay_verify_multiple_payment_proofs(ser_channel_state: *mut c_char, ser_sender_pay_proof: *mut c_char, ser_receiver_pay_proof: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_pay_verify_multiple_payment_proofs(ser_channel_state: *mut c_char, ser_sender_pay_proof: *mut c_char, ser_receiver_pay_proof: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the payment proofs
|
||||
let sender_payment_result: ResultSerdeType<bidirectional::Payment<Bls12>> = deserialize_result_object(ser_sender_pay_proof);
|
||||
let sender_payment_result: ResultSerdeType<bidirectional::Payment<CURVE>> = deserialize_result_object(ser_sender_pay_proof);
|
||||
let sender_payment = handle_errors!(sender_payment_result);
|
||||
|
||||
let receiver_payment_result: ResultSerdeType<bidirectional::Payment<Bls12>> = deserialize_result_object(ser_receiver_pay_proof);
|
||||
let receiver_payment_result: ResultSerdeType<bidirectional::Payment<CURVE>> = deserialize_result_object(ser_receiver_pay_proof);
|
||||
let receiver_payment = handle_errors!(receiver_payment_result);
|
||||
|
||||
// Deserialize the merch state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<Bls12>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let mut merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
let close_token_result = bidirectional::verify_multiple_payment_proofs(rng, &channel_state, &sender_payment, &receiver_payment, &mut merch_state);
|
||||
|
@ -329,21 +323,21 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_pay_generate_revoke_token(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char, ser_new_cust_state: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_pay_generate_revoke_token(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char, ser_new_cust_state: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<Bls12>> = deserialize_result_object(ser_cust_state);
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_cust_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let new_cust_state_result: ResultSerdeType<bidirectional::CustomerState<Bls12>> = deserialize_result_object(ser_new_cust_state);
|
||||
let new_cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_new_cust_state);
|
||||
let new_cust_state = handle_errors!(new_cust_state_result);
|
||||
|
||||
// Deserialize the close token
|
||||
let close_token_result: ResultSerdeType<bidirectional::Signature<Bls12>> = deserialize_result_object(ser_close_token);
|
||||
let close_token_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_close_token);
|
||||
let close_token = handle_errors!(close_token_result);
|
||||
|
||||
let revoke_token = bidirectional::generate_revoke_token(&channel_state, &mut cust_state, new_cust_state, &close_token);
|
||||
|
@ -354,13 +348,13 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_pay_verify_revoke_token(ser_revoke_token: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_pay_verify_revoke_token(ser_revoke_token: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the revoke token
|
||||
let revoke_token_result: ResultSerdeType<bidirectional::RevokeToken> = deserialize_result_object(ser_revoke_token);
|
||||
let revoke_token = handle_errors!(revoke_token_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<Bls12>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let mut merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
// send revoke token and get pay-token in response
|
||||
|
@ -374,7 +368,7 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_pay_verify_multiple_revoke_tokens(ser_sender_revoke_token: *mut c_char, ser_receiver_revoke_token: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_pay_verify_multiple_revoke_tokens(ser_sender_revoke_token: *mut c_char, ser_receiver_revoke_token: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the revoke tokens
|
||||
let sender_revoke_token_result: ResultSerdeType<bidirectional::RevokeToken> = deserialize_result_object(ser_sender_revoke_token);
|
||||
let sender_revoke_token = handle_errors!(sender_revoke_token_result);
|
||||
|
@ -383,7 +377,7 @@ pub mod ffishim {
|
|||
let receiver_revoke_token = handle_errors!(receiver_revoke_token_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<Bls12>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let mut merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
// send revoke token and get pay-token in response
|
||||
|
@ -399,17 +393,17 @@ pub mod ffishim {
|
|||
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_pay_verify_payment_token(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char, ser_pay_token: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_pay_verify_payment_token(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char, ser_pay_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<Bls12>> = deserialize_result_object(ser_cust_state);
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_cust_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Deserialize the pay token
|
||||
let pay_token_result: ResultSerdeType<bidirectional::Signature<Bls12>> = deserialize_result_object(ser_pay_token);
|
||||
let pay_token_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_pay_token);
|
||||
let pay_token = handle_errors!(pay_token_result);
|
||||
|
||||
// verify the pay token and update internal state
|
||||
|
@ -423,13 +417,13 @@ pub mod ffishim {
|
|||
// CLOSE
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_customer_close(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_customer_close(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<Bls12>> = deserialize_result_object(ser_cust_state);
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_cust_state);
|
||||
let cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
let cust_close = bidirectional::customer_close(&channel_state, &cust_state);
|
||||
|
@ -439,21 +433,21 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_merchant_close(ser_channel_state: *mut c_char, ser_channel_token: *mut c_char, ser_address: *const c_char, ser_cust_close: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_merchant_close(ser_channel_state: *mut c_char, ser_channel_token: *mut c_char, ser_address: *const c_char, ser_cust_close: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<Bls12>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<Bls12>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the customer close structure
|
||||
let cust_close_result: ResultSerdeType<bidirectional::ChannelcloseC<Bls12>> = deserialize_result_object(ser_cust_close);
|
||||
let cust_close_result: ResultSerdeType<bidirectional::ChannelcloseC<CURVE>> = deserialize_result_object(ser_cust_close);
|
||||
let cust_close = handle_errors!(cust_close_result);
|
||||
|
||||
// Deserialize the merch state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<Bls12>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
// Deserialize the destination address as a string
|
||||
|
@ -475,9 +469,9 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_wtp_verify_cust_close_message(ser_channel_token: *mut c_char, ser_wpk: *mut c_char, ser_close_msg: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_wtp_verify_cust_close_message(ser_channel_token: *mut c_char, ser_wpk: *mut c_char, ser_close_msg: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<Bls12>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the wpk
|
||||
|
@ -485,11 +479,11 @@ pub mod ffishim {
|
|||
let wpk = handle_errors!(wpk_result);
|
||||
|
||||
// Deserialize the close wallet
|
||||
let close_msg_result: ResultSerdeType<bidirectional::Wallet<Bls12>> = deserialize_result_object(ser_close_msg);
|
||||
let close_msg_result: ResultSerdeType<bidirectional::Wallet<CURVE>> = deserialize_result_object(ser_close_msg);
|
||||
let close_msg = handle_errors!(close_msg_result);
|
||||
|
||||
// Deserialize the close token
|
||||
let close_token_result: ResultSerdeType<bidirectional::Signature<Bls12>> = deserialize_result_object(ser_close_token);
|
||||
let close_token_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_close_token);
|
||||
let close_token = handle_errors!(close_token_result);
|
||||
|
||||
// check the signatures
|
||||
|
@ -500,9 +494,9 @@ pub mod ffishim {
|
|||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bidirectional_wtp_verify_merch_close_message(ser_channel_token: *mut c_char, ser_wpk: *mut c_char, ser_merch_close: *mut c_char) -> *mut c_char {
|
||||
pub extern fn ffishim_bls12_wtp_verify_merch_close_message(ser_channel_token: *mut c_char, ser_wpk: *mut c_char, ser_merch_close: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<Bls12>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the wpk
|
||||
|
|
|
@ -0,0 +1,511 @@
|
|||
#[no_mangle]
|
||||
pub mod ffishim_bn256 {
|
||||
extern crate libc;
|
||||
|
||||
use bidirectional;
|
||||
use ff::ScalarEngine;
|
||||
use pairing::bn256::Bn256;
|
||||
|
||||
use serde::Deserialize;
|
||||
|
||||
use libc::c_char;
|
||||
use std::ffi::{CStr, CString};
|
||||
use std::str;
|
||||
|
||||
fn error_message(s: String) -> *mut c_char {
|
||||
let ser = ["{\'error\':\'", &s, "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
macro_rules! bolt_try {
|
||||
($e:expr) => (match $e {
|
||||
Ok(val) => val.unwrap(),
|
||||
Err(err) => return error_message(err),
|
||||
});
|
||||
}
|
||||
|
||||
macro_rules! handle_errors {
|
||||
($e:expr) => (match $e {
|
||||
Ok(val) => val,
|
||||
Err(err) => return error_message(err.to_string()),
|
||||
});
|
||||
}
|
||||
|
||||
pub type ResultSerdeType<T> = Result<T, serde_json::error::Error>;
|
||||
type CURVE = Bn256;
|
||||
|
||||
fn deserialize_result_object<'a, T>(serialized: *mut c_char) -> ResultSerdeType<T>
|
||||
where
|
||||
T: Deserialize<'a>,
|
||||
{
|
||||
let bytes = unsafe { CStr::from_ptr(serialized).to_bytes() };
|
||||
let string: &str = str::from_utf8(bytes).unwrap(); // make sure the bytes are UTF-8
|
||||
serde_json::from_str(&string)
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_wtp_check_wpk(ser_wpk: *mut c_char) -> *mut c_char {
|
||||
let wpk_result: ResultSerdeType<secp256k1::PublicKey> = deserialize_result_object(ser_wpk);
|
||||
let _wpk = handle_errors!(wpk_result);
|
||||
|
||||
let res = true;
|
||||
let ser = ["{\'result\':\'", serde_json::to_string(&res).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_channel_setup(channel_name: *const c_char, third_party_support: u32) -> *mut c_char {
|
||||
let bytes = unsafe { CStr::from_ptr(channel_name).to_bytes() };
|
||||
let name: &str = str::from_utf8(bytes).unwrap(); // make sure the bytes are UTF-8
|
||||
|
||||
let mut tps = false;
|
||||
if third_party_support > 1 {
|
||||
tps = true;
|
||||
}
|
||||
let channel_state = bidirectional::ChannelState::<CURVE>::new(name.to_string(), tps);
|
||||
|
||||
let ser = ["{\'channel_state\':\'", serde_json::to_string(&channel_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
// INIT
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_init_merchant(ser_channel_state: *mut c_char, name_ptr: *const c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let mut channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
let bytes = unsafe { CStr::from_ptr(name_ptr).to_bytes() };
|
||||
let name: &str = str::from_utf8(bytes).unwrap(); // make sure the bytes are UTF-8
|
||||
|
||||
let (channel_token, merch_state, channel_state) = bidirectional::init_merchant(rng, &mut channel_state, name);
|
||||
|
||||
let ser = ["{\'channel_token\':\'", serde_json::to_string(&channel_token).unwrap().as_str(), "\', \'merch_state\':\'", serde_json::to_string(&merch_state).unwrap().as_str(), "\', \'channel_state\':\'", serde_json::to_string(&channel_state).unwrap().as_str(), "\'}"].concat();
|
||||
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_init_customer(ser_channel_token: *mut c_char, balance_customer: i64, balance_merchant: i64, name_ptr: *const c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let mut channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the name
|
||||
let bytes = unsafe { CStr::from_ptr(name_ptr).to_bytes() };
|
||||
let name: &str = str::from_utf8(bytes).unwrap(); // make sure the bytes are UTF-8
|
||||
|
||||
// We change the channel state
|
||||
let cust_state = bidirectional::init_customer(rng, &mut channel_token, balance_customer, balance_merchant, name);
|
||||
let ser = ["{\'cust_state\':\'", serde_json::to_string(&cust_state).unwrap().as_str(), "\', \'channel_token\':\'", serde_json::to_string(&channel_token).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
// ESTABLISH
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_establish_customer_generate_proof(ser_channel_token: *mut c_char, ser_customer_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let mut channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_customer_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
let (com, com_proof) = bidirectional::establish_customer_generate_proof(rng, &mut channel_token, &mut cust_state);
|
||||
|
||||
let ser = ["{\'cust_state\':\'", serde_json::to_string(&cust_state).unwrap().as_str(),
|
||||
"\', \'channel_token\':\'", serde_json::to_string(&channel_token).unwrap().as_str(),
|
||||
"\', \'com\':\'", serde_json::to_string(&com).unwrap().as_str(),
|
||||
"\', \'com_proof\':\'", serde_json::to_string(&com_proof).unwrap().as_str(),
|
||||
"\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_generate_channel_id(ser_channel_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
let id = channel_token.compute_channel_id();
|
||||
let ser = ["{\'channel_id\':\'", serde_json::to_string(&id).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_establish_merchant_issue_close_token(ser_channel_state: *mut c_char, ser_com: *mut c_char, ser_com_proof: *mut c_char, ser_channel_id: *mut c_char, init_cust_bal: i64, init_merch_bal: i64, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the com proof
|
||||
let com_result: ResultSerdeType<bidirectional::Commitment<CURVE>> = deserialize_result_object(ser_com);
|
||||
let com = handle_errors!(com_result);
|
||||
|
||||
// Deserialize the com proof
|
||||
let com_proof_result: ResultSerdeType<bidirectional::CommitmentProof<CURVE>> = deserialize_result_object(ser_com_proof);
|
||||
let com_proof = handle_errors!(com_proof_result);
|
||||
|
||||
// Deserialize the merchant state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
// Deserialize the pk_c
|
||||
let channel_id_result: ResultSerdeType<<CURVE as ScalarEngine>::Fr> = deserialize_result_object(ser_channel_id);
|
||||
let channel_id_fr = handle_errors!(channel_id_result);
|
||||
|
||||
let close_token = bolt_try!(bidirectional::establish_merchant_issue_close_token(rng, &channel_state, &com, &com_proof, &channel_id_fr, init_cust_bal, init_merch_bal, &merch_state));
|
||||
|
||||
let ser = ["{\'close_token\':\'", serde_json::to_string(&close_token).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_establish_merchant_issue_pay_token(ser_channel_state: *mut c_char, ser_com: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the commitment
|
||||
let com_result: ResultSerdeType<bidirectional::Commitment<CURVE>> = deserialize_result_object(ser_com);
|
||||
let com = handle_errors!(com_result);
|
||||
|
||||
// Deserialize the merchant state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
let pay_token = bidirectional::establish_merchant_issue_pay_token(rng, &channel_state, &com, &merch_state);
|
||||
|
||||
let ser = ["{\'pay_token\':\'", serde_json::to_string(&pay_token).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_verify_close_token(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let mut channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_customer_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Deserialize the close token
|
||||
let close_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_close_token);
|
||||
let close_token = handle_errors!(close_result);
|
||||
|
||||
let is_close_token_valid = cust_state.verify_close_token(&mut channel_state, &close_token);
|
||||
|
||||
let ser = ["{\'cust_state\':\'", serde_json::to_string(&cust_state).unwrap().as_str(),
|
||||
"\', \'is_token_valid\':\'", serde_json::to_string(&is_close_token_valid).unwrap().as_str(),
|
||||
"\', \'channel_state\':\'", serde_json::to_string(&channel_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_establish_customer_final(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, ser_pay_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let mut channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_customer_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Deserialize the custdata
|
||||
let pay_token_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_pay_token);
|
||||
let pay_token = handle_errors!(pay_token_result);
|
||||
|
||||
let is_channel_established = bidirectional::establish_customer_final(&mut channel_state, &mut cust_state, &pay_token);
|
||||
|
||||
let ser = ["{\'cust_state\':\'", serde_json::to_string(&cust_state).unwrap().as_str(),
|
||||
"\', \'is_established\':\'", serde_json::to_string(&is_channel_established).unwrap().as_str(),
|
||||
"\', \'channel_state\':\'", serde_json::to_string(&channel_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
// PAY
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_pay_generate_payment_proof(ser_channel_state: *mut c_char, ser_customer_state: *mut c_char, amount: i64) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_customer_state);
|
||||
let cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Generate the payment proof
|
||||
let (payment, new_cust_state) = bidirectional::generate_payment_proof(rng, &channel_state, &cust_state, amount);
|
||||
// Serialize the results and return to caller
|
||||
let ser = ["{\'payment\':\'", serde_json::to_string(&payment).unwrap().as_str(),
|
||||
"\', \'cust_state\':\'", serde_json::to_string(&new_cust_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_pay_verify_payment_proof(ser_channel_state: *mut c_char, ser_pay_proof: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the payment proof
|
||||
let payment_result: ResultSerdeType<bidirectional::Payment<CURVE>> = deserialize_result_object(ser_pay_proof);
|
||||
let payment = handle_errors!(payment_result);
|
||||
|
||||
// Deserialize the merch state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let mut merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
let close_token = bidirectional::verify_payment_proof(rng, &channel_state, &payment, &mut merch_state);
|
||||
let ser = ["{\'close_token\':\'", serde_json::to_string(&close_token).unwrap().as_str(),
|
||||
"\', \'merch_state\':\'", serde_json::to_string(&merch_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_pay_verify_multiple_payment_proofs(ser_channel_state: *mut c_char, ser_sender_pay_proof: *mut c_char, ser_receiver_pay_proof: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
let rng = &mut rand::thread_rng();
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the payment proofs
|
||||
let sender_payment_result: ResultSerdeType<bidirectional::Payment<CURVE>> = deserialize_result_object(ser_sender_pay_proof);
|
||||
let sender_payment = handle_errors!(sender_payment_result);
|
||||
|
||||
let receiver_payment_result: ResultSerdeType<bidirectional::Payment<CURVE>> = deserialize_result_object(ser_receiver_pay_proof);
|
||||
let receiver_payment = handle_errors!(receiver_payment_result);
|
||||
|
||||
// Deserialize the merch state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let mut merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
let close_token_result = bidirectional::verify_multiple_payment_proofs(rng, &channel_state, &sender_payment, &receiver_payment, &mut merch_state);
|
||||
let (sender_close_token, receiver_cond_close_token) = handle_errors!(close_token_result).unwrap();
|
||||
let ser = ["{\'sender_close_token\':\'", serde_json::to_string(&sender_close_token).unwrap().as_str(),
|
||||
"\', \'receiver_cond_close_token\':\'", serde_json::to_string(&receiver_cond_close_token).unwrap().as_str(),
|
||||
"\', \'merch_state\':\'", serde_json::to_string(&merch_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_pay_generate_revoke_token(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char, ser_new_cust_state: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_cust_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let new_cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_new_cust_state);
|
||||
let new_cust_state = handle_errors!(new_cust_state_result);
|
||||
|
||||
// Deserialize the close token
|
||||
let close_token_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_close_token);
|
||||
let close_token = handle_errors!(close_token_result);
|
||||
|
||||
let revoke_token = bidirectional::generate_revoke_token(&channel_state, &mut cust_state, new_cust_state, &close_token);
|
||||
let ser = ["{\'revoke_token\':\'", serde_json::to_string(&revoke_token).unwrap().as_str(),
|
||||
"\', \'cust_state\':\'", serde_json::to_string(&cust_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_pay_verify_revoke_token(ser_revoke_token: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the revoke token
|
||||
let revoke_token_result: ResultSerdeType<bidirectional::RevokeToken> = deserialize_result_object(ser_revoke_token);
|
||||
let revoke_token = handle_errors!(revoke_token_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let mut merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
// send revoke token and get pay-token in response
|
||||
let pay_token_result = bidirectional::verify_revoke_token(&revoke_token, &mut merch_state);
|
||||
let pay_token = handle_errors!(pay_token_result);
|
||||
|
||||
let ser = ["{\'pay_token\':\'", serde_json::to_string(&pay_token.unwrap()).unwrap().as_str(),
|
||||
"\', \'merch_state\':\'", serde_json::to_string(&merch_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_pay_verify_multiple_revoke_tokens(ser_sender_revoke_token: *mut c_char, ser_receiver_revoke_token: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the revoke tokens
|
||||
let sender_revoke_token_result: ResultSerdeType<bidirectional::RevokeToken> = deserialize_result_object(ser_sender_revoke_token);
|
||||
let sender_revoke_token = handle_errors!(sender_revoke_token_result);
|
||||
|
||||
let receiver_revoke_token_result: ResultSerdeType<bidirectional::RevokeToken> = deserialize_result_object(ser_receiver_revoke_token);
|
||||
let receiver_revoke_token = handle_errors!(receiver_revoke_token_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let mut merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
// send revoke token and get pay-token in response
|
||||
let pay_token_result = bidirectional::verify_multiple_revoke_tokens(&sender_revoke_token, &receiver_revoke_token, &mut merch_state);
|
||||
let (sender_pay_token, receiver_pay_token) = handle_errors!(pay_token_result).unwrap();
|
||||
|
||||
let ser = ["{\'sender_pay_token\':\'", serde_json::to_string(&sender_pay_token).unwrap().as_str(),
|
||||
"\', \'receiver_pay_token\':\'", serde_json::to_string(&receiver_pay_token).unwrap().as_str(),
|
||||
"\', \'merch_state\':\'", serde_json::to_string(&merch_state).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_pay_verify_payment_token(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char, ser_pay_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_cust_state);
|
||||
let mut cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
// Deserialize the pay token
|
||||
let pay_token_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_pay_token);
|
||||
let pay_token = handle_errors!(pay_token_result);
|
||||
|
||||
// verify the pay token and update internal state
|
||||
let is_pay_valid = cust_state.verify_pay_token(&channel_state, &pay_token);
|
||||
let ser = ["{\'cust_state\':\'", serde_json::to_string(&cust_state).unwrap().as_str(),
|
||||
"\', \'is_pay_valid\':\'", serde_json::to_string(&is_pay_valid).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
// CLOSE
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_customer_close(ser_channel_state: *mut c_char, ser_cust_state: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the cust state
|
||||
let cust_state_result: ResultSerdeType<bidirectional::CustomerState<CURVE>> = deserialize_result_object(ser_cust_state);
|
||||
let cust_state = handle_errors!(cust_state_result);
|
||||
|
||||
let cust_close = bidirectional::customer_close(&channel_state, &cust_state);
|
||||
let ser = ["{\'cust_close\':\'", serde_json::to_string(&cust_close).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_merchant_close(ser_channel_state: *mut c_char, ser_channel_token: *mut c_char, ser_address: *const c_char, ser_cust_close: *mut c_char, ser_merch_state: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel state
|
||||
let channel_state_result: ResultSerdeType<bidirectional::ChannelState<CURVE>> = deserialize_result_object(ser_channel_state);
|
||||
let channel_state = handle_errors!(channel_state_result);
|
||||
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the customer close structure
|
||||
let cust_close_result: ResultSerdeType<bidirectional::ChannelcloseC<CURVE>> = deserialize_result_object(ser_cust_close);
|
||||
let cust_close = handle_errors!(cust_close_result);
|
||||
|
||||
// Deserialize the merch state
|
||||
let merch_state_result: ResultSerdeType<bidirectional::MerchantState<CURVE>> = deserialize_result_object(ser_merch_state);
|
||||
let merch_state = handle_errors!(merch_state_result);
|
||||
|
||||
// Deserialize the destination address as a string
|
||||
let ser_addr_bytes = unsafe { CStr::from_ptr(ser_address).to_bytes() };
|
||||
let address: &str = str::from_utf8(ser_addr_bytes).unwrap(); // make sure the bytes are UTF-8
|
||||
|
||||
let option = bidirectional::merchant_close(&channel_state, &channel_token, &cust_close, &merch_state);
|
||||
let keys = match option {
|
||||
Ok(n) => n.unwrap(),
|
||||
Err(err) => return error_message(err),
|
||||
};
|
||||
|
||||
let merch_close: bidirectional::ChannelcloseM = merch_state.sign_revoke_message(address.to_string(), &keys.revoke_token);
|
||||
|
||||
let ser = ["{\'wpk\':\'", serde_json::to_string(&keys.wpk).unwrap().as_str(),
|
||||
"\', \'merch_close\':\'", serde_json::to_string(&merch_close).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_wtp_verify_cust_close_message(ser_channel_token: *mut c_char, ser_wpk: *mut c_char, ser_close_msg: *mut c_char, ser_close_token: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the wpk
|
||||
let wpk_result: ResultSerdeType<secp256k1::PublicKey> = deserialize_result_object(ser_wpk);
|
||||
let wpk = handle_errors!(wpk_result);
|
||||
|
||||
// Deserialize the close wallet
|
||||
let close_msg_result: ResultSerdeType<bidirectional::Wallet<CURVE>> = deserialize_result_object(ser_close_msg);
|
||||
let close_msg = handle_errors!(close_msg_result);
|
||||
|
||||
// Deserialize the close token
|
||||
let close_token_result: ResultSerdeType<bidirectional::Signature<CURVE>> = deserialize_result_object(ser_close_token);
|
||||
let close_token = handle_errors!(close_token_result);
|
||||
|
||||
// check the signatures
|
||||
let token_valid = bidirectional::wtp_verify_cust_close_message(&channel_token, &wpk, &close_msg, &close_token);
|
||||
let ser = ["{\"result\":\"", serde_json::to_string(&token_valid).unwrap().as_str(), "\"}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
pub extern fn ffishim_bn256_wtp_verify_merch_close_message(ser_channel_token: *mut c_char, ser_wpk: *mut c_char, ser_merch_close: *mut c_char) -> *mut c_char {
|
||||
// Deserialize the channel token
|
||||
let channel_token_result: ResultSerdeType<bidirectional::ChannelToken<CURVE>> = deserialize_result_object(ser_channel_token);
|
||||
let channel_token = handle_errors!(channel_token_result);
|
||||
|
||||
// Deserialize the wpk
|
||||
let wpk_result: ResultSerdeType<secp256k1::PublicKey> = deserialize_result_object(ser_wpk);
|
||||
let wpk = handle_errors!(wpk_result);
|
||||
|
||||
// Deserialize the merch close
|
||||
//let revoke_token: secp256k1::Signature = deserialize_object(ser_revoke_token);
|
||||
let merch_close_result: ResultSerdeType<bidirectional::ChannelcloseM> = deserialize_result_object(ser_merch_close);
|
||||
let merch_close = handle_errors!(merch_close_result);
|
||||
|
||||
let revoke_token_valid = bidirectional::wtp_verify_revoke_message(&wpk, &merch_close.revoke.unwrap());
|
||||
let merch_close_valid = bidirectional::wtp_verify_merch_close_message(&channel_token, &merch_close);
|
||||
let token_valid = revoke_token_valid && merch_close_valid;
|
||||
|
||||
let ser = ["{\'result\':\'", serde_json::to_string(&token_valid).unwrap().as_str(), "\'}"].concat();
|
||||
let cser = CString::new(ser).unwrap();
|
||||
cser.into_raw()
|
||||
}
|
||||
}
|
276
src/lib.rs
276
src/lib.rs
|
@ -13,16 +13,15 @@
|
|||
#![allow(non_upper_case_globals)]
|
||||
#![allow(unused_results)]
|
||||
#![allow(missing_docs)]
|
||||
#![feature(exclusive_range_pattern)]
|
||||
|
||||
#![cfg_attr(all(test, feature = "unstable"), feature(test))]
|
||||
#[cfg(all(test, feature = "unstable"))]
|
||||
extern crate test;
|
||||
|
||||
extern crate ff;
|
||||
extern crate pairing;
|
||||
extern crate ff_bl as ff;
|
||||
extern crate pairing_bl as pairing;
|
||||
extern crate rand;
|
||||
extern crate rand_core;
|
||||
// extern crate rand_core;
|
||||
|
||||
extern crate secp256k1;
|
||||
extern crate time;
|
||||
|
@ -32,9 +31,11 @@ extern crate serde;
|
|||
extern crate serde_with;
|
||||
|
||||
extern crate libc;
|
||||
extern crate hex;
|
||||
|
||||
#[cfg(test)]
|
||||
extern crate core;
|
||||
extern crate serde_json;
|
||||
|
||||
pub mod cl;
|
||||
pub mod ccs08;
|
||||
|
@ -44,6 +45,7 @@ pub mod nizk;
|
|||
pub mod util;
|
||||
pub mod wallet;
|
||||
pub mod ffishim;
|
||||
pub mod ffishim_bn256;
|
||||
|
||||
use std::fmt;
|
||||
use std::str;
|
||||
|
@ -159,10 +161,6 @@ pub mod bidirectional {
|
|||
pub signature: secp256k1::Signature,
|
||||
}
|
||||
|
||||
pub fn init() {
|
||||
//sodiumoxide::init();
|
||||
}
|
||||
|
||||
///
|
||||
/// init_merchant - takes as input the public params, merchant balance and keypair.
|
||||
/// Generates merchant data which consists of channel token and merchant state.
|
||||
|
@ -507,6 +505,180 @@ pub mod bidirectional {
|
|||
}
|
||||
}
|
||||
|
||||
pub mod wtp_utils {
|
||||
// Useful routines that simplify the Bolt WTP implementation for Zcash
|
||||
use pairing::bls12_381::Bls12;
|
||||
use ::{util, BoltResult};
|
||||
use cl;
|
||||
use ped92::CSMultiParams;
|
||||
pub use cl::Signature;
|
||||
pub use channels::ChannelToken;
|
||||
pub use wallet::Wallet;
|
||||
use channels::ChannelcloseM;
|
||||
|
||||
const BLS12_381_CHANNEL_TOKEN_LEN: usize = 1074;
|
||||
const BLS12_381_G1_LEN: usize = 48;
|
||||
const BLS12_381_G2_LEN: usize = 96;
|
||||
const SECP256K1_PK_LEN: usize = 33;
|
||||
const ADDRESS_LEN: usize = 33;
|
||||
|
||||
pub fn reconstruct_secp_public_key(pk_bytes: &[u8; SECP256K1_PK_LEN]) -> secp256k1::PublicKey {
|
||||
return secp256k1::PublicKey::from_slice(pk_bytes).unwrap();
|
||||
}
|
||||
|
||||
pub fn reconstruct_secp_signature(sig_bytes: &[u8]) -> secp256k1::Signature {
|
||||
return secp256k1::Signature::from_der(sig_bytes).unwrap();
|
||||
}
|
||||
|
||||
pub fn reconstruct_close_wallet_bls12(channel_token: &ChannelToken<Bls12>, wpk: &secp256k1::PublicKey, cust_bal: u32, merch_bal: u32) -> Wallet<Bls12> {
|
||||
let channelId = channel_token.compute_channel_id();
|
||||
let wpk_h = util::hash_pubkey_to_fr::<Bls12>(&wpk);
|
||||
let close = util::hash_to_fr::<Bls12>(String::from("close").into_bytes());
|
||||
|
||||
return Wallet {
|
||||
channelId, wpk: wpk_h, bc: cust_bal as i64, bm: merch_bal as i64, close: Some(close)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn reconstruct_signature_bls12(sig: &Vec<u8>) -> BoltResult<cl::Signature<Bls12>> {
|
||||
if (sig.len() != BLS12_381_G1_LEN * 2) {
|
||||
return Err(String::from("signature has invalid length"));
|
||||
}
|
||||
|
||||
let mut cur_index = 0;
|
||||
let mut end_index = BLS12_381_G1_LEN;
|
||||
let ser_cl_h = sig[cur_index .. end_index].to_vec();
|
||||
let str_cl_h = util::encode_as_hexstring(&ser_cl_h);
|
||||
let h = str_cl_h.as_bytes();
|
||||
|
||||
cur_index = end_index;
|
||||
end_index += BLS12_381_G1_LEN;
|
||||
let ser_cl_H = sig[cur_index .. end_index].to_vec();
|
||||
let str_cl_H = util::encode_as_hexstring(&ser_cl_H);
|
||||
let H = str_cl_H.as_bytes();
|
||||
|
||||
let cl_sig = cl::Signature::<Bls12>::from_slice(&h, &H);
|
||||
|
||||
Ok(Some(cl_sig))
|
||||
}
|
||||
|
||||
pub fn reconstruct_channel_token_bls12(channel_token: &Vec<u8>) -> BoltResult<ChannelToken<Bls12>>
|
||||
{
|
||||
// parse pkc, pkm, pkM, mpk and comParams
|
||||
if channel_token.len() != BLS12_381_CHANNEL_TOKEN_LEN {
|
||||
return Err(String::from("could not reconstruct the channel token!"));
|
||||
}
|
||||
|
||||
let num_y_elems = 5;
|
||||
let num_com_params= 6;
|
||||
|
||||
let mut cur_index = 0;
|
||||
let mut end_index = SECP256K1_PK_LEN;
|
||||
let pkc = secp256k1::PublicKey::from_slice(&channel_token[cur_index .. end_index]).unwrap();
|
||||
|
||||
cur_index = end_index;
|
||||
end_index += SECP256K1_PK_LEN;
|
||||
let pkm = secp256k1::PublicKey::from_slice(&channel_token[cur_index .. end_index]).unwrap();
|
||||
|
||||
cur_index = end_index;
|
||||
end_index += BLS12_381_G2_LEN; // pk_M => (X, Y)
|
||||
let ser_cl_x = channel_token[cur_index .. end_index].to_vec();
|
||||
let str_cl_x = util::encode_as_hexstring(&ser_cl_x);
|
||||
let X = str_cl_x.as_bytes();
|
||||
|
||||
let mut Y = Vec::new();
|
||||
for _ in 0 .. num_y_elems {
|
||||
cur_index = end_index;
|
||||
end_index += BLS12_381_G2_LEN;
|
||||
let cl_y = channel_token[cur_index .. end_index].to_vec();
|
||||
let ser_cl_y = util::encode_as_hexstring(&cl_y);
|
||||
let str_cl_y = ser_cl_y.as_bytes();
|
||||
Y.extend(str_cl_y);
|
||||
}
|
||||
let cl_pk= cl::PublicKey::<Bls12>::from_slice(&X, &Y.as_slice(), str_cl_x.len(), num_y_elems);
|
||||
|
||||
cur_index = end_index;
|
||||
end_index += BLS12_381_G1_LEN;
|
||||
let g1 = channel_token[cur_index .. end_index].to_vec();
|
||||
let ser_mpk_g1 = util::encode_as_hexstring(&g1);
|
||||
|
||||
cur_index = end_index;
|
||||
end_index += BLS12_381_G2_LEN;
|
||||
let g2 = channel_token[cur_index .. end_index].to_vec();
|
||||
let ser_mpk_g2 = util::encode_as_hexstring(&g2);
|
||||
|
||||
let ser_g1 = ser_mpk_g1.as_bytes();
|
||||
let ser_g2 = ser_mpk_g2.as_bytes();
|
||||
|
||||
let mpk = cl::PublicParams::<Bls12>::from_slice(&ser_g1, &ser_g2);
|
||||
|
||||
let mut comparams = Vec::new();
|
||||
for _ in 0 .. num_com_params {
|
||||
cur_index = end_index;
|
||||
end_index += BLS12_381_G1_LEN;
|
||||
let com = channel_token[cur_index .. end_index].to_vec();
|
||||
let ser_com = util::encode_as_hexstring(&com);
|
||||
let str_com = ser_com.as_bytes();
|
||||
comparams.extend(str_com);
|
||||
}
|
||||
|
||||
let com_params = CSMultiParams::<Bls12>::from_slice(&comparams.as_slice(), ser_mpk_g1.len(), num_com_params);
|
||||
|
||||
Ok(Some(ChannelToken {
|
||||
pk_c: Some(pkc), pk_m: pkm, cl_pk_m: cl_pk, mpk: mpk, comParams: com_params
|
||||
}))
|
||||
}
|
||||
|
||||
///
|
||||
/// Used in open-channel WTP for validating that a close_token is a valid signature
|
||||
///
|
||||
pub fn wtp_verify_cust_close_message(channel_token: &ChannelToken<Bls12>, wpk: &secp256k1::PublicKey,
|
||||
close_msg: &Wallet<Bls12>, close_token: &cl::Signature<Bls12>) -> bool {
|
||||
// close_msg => <pkc> || <wpk> || <balance-cust> || <balance-merch> || CLOSE
|
||||
// close_token = regular CL signature on close_msg
|
||||
// channel_token => <pk_c, CL_PK_m, pk_m, mpk, comParams>
|
||||
|
||||
// (1) check that channel token and close msg are consistent (e.g., close_msg.channelId == H(channel_token.pk_c) &&
|
||||
let chan_token_cid = channel_token.compute_channel_id(); // util::hash_pubkey_to_fr::<Bls12>(&pk_c);
|
||||
let chan_token_wpk = util::hash_pubkey_to_fr::<Bls12>(&wpk);
|
||||
|
||||
let cid_thesame = (close_msg.channelId == chan_token_cid);
|
||||
// (2) check that wpk matches what's in the close msg
|
||||
let wpk_thesame = (close_msg.wpk == chan_token_wpk);
|
||||
return cid_thesame && wpk_thesame && channel_token.cl_pk_m.verify(&channel_token.mpk, &close_msg.as_fr_vec(), &close_token);
|
||||
}
|
||||
|
||||
pub fn wtp_generate_secp_signature(seckey: &[u8; 32], msg: &[u8; 32]) -> Vec<u8> {
|
||||
let secp = secp256k1::Secp256k1::signing_only();
|
||||
|
||||
let msg = secp256k1::Message::from_slice(msg).unwrap();
|
||||
let seckey = secp256k1::SecretKey::from_slice(seckey).unwrap();
|
||||
let sig = secp.sign(&msg, &seckey);
|
||||
|
||||
// get serialized signature
|
||||
let ser_sig = sig.serialize_der();
|
||||
|
||||
return ser_sig.to_vec();
|
||||
}
|
||||
|
||||
pub fn wtp_verify_secp_signature(pubkey: &secp256k1::PublicKey, hash: &Vec<u8>, sig: &secp256k1::Signature) -> bool {
|
||||
let secp = secp256k1::Secp256k1::verification_only();
|
||||
let msg = secp256k1::Message::from_slice(hash.as_slice()).unwrap();
|
||||
|
||||
return secp.verify(&msg, &sig, &pubkey).is_ok()
|
||||
}
|
||||
|
||||
pub fn reconstruct_secp_channel_close_m(address: &[u8; ADDRESS_LEN], ser_revoke_token: &Vec<u8>, ser_sig: &Vec<u8>) -> ChannelcloseM {
|
||||
let revoke_token = secp256k1::Signature::from_der(&ser_revoke_token.as_slice()).unwrap();
|
||||
let sig = secp256k1::Signature::from_der(&ser_sig.as_slice()).unwrap();
|
||||
ChannelcloseM {
|
||||
address: hex::encode(&address.to_vec()),
|
||||
revoke: Some(revoke_token),
|
||||
signature: sig,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(all(test, feature = "unstable"))]
|
||||
mod benches {
|
||||
use rand::{Rng, thread_rng};
|
||||
|
@ -523,6 +695,7 @@ mod tests {
|
|||
use super::*;
|
||||
use pairing::bls12_381::Bls12;
|
||||
use rand::Rng;
|
||||
use sha2::Digest;
|
||||
|
||||
fn setup_new_channel_helper(channel_state: &mut bidirectional::ChannelState<Bls12>,
|
||||
init_cust_bal: i64, init_merch_bal: i64)
|
||||
|
@ -899,4 +1072,91 @@ mod tests {
|
|||
|
||||
let _des_cw: bidirectional::CustomerState<Bls12> = serde_json::from_str(&serialized_cw).unwrap();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_reconstruct_channel_token() {
|
||||
let _ser_channel_token = "024c252c7e36d0c30ae7c67dabea2168f41b36b85c14d3e180b423fa1a5df0e7ac027df0457901953b9b776f4999d5a1e78\
|
||||
049c0afa4f741d0d3bb7d9711a0f8c0038f4c70072363fe07ffe1450d63205cbaeaafe600ca9001d8bbf8984ce54a9c5e041084779dace7a4cf582906ea4e\
|
||||
493a1368ec7f05e7f89635c555c26e5d0149186095856dc210bef4b8fec03415cd6d1253bdafd0934a20b57ee088fa7ee0bab0668b1aa84c30e856dd685ce\
|
||||
e2a95844cb68504e82fd9dd874cbf6f7ee58155245e97c52625b53f4ca969f48b33c59f0009adc70d1472a303a35ace0d96149c8cdb96f29b6f476b8f4a10\
|
||||
bd430c4658d4e0b5873fcb946a76aa861c6c4c601ab8fb0b9c88d2e8861de2f0dae2bb2a8492db2978ce8f2e509328efbf12384ae2db5c17021d222724a3b\
|
||||
c4b621bf4f32601d555ff2cfc2171adeb2f1bd42c484c1c0a1e5d7d2853c102080680cefc925808b6e3d71b29a93f7e8f5c2eeeeef944b3740feddb24ec2c\
|
||||
17e3db22ee6a7af77e32a9d186bdcc150dd59b0cd92b92b6656cb588dec9d1d07be5e2a319bf37f1120b7c656f78dc6c4064f8d63f590f70cdc0c1746fde6\
|
||||
035eeb9aa90b69ea666ad71b27078ab61573aec60bab80a4e6a8e4d8ce02204f5b7e0131bf24d5df1428e9e571891c6feb1c0a52ba789136b244f13f510c4\
|
||||
f1f0eb4b0a7e675f105f8102c672461da340ebcae1eddd49a009bcf3b199eb2006fab6cf0ccf102b5c6dd45722dc0c27d4b9697f627f1bcbe44f6d96842de\
|
||||
c92877ff23d374964970c3386972a8ae369367907001bcd8bba458b8f29842321a8231f3441054999cb19b2c40409da8216406298e1d41bcaf5ea8a225266\
|
||||
2848d3f810dd369aba5ff684360080aa6f5e9ba61be1331f6bdf8b00d1ec8453637c4b480f6d0c5e5467013aa0e8be1777c370a1988db21d8d3de3f6d79d8\
|
||||
cbe6412f88d39de0cd1bf9e8f9b57ff933f21bef89b5bd3f9a901936568db58cc8326a719bf56438bbcab659a20ea5c0342eb9f072f105303c90de3b3b865\
|
||||
66155899d05d00396cfae74ac0526f0dd30c33e0c6790f3f8119dac12fb6f870b9a317afa94cd624b88ede30d49d2373b58453637c4b480f6d0c5e5467013\
|
||||
aa0e8be1777c370a1988db21d8d3de3f6d79d8cbe6412f88d39de0cd1bf9e8f9b57ffa397625c859a63e2c6e42486c4f76f306d484cce151f8614f87506e9\
|
||||
9c871521dd244bfeb380481aed8df823a507c7a3ad367c1797fc6efa089f929729e7d48bfa9c60860fbb212918bb91d8c6aa523046bdf208c95fa5a0fb86a\
|
||||
1e46f92e0e5893e136b74d38e106fa990590598932a4e2458034cea22337c6f365bcb5cab59ceea03d7a9f7821ea432e262877ef0128cb73d8733c3961762\
|
||||
26acb6b3de132c803be39a4e803cbc5a4670cb6169583fa899146fab0227dc2ae167393f96f3b8b31e015af1c305de3a07f52408e9c52495c2458ea05c7a3\
|
||||
71dc14f3b1d6a646ed7cc0ca9417d8bde6efc1ac300d8e28f";
|
||||
let ser_channel_token = hex::decode(_ser_channel_token).unwrap();
|
||||
|
||||
let option_ct = wtp_utils::reconstruct_channel_token_bls12(&ser_channel_token);
|
||||
let channel_token = match option_ct {
|
||||
Ok(n) => n.unwrap(),
|
||||
Err(e) => panic!("Error reconstructing compact rep of channel token: {}", e)
|
||||
};
|
||||
|
||||
let channelId = channel_token.compute_channel_id();
|
||||
|
||||
let original_channelId = "[\"0744645c9cbbf4e47f456fa05e2c6888a59f688641d25b2607610ce03b4ae20c\"]";
|
||||
let computed_channelId = serde_json::to_string(&channelId).unwrap();
|
||||
|
||||
println!("channel ID: {}", channelId);
|
||||
println!("pkc: {:?}", channel_token.pk_c.unwrap());
|
||||
println!("pkm: {:?}", channel_token.pk_m);
|
||||
|
||||
assert_eq!(original_channelId, computed_channelId);
|
||||
|
||||
// reconstruct signature
|
||||
let _ser_signature = "93f26490b4576c38dfb8dceae547f4b49aeb945ecc9cccc528c39068c78177bda68aaf45743f09c48ad99b6007fe415b\
|
||||
aee9eafd51cfdb0dc567a5d152bc37861727e85088b417cf3ff57c108d0156eee56aff810f1e5f9e76cd6a3590d6db5e";
|
||||
let ser_signature = hex::decode(_ser_signature).unwrap();
|
||||
|
||||
let option_sig = wtp_utils::reconstruct_signature_bls12(&ser_signature);
|
||||
|
||||
let sig = match option_sig {
|
||||
Ok(n) => n.unwrap(),
|
||||
Err(e) => panic!("Error reconstructing compact rep of signature: {}", e)
|
||||
};
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_reconstruct_secp_sig() {
|
||||
let _ser_sig = "3044022064650285b55624f1f64b2c75e76589fa4b1033dabaa7ff50ff026e1dc038279202204ca696e0a829687c87171e8e5dab17069be248ff2595fd9607f3346dadcb579f";
|
||||
let ser_sig = hex::decode(_ser_sig).unwrap();
|
||||
|
||||
let signature = wtp_utils::reconstruct_secp_signature(ser_sig.as_slice());
|
||||
assert_eq!(format!("{:?}", signature), _ser_sig);
|
||||
|
||||
let sk = hex::decode("81361b9bc2f67524dcc59b980dc8b06aadb77db54f6968d2af76ecdb612e07e4").unwrap();
|
||||
let msg = "hello world!";
|
||||
let mut sha256 = sha2::Sha256::new();
|
||||
sha256.input(msg);
|
||||
let mut hash = [0u8; 32];
|
||||
hash.copy_from_slice(&sha256.result());
|
||||
|
||||
let mut seckey = [0u8; 32];
|
||||
seckey.copy_from_slice(sk.as_slice());
|
||||
let sig = wtp_utils::wtp_generate_secp_signature(&seckey, &hash);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_reconstruct_channel_close_m() {
|
||||
let mut address = [0u8; 33];
|
||||
let address_slice = hex::decode("0a1111111111111111111111111111111111111111111111111111111111111111").unwrap();
|
||||
address.copy_from_slice(address_slice.as_slice());
|
||||
|
||||
let channelClose = wtp_utils::reconstruct_secp_channel_close_m(&address,
|
||||
&hex::decode("3044022041932b376fe2c5e9e9ad0a3804e2290c3bc40617ea4f7b913be858dbcc3760b50220429d6eb1aabbd4135db4e0776c0b768af844b0af44f2f8f9da5a65e8541b4e9f").unwrap(),
|
||||
&hex::decode("3045022100e76653c5f8cb4c2f39efc7c5450d4f68ef3d84d482305534f5dfc310095a3124022003c4651ce1305cffe5e483ab99925cc4c9c5df2b5449bb18a51d52b21d789716").unwrap());
|
||||
|
||||
assert_eq!(channelClose.address, "0a1111111111111111111111111111111111111111111111111111111111111111");
|
||||
assert_eq!(format!("{:?}", channelClose.revoke.unwrap()), "3044022041932b376fe2c5e9e9ad0a3804e2290c3bc40617ea4f7b913be858dbcc3760b50220429d6eb1aabbd4135db4e0776c0b768af844b0af44f2f8f9da5a65e8541b4e9f");
|
||||
assert_eq!(format!("{:?}", channelClose.signature), "3045022100e76653c5f8cb4c2f39efc7c5450d4f68ef3d84d482305534f5dfc310095a3124022003c4651ce1305cffe5e483ab99925cc4c9c5df2b5449bb18a51d52b21d789716");
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,3 @@
|
|||
extern crate pairing;
|
||||
extern crate rand;
|
||||
|
||||
use super::*;
|
||||
use rand::Rng;
|
||||
use cl::{Signature, PublicParams, setup, BlindKeyPair, SignatureProof, BlindPublicKey};
|
||||
|
|
56
src/ped92.rs
56
src/ped92.rs
|
@ -1,5 +1,5 @@
|
|||
// ped92.rs
|
||||
use rand::Rng;
|
||||
use rand::{Rng, AsByteSliceMut};
|
||||
use pairing::{Engine, CurveProjective};
|
||||
use ff::{Rand, Field, PrimeField};
|
||||
use std::fmt;
|
||||
|
@ -40,6 +40,24 @@ impl<E: Engine> PartialEq for CSMultiParams<E> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<E: Engine> CSMultiParams<E> {
|
||||
pub fn from_slice<'de>(ser_gs: &'de [u8], g_len: usize, num_elems: usize) -> Self
|
||||
where <E as pairing::Engine>::G1: serde::Deserialize<'de>
|
||||
{
|
||||
let mut pub_bases: Vec<E::G1> = Vec::new();
|
||||
let mut start_pos = 0;
|
||||
let mut end_pos = g_len;
|
||||
for _ in 0 .. num_elems {
|
||||
let g: E::G1 = serde_json::from_slice(&ser_gs[start_pos .. end_pos]).unwrap();
|
||||
start_pos = end_pos;
|
||||
end_pos += g_len;
|
||||
pub_bases.push(g);
|
||||
}
|
||||
|
||||
return CSMultiParams { pub_bases};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
impl<E: Engine> fmt::Display for CSMultiParams<E> {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
|
@ -369,5 +387,39 @@ mod tests {
|
|||
assert_eq!(proof.verify_proof(&comParams, &com.c, &challenge, None), true);
|
||||
}
|
||||
|
||||
// add tests for extend/remove commits dynamically
|
||||
#[test]
|
||||
fn test_cs_multiparam_serialization() {
|
||||
|
||||
let mut vec: Vec<u8> = Vec::new();
|
||||
let bin_g1= vec![132, 83, 99, 124, 75, 72, 15, 109, 12, 94, 84, 103, 1, 58, 160, 232, 190, 23, 119, 195, 112, 161, 152, 141, 178, 29, 141, 61, 227, 246, 215, 157, 140, 190, 100, 18, 248, 141, 57, 222, 12, 209, 191, 158, 143, 155, 87, 255];
|
||||
let bin_g2 = vec![140, 16, 244, 244, 135, 28, 18, 94, 46, 64, 233, 195, 218, 147, 238, 170, 46, 164, 50, 92, 234, 117, 61, 158, 64, 226, 153, 38, 127, 168, 49, 125, 177, 183, 74, 164, 138, 128, 168, 84, 137, 67, 21, 179, 124, 88, 194, 239];
|
||||
let bin_g3 = vec![147, 174, 242, 238, 231, 127, 9, 120, 16, 9, 191, 238, 60, 57, 106, 34, 198, 62, 28, 183, 77, 170, 27, 116, 36, 75, 242, 26, 242, 23, 213, 31, 186, 21, 141, 219, 59, 104, 247, 118, 56, 95, 183, 124, 103, 83, 93, 154];
|
||||
|
||||
let ser_g1 = util::encode_as_hexstring(&bin_g1);
|
||||
let ser_g2 = util::encode_as_hexstring(&bin_g2);
|
||||
let ser_g3 = util::encode_as_hexstring(&bin_g3);
|
||||
|
||||
let str_g1 = ser_g1.as_bytes();
|
||||
let str_g2 = ser_g2.as_bytes();
|
||||
let str_g3 = ser_g3.as_bytes();
|
||||
|
||||
vec.extend(str_g1);
|
||||
vec.extend(str_g2);
|
||||
vec.extend(str_g3);
|
||||
|
||||
let rec_csparams = CSMultiParams::<Bls12>::from_slice(&vec.as_slice(), str_g1.len(), 3);
|
||||
println!("CS params: {:?}", rec_csparams.pub_bases);
|
||||
|
||||
let ser_cs = serde_json::to_string(&rec_csparams).unwrap();
|
||||
|
||||
println!("Serialized: {:}", ser_cs);
|
||||
let rec_g1_str = serde_json::to_string(&rec_csparams.pub_bases[0]).unwrap();
|
||||
assert_eq!(rec_g1_str, "\"8453637c4b480f6d0c5e5467013aa0e8be1777c370a1988db21d8d3de3f6d79d8cbe6412f88d39de0cd1bf9e8f9b57ff\"");
|
||||
|
||||
let rec_g2_str = serde_json::to_string(&rec_csparams.pub_bases[1]).unwrap();
|
||||
assert_eq!(rec_g2_str, "\"8c10f4f4871c125e2e40e9c3da93eeaa2ea4325cea753d9e40e299267fa8317db1b74aa48a80a854894315b37c58c2ef\"");
|
||||
|
||||
let rec_g3_str = serde_json::to_string(&rec_csparams.pub_bases[2]).unwrap();
|
||||
assert_eq!(rec_g3_str, "\"93aef2eee77f09781009bfee3c396a22c63e1cb74daa1b74244bf21af217d51fba158ddb3b68f776385fb77c67535d9a\"");
|
||||
}
|
||||
}
|
||||
|
|
30
src/util.rs
30
src/util.rs
|
@ -24,6 +24,12 @@ pub fn is_vec_g2_equal<E: Engine>(a: &Vec<E::G2>, b: &Vec<E::G2>) -> bool {
|
|||
.all(|(a, b)| a == b)
|
||||
}
|
||||
|
||||
pub fn encode_as_hexstring(bytes: &Vec<u8>) -> String {
|
||||
let mut ser_hex = hex::encode(bytes);
|
||||
ser_hex.insert(0, '"');
|
||||
ser_hex.push('"');
|
||||
return ser_hex;
|
||||
}
|
||||
|
||||
pub fn hash_g1_to_fr<E: Engine>(x: &Vec<E::G1>) -> E::Fr {
|
||||
let mut x_vec: Vec<u8> = Vec::new();
|
||||
|
@ -39,7 +45,7 @@ pub fn hash_g2_to_fr<E: Engine>(x: &E::G2) -> E::Fr {
|
|||
hash_to_fr::<E>(x_vec)
|
||||
}
|
||||
|
||||
pub fn fmt_bytes_to_int(bytearray: [u8; 64]) -> String {
|
||||
pub fn fmt_bytes_to_int(bytearray: [u8; 32]) -> String {
|
||||
let mut result: String = "".to_string();
|
||||
for byte in bytearray.iter() {
|
||||
// Decide if you want upper- or lowercase results,
|
||||
|
@ -55,12 +61,13 @@ pub fn fmt_bytes_to_int(bytearray: [u8; 64]) -> String {
|
|||
return s;
|
||||
}
|
||||
|
||||
|
||||
pub fn compute_the_hash<E: Engine>(bytes: &Vec<u8>) -> E::Fr {
|
||||
let mut hasher = sha2::Sha512::new();
|
||||
let mut hasher = sha2::Sha256::new();
|
||||
hasher.input(&bytes.as_slice());
|
||||
let sha2_digest = hasher.result();
|
||||
let mut hash_buf: [u8; 64] = [0; 64];
|
||||
hash_buf.copy_from_slice(&sha2_digest[0..64]);
|
||||
let mut hash_buf: [u8; 32] = [0; 32];
|
||||
hash_buf.copy_from_slice(&sha2_digest);
|
||||
let hexresult = fmt_bytes_to_int(hash_buf);
|
||||
return E::Fr::from_str(&hexresult).unwrap();
|
||||
}
|
||||
|
@ -89,10 +96,9 @@ pub fn convert_int_to_fr<E: Engine>(value: i64) -> E::Fr {
|
|||
|
||||
pub fn compute_pub_key_fingerprint(wpk: &secp256k1::PublicKey) -> String {
|
||||
let x_slice = wpk.serialize();
|
||||
let mut hasher = sha2::Sha512::new();
|
||||
let mut hasher = sha2::Sha256::new();
|
||||
hasher.input(&x_slice.to_vec());
|
||||
let sha2_digest = hasher.result();
|
||||
// let sha2_digest = sha512::hash(&x_slice);
|
||||
let h = format!("{:x}", HexSlice::new(&sha2_digest[0..16]));
|
||||
return h;
|
||||
}
|
||||
|
@ -105,12 +111,12 @@ pub fn hash_buffer_to_fr<'a, E: Engine>(prefix: &'a str, buf: &[u8; 64]) -> E::F
|
|||
}
|
||||
|
||||
pub fn hash_to_slice(input_buf: &Vec<u8>) -> [u8; 32] {
|
||||
let mut hasher = sha2::Sha512::new();
|
||||
let mut hasher = sha2::Sha256::new();
|
||||
hasher.input(&input_buf.as_slice());
|
||||
let sha2_digest = hasher.result();
|
||||
|
||||
let mut hash_buf: [u8; 32] = [0; 32];
|
||||
hash_buf.copy_from_slice(&sha2_digest[0..32]);
|
||||
hash_buf.copy_from_slice(&sha2_digest);
|
||||
return hash_buf;
|
||||
}
|
||||
|
||||
|
@ -158,7 +164,7 @@ mod tests {
|
|||
let mut two = G2::one();
|
||||
two.double();
|
||||
assert_eq!(format!("{}", hash_g2_to_fr::<Bls12>(&two).into_repr()),
|
||||
"0x27cd26f702a777dbf782534ae6bf2ec4aa6cb4617c8366f10f59bef13beb8c56");
|
||||
"0x6550a1431236024424ac8e7f65781f244b70a38e5b3c275000a2b91089706868");
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
@ -168,13 +174,13 @@ mod tests {
|
|||
let mut x_vec: Vec<u8> = Vec::new();
|
||||
x_vec.extend(format!("{}", two).bytes());
|
||||
assert_eq!(format!("{}", hash_to_fr::<Bls12>(x_vec).into_repr()),
|
||||
"0x27cd26f702a777dbf782534ae6bf2ec4aa6cb4617c8366f10f59bef13beb8c56");
|
||||
"0x6550a1431236024424ac8e7f65781f244b70a38e5b3c275000a2b91089706868");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn fmt_byte_to_int_works() {
|
||||
assert_eq!(fmt_bytes_to_int([12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123]),
|
||||
"122352312313431223523123134312235231231343122352312313431223523123134312235231231343122352312313431223523123134312235231231343122352312313431223523123");
|
||||
assert_eq!(fmt_bytes_to_int([12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235]), // , 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123, 13, 43, 12, 235, 23, 123]),
|
||||
"122352312313431223523123134312235231231343122352312313431223523123134312235");
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
|
|
@ -1,5 +1,3 @@
|
|||
extern crate pairing;
|
||||
|
||||
use super::*;
|
||||
use pairing::Engine;
|
||||
use ff::PrimeField;
|
||||
|
|
Loading…
Reference in New Issue