mirror of
https://github.com/mii443/encrypt.git
synced 2025-08-22 15:05:33 +00:00
support pairing multiply
This commit is contained in:
16
client2.gpsl
16
client2.gpsl
@ -1,15 +1,5 @@
|
||||
fn main() {
|
||||
let a = encrypt(16)
|
||||
println("a: " + a)
|
||||
let b = encrypt(60)
|
||||
println("b: " + b)
|
||||
let c = encrypt(48)
|
||||
println("c: " + c)
|
||||
let d = encrypt(2)
|
||||
println("d: " + d)
|
||||
let e = encrypt(24)
|
||||
println("e: " + e)
|
||||
let f = encrypt(15)
|
||||
let r = a + b + c + d + e - f
|
||||
println("(a + b + c + d + e - f) * 2 = " + decrypt(r * 2))
|
||||
let a = encrypt(3);
|
||||
let b = encrypt2(2);
|
||||
println(decrypt_pair(a * b));
|
||||
}
|
||||
|
@ -17,4 +17,7 @@ pub struct Args {
|
||||
|
||||
#[clap(short, long, takes_value = false)]
|
||||
pub compile: bool,
|
||||
|
||||
#[clap(short, long, value_parser)]
|
||||
pub curve: Option<String>,
|
||||
}
|
||||
|
@ -133,9 +133,17 @@ pub fn start_client(args: Args) {
|
||||
servers.insert(ip, Arc::new(Mutex::new(stream)));
|
||||
}
|
||||
|
||||
let encryption = Encryption::secp256k1();
|
||||
let encryption = if let Some(curve) = args.curve {
|
||||
if curve == String::from("pairing") {
|
||||
Encryption::pairing_friendly()
|
||||
} else {
|
||||
panic!("Unknown curve");
|
||||
}
|
||||
} else {
|
||||
Encryption::secp256k1()
|
||||
};
|
||||
|
||||
let config = Config::read_or_create();
|
||||
let config = Config::read_or_create(Some(encryption.clone()));
|
||||
|
||||
let mut gpsl = GPSL::new(
|
||||
Some(functions),
|
||||
@ -143,7 +151,9 @@ pub fn start_client(args: Args) {
|
||||
Some(servers),
|
||||
encryption.clone(),
|
||||
config.private_key,
|
||||
config.private_key2,
|
||||
config.public_key,
|
||||
config.public_key2,
|
||||
vec![STD_FUNC],
|
||||
);
|
||||
let res = gpsl.run("main".to_string(), HashMap::new());
|
||||
|
@ -14,7 +14,9 @@ use crate::elliptic_curve::encryption::Encryption;
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
pub struct ConfigFile {
|
||||
pub private_key: Option<String>,
|
||||
pub private_key2: Option<String>,
|
||||
pub public_key: Option<String>,
|
||||
pub public_key2: Option<String>,
|
||||
}
|
||||
|
||||
impl ConfigFile {
|
||||
@ -29,6 +31,16 @@ impl ConfigFile {
|
||||
}
|
||||
};
|
||||
|
||||
let private_key2 = {
|
||||
if let Some(private_key2) = config.private_key2 {
|
||||
let s = private_key2.to_string();
|
||||
let encode = base64::encode(&s);
|
||||
Some(encode)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
};
|
||||
|
||||
let public_key = {
|
||||
if let Some(public_key) = config.public_key {
|
||||
let s = serde_json::to_string(&public_key).unwrap();
|
||||
@ -39,9 +51,21 @@ impl ConfigFile {
|
||||
}
|
||||
};
|
||||
|
||||
let public_key2 = {
|
||||
if let Some(public_key2) = config.public_key2 {
|
||||
let s = serde_json::to_string(&public_key2).unwrap();
|
||||
let encode = base64::encode(&s);
|
||||
Some(encode)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
};
|
||||
|
||||
Self {
|
||||
private_key,
|
||||
private_key2,
|
||||
public_key,
|
||||
public_key2,
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -49,19 +73,24 @@ impl ConfigFile {
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
pub struct Config {
|
||||
pub private_key: Option<U512>,
|
||||
pub private_key2: Option<U512>,
|
||||
pub public_key: Option<EllipticCurvePoint>,
|
||||
pub public_key2: Option<EllipticCurvePoint>,
|
||||
}
|
||||
|
||||
impl Config {
|
||||
pub fn read_or_create() -> Self {
|
||||
let encryption = Encryption::secp256k1();
|
||||
pub fn read_or_create(encryption: Option<Encryption>) -> Self {
|
||||
let encryption = encryption.unwrap_or(Encryption::secp256k1());
|
||||
if Path::new("gpsl_conf").exists() {
|
||||
Config::from_file("gpsl_conf")
|
||||
} else {
|
||||
let private_key = Encryption::get_private_key();
|
||||
let private_key2 = Encryption::get_private_key();
|
||||
let config = Config {
|
||||
private_key: Some(private_key),
|
||||
private_key2: Some(private_key2),
|
||||
public_key: Some(encryption.get_public_key(private_key)),
|
||||
public_key2: Some(encryption.get_public_key(private_key2)),
|
||||
};
|
||||
|
||||
let mut file = File::create("gpsl_conf").unwrap();
|
||||
@ -99,6 +128,16 @@ impl Config {
|
||||
}
|
||||
};
|
||||
|
||||
let private_key2 = {
|
||||
if let Some(private_key2) = config.private_key2 {
|
||||
let decoded = base64::decode(&private_key2).unwrap();
|
||||
let s = std::str::from_utf8(&decoded).unwrap();
|
||||
Some(U512::from_str_radix(s, 10).unwrap())
|
||||
} else {
|
||||
None
|
||||
}
|
||||
};
|
||||
|
||||
let public_key = {
|
||||
if let Some(public_key) = config.public_key {
|
||||
let decoded = base64::decode(&public_key).unwrap();
|
||||
@ -110,9 +149,22 @@ impl Config {
|
||||
}
|
||||
};
|
||||
|
||||
let public_key2 = {
|
||||
if let Some(public_key2) = config.public_key2 {
|
||||
let decoded = base64::decode(&public_key2).unwrap();
|
||||
let s = std::str::from_utf8(&decoded).unwrap();
|
||||
let r = EllipticCurvePoint::from_str(s).unwrap();
|
||||
Some(r)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
};
|
||||
|
||||
Config {
|
||||
private_key,
|
||||
private_key2,
|
||||
public_key,
|
||||
public_key2,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -20,6 +20,8 @@ use super::elliptic_curve::{EllipticCurve, EllipticCurvePoint};
|
||||
pub struct Encryption {
|
||||
pub ellictic_curve: EllipticCurve,
|
||||
pub base_point: EllipticCurvePoint,
|
||||
pub base_point2: Option<EllipticCurvePoint>,
|
||||
pub r: Option<U512>,
|
||||
pub order: FiniteFieldElement,
|
||||
pub plain_mapping: Vec<EllipticCurvePoint>,
|
||||
}
|
||||
@ -94,6 +96,52 @@ impl Mul<U512> for EncryptedEllipticCurvePoint {
|
||||
}
|
||||
|
||||
impl Encryption {
|
||||
pub fn pair_multiply(
|
||||
&self,
|
||||
p: EncryptedEllipticCurvePoint,
|
||||
q: EncryptedEllipticCurvePoint,
|
||||
) -> (
|
||||
FiniteFieldElement,
|
||||
FiniteFieldElement,
|
||||
FiniteFieldElement,
|
||||
FiniteFieldElement,
|
||||
) {
|
||||
let r = self.r.unwrap();
|
||||
let a = EllipticCurvePoint::weil(p.data, q.data, r);
|
||||
let b = EllipticCurvePoint::weil(p.data, q.rp, r);
|
||||
let c = EllipticCurvePoint::weil(p.rp, q.data, r);
|
||||
let d = EllipticCurvePoint::weil(p.rp, q.rp, r);
|
||||
|
||||
(a, b, c, d)
|
||||
}
|
||||
|
||||
pub fn decrypt_pair(
|
||||
&self,
|
||||
a: FiniteFieldElement,
|
||||
b: FiniteFieldElement,
|
||||
c: FiniteFieldElement,
|
||||
d: FiniteFieldElement,
|
||||
private_key: U512,
|
||||
private_key2: U512,
|
||||
) -> U512 {
|
||||
let f =
|
||||
EllipticCurvePoint::weil(self.base_point, self.base_point2.unwrap(), self.r.unwrap());
|
||||
let dec =
|
||||
a * d.pow(private_key * private_key2) / b.pow(private_key2) / c.pow(private_key) * f;
|
||||
|
||||
let mut i = U512::one();
|
||||
let mut b = f;
|
||||
while b != dec {
|
||||
b = b * f;
|
||||
i += U512::one();
|
||||
}
|
||||
if i < U512::from(7u8) {
|
||||
i
|
||||
} else {
|
||||
U512::zero()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn secp256k1() -> Self {
|
||||
let p = U512::from_str_radix(
|
||||
"115792089237316195423570985008687907853269984665640564039457584007908834671663",
|
||||
@ -135,11 +183,49 @@ impl Encryption {
|
||||
Self {
|
||||
ellictic_curve: ec,
|
||||
base_point: ec.point(secp256_k1_base_x, secp256_k1_base_y),
|
||||
base_point2: None,
|
||||
r: None,
|
||||
order: secp256_k1_order,
|
||||
plain_mapping: vec![],
|
||||
}
|
||||
}
|
||||
|
||||
pub fn pairing_friendly() -> Self {
|
||||
let p = U512::from_str_radix("1009", 10).unwrap();
|
||||
let ec_a = FiniteFieldElement::new(U512::from(37u8), p);
|
||||
let ec_b = FiniteFieldElement::new(U512::from_str_radix("0", 10).unwrap(), p);
|
||||
let pp = {
|
||||
let x = FiniteFieldElement::new(U512::from_str_radix("417", 10).unwrap(), p);
|
||||
let y = FiniteFieldElement::new(U512::from_str_radix("952", 10).unwrap(), p);
|
||||
EllipticCurvePoint::Point {
|
||||
x,
|
||||
y,
|
||||
a: ec_a,
|
||||
b: ec_b,
|
||||
}
|
||||
};
|
||||
let pd = {
|
||||
let x = FiniteFieldElement::new(U512::from_str_radix("561", 10).unwrap(), p);
|
||||
let y = FiniteFieldElement::new(U512::from_str_radix("153", 10).unwrap(), p);
|
||||
EllipticCurvePoint::Point {
|
||||
x,
|
||||
y,
|
||||
a: ec_a,
|
||||
b: ec_b,
|
||||
}
|
||||
};
|
||||
let ec = EllipticCurve { a: ec_a, b: ec_b };
|
||||
|
||||
Self {
|
||||
ellictic_curve: ec,
|
||||
base_point: pp,
|
||||
base_point2: Some(pd),
|
||||
r: Some(U512::from(7u8)),
|
||||
order: FiniteFieldElement::new(U512::from_str_radix("7", 10).unwrap(), p),
|
||||
plain_mapping: vec![],
|
||||
}
|
||||
}
|
||||
|
||||
pub fn ec_point_to_plain(&self, point: EllipticCurvePoint) -> U512 {
|
||||
match point {
|
||||
EllipticCurvePoint::Infinity => return U512::from(0u8),
|
||||
@ -219,6 +305,14 @@ impl Encryption {
|
||||
return self.base_point * m;
|
||||
}
|
||||
|
||||
pub fn plain_to_ec_point_sub(&self, m: U512) -> EllipticCurvePoint {
|
||||
if m == U512::from(0u8) {
|
||||
return EllipticCurvePoint::Infinity;
|
||||
}
|
||||
|
||||
return self.base_point2.unwrap() * m;
|
||||
}
|
||||
|
||||
pub fn decrypt(ecc_p: EncryptedEllipticCurvePoint, private_key: U512) -> EllipticCurvePoint {
|
||||
let rq = ecc_p.rp * private_key;
|
||||
ecc_p.data + (-rq)
|
||||
|
@ -25,7 +25,9 @@ pub struct ExternalFuncReturn {
|
||||
pub struct ExternalFunctionCallData {
|
||||
pub encryption: Encryption,
|
||||
pub private_key: Option<U512>,
|
||||
pub private_key2: Option<U512>,
|
||||
pub public_key: Option<EllipticCurvePoint>,
|
||||
pub public_key2: Option<EllipticCurvePoint>,
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
@ -135,6 +137,20 @@ pub const STD_FUNC: fn(
|
||||
value: Some(Variable::PureEncrypted { value: eep }),
|
||||
}
|
||||
}
|
||||
"encrypt2" => {
|
||||
let encryption = data.encryption;
|
||||
let plain = match args[0] {
|
||||
Variable::Number { value } => U512::from(value),
|
||||
Variable::U512 { value } => value,
|
||||
_ => panic!("encrypt: first argument must be a number"),
|
||||
};
|
||||
let ec = encryption.plain_to_ec_point_sub(plain);
|
||||
let eep = encryption.encrypt(ec, data.public_key.unwrap(), None);
|
||||
ExternalFuncReturn {
|
||||
status: ExternalFuncStatus::SUCCESS,
|
||||
value: Some(Variable::PureEncrypted { value: eep }),
|
||||
}
|
||||
}
|
||||
"decrypt" => {
|
||||
let encryption = data.encryption;
|
||||
let eep = match args[0] {
|
||||
@ -150,6 +166,27 @@ pub const STD_FUNC: fn(
|
||||
}),
|
||||
}
|
||||
}
|
||||
"decrypt_pair" => {
|
||||
let encryption = data.encryption;
|
||||
let (a, b, c, d) = match args[0] {
|
||||
Variable::PairedEncrypted { a, b, c, d } => (a, b, c, d),
|
||||
_ => panic!("decrypt: first argument must be a pure encrypted point"),
|
||||
};
|
||||
|
||||
let plain = encryption.decrypt_pair(
|
||||
a,
|
||||
b,
|
||||
c,
|
||||
d,
|
||||
data.private_key.unwrap(),
|
||||
data.private_key2.unwrap(),
|
||||
);
|
||||
|
||||
ExternalFuncReturn {
|
||||
status: ExternalFuncStatus::SUCCESS,
|
||||
value: Some(Variable::U512 { value: plain }),
|
||||
}
|
||||
}
|
||||
"to_num" => {
|
||||
let num = match args[0].clone() {
|
||||
Variable::Number { value } => value,
|
||||
@ -219,7 +256,9 @@ pub const STD_FUNC: fn(
|
||||
Variable::Number { value } => println!("{}", value),
|
||||
Variable::U512 { value } => println!("{:x}", value),
|
||||
Variable::PureEncrypted { value } => println!("{}", value),
|
||||
Variable::PairedEncrypted { value } => println!("{:x}", value.value),
|
||||
Variable::PairedEncrypted { a, b, c, d } => {
|
||||
println!("{:x}{:x}{:x}{:x}", a.value, b.value, c.value, d.value)
|
||||
}
|
||||
Variable::Vec { value, gpsl_type } => {
|
||||
STD_FUNC(
|
||||
"print".to_string(),
|
||||
@ -232,7 +271,9 @@ pub const STD_FUNC: fn(
|
||||
ExternalFunctionCallData {
|
||||
encryption: data.encryption.clone(),
|
||||
private_key: data.private_key.clone(),
|
||||
private_key2: data.private_key2.clone(),
|
||||
public_key: data.public_key.clone(),
|
||||
public_key2: data.public_key2.clone(),
|
||||
},
|
||||
);
|
||||
println!("");
|
||||
@ -257,7 +298,9 @@ pub const STD_FUNC: fn(
|
||||
Variable::Number { value } => print!("{}", value),
|
||||
Variable::U512 { value } => print!("{:x}", value),
|
||||
Variable::PureEncrypted { value } => print!("{}", value),
|
||||
Variable::PairedEncrypted { value } => print!("{:x}", value.value),
|
||||
Variable::PairedEncrypted { a, b, c, d } => {
|
||||
print!("{:x}{:x}{:x}{:x}", a.value, b.value, c.value, d.value)
|
||||
}
|
||||
Variable::Vec { value, .. } => {
|
||||
print!("[");
|
||||
let mut f = false;
|
||||
@ -275,7 +318,9 @@ pub const STD_FUNC: fn(
|
||||
ExternalFunctionCallData {
|
||||
encryption: data.encryption.clone(),
|
||||
private_key: data.private_key,
|
||||
private_key2: data.private_key2,
|
||||
public_key: data.public_key,
|
||||
public_key2: data.public_key2,
|
||||
},
|
||||
);
|
||||
}
|
||||
|
@ -22,7 +22,10 @@ pub enum Variable {
|
||||
value: EncryptedEllipticCurvePoint,
|
||||
},
|
||||
PairedEncrypted {
|
||||
value: FiniteFieldElement,
|
||||
a: FiniteFieldElement,
|
||||
b: FiniteFieldElement,
|
||||
c: FiniteFieldElement,
|
||||
d: FiniteFieldElement,
|
||||
},
|
||||
U512 {
|
||||
value: U512,
|
||||
@ -60,7 +63,10 @@ impl Variable {
|
||||
Variable::Text { value } => Some(value.clone()),
|
||||
Variable::Number { value } => Some(value.to_string()),
|
||||
Variable::PureEncrypted { value } => Some(value.to_string()),
|
||||
Variable::PairedEncrypted { value } => Some(value.to_string()),
|
||||
Variable::PairedEncrypted { a, b, c, d } => Some(format!(
|
||||
"{:x}{:x}{:x}{:x}",
|
||||
a.value, b.value, c.value, d.value
|
||||
)),
|
||||
Variable::U512 { value } => Some(value.to_string()),
|
||||
Variable::Vec { value, .. } => {
|
||||
let mut result = String::new();
|
||||
|
@ -31,7 +31,9 @@ pub struct GPSL {
|
||||
pub servers: Option<HashMap<String, Arc<Mutex<TcpStream>>>>,
|
||||
pub encryption: Encryption,
|
||||
pub private_key: Option<U512>,
|
||||
pub private_key2: Option<U512>,
|
||||
pub public_key: Option<EllipticCurvePoint>,
|
||||
pub public_key2: Option<EllipticCurvePoint>,
|
||||
pub global_variables: Vec<Variable>,
|
||||
pub blocks: VecDeque<Block>,
|
||||
pub external_func: Vec<
|
||||
@ -76,7 +78,9 @@ impl GPSL {
|
||||
servers: Option<HashMap<String, Arc<Mutex<TcpStream>>>>,
|
||||
encryption: Encryption,
|
||||
private_key: Option<U512>,
|
||||
private_key2: Option<U512>,
|
||||
public_key: Option<EllipticCurvePoint>,
|
||||
public_key2: Option<EllipticCurvePoint>,
|
||||
external_func: Vec<
|
||||
fn(
|
||||
String,
|
||||
@ -93,7 +97,9 @@ impl GPSL {
|
||||
servers,
|
||||
encryption,
|
||||
private_key,
|
||||
private_key2,
|
||||
public_key,
|
||||
public_key2,
|
||||
global_variables: vec![],
|
||||
blocks: VecDeque::new(),
|
||||
external_func,
|
||||
@ -295,7 +301,9 @@ impl GPSL {
|
||||
ExternalFunctionCallData {
|
||||
encryption: self.encryption.clone(),
|
||||
private_key: self.private_key,
|
||||
private_key2: self.private_key2,
|
||||
public_key: self.public_key,
|
||||
public_key2: self.public_key2,
|
||||
},
|
||||
);
|
||||
if res.status == ExternalFuncStatus::SUCCESS {
|
||||
@ -435,6 +443,10 @@ impl GPSL {
|
||||
Variable::U512 { value: rhs } => {
|
||||
Ok(Some(Variable::PureEncrypted { value: lhs * rhs }))
|
||||
}
|
||||
Variable::PureEncrypted { value: rhs } => {
|
||||
let (a, b, c, d) = self.encryption.pair_multiply(lhs, rhs);
|
||||
Ok(Some(Variable::PairedEncrypted { a, b, c, d }))
|
||||
}
|
||||
_ => Err("Cannot multiply non-number to ppe.".to_string()),
|
||||
},
|
||||
_ => Err("Cannot multiply non-number.".to_string()),
|
||||
|
@ -39,11 +39,23 @@ pub fn start_server(args: Args) {
|
||||
let functions: HashMap<String, Box<Node>> = serde_json::from_str(&buf).unwrap();
|
||||
debug!("Received: {:?}", functions);
|
||||
|
||||
let encryption = if let Some(curve) = args.curve.clone() {
|
||||
if curve == "pairing".to_string() {
|
||||
Encryption::pairing_friendly()
|
||||
} else {
|
||||
panic!("Unknown curve: {}", curve);
|
||||
}
|
||||
} else {
|
||||
Encryption::secp256k1()
|
||||
};
|
||||
|
||||
let mut gpsl = GPSL::new(
|
||||
Some(functions),
|
||||
Some(HashMap::new()),
|
||||
Some(HashMap::new()),
|
||||
Encryption::secp256k1(),
|
||||
encryption,
|
||||
None,
|
||||
None,
|
||||
None,
|
||||
None,
|
||||
vec![STD_FUNC],
|
||||
|
Reference in New Issue
Block a user