From c5e102fa6ec8bf080f50d6c46850de2e6c31df9c Mon Sep 17 00:00:00 2001 From: opentrade Date: Sat, 10 Apr 2021 10:41:27 +0800 Subject: [PATCH] Only ed25519 --- Cargo.lock | 8 ++++- Cargo.toml | 2 +- src/lic.rs | 102 +++++++++++++---------------------------------------- 3 files changed, 33 insertions(+), 79 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 2553df2..ac87061 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -245,6 +245,12 @@ dependencies = [ "lazy_static", ] +[[package]] +name = "cryptoxide" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "46212f5d1792f89c3e866fb10636139464060110c568edd7f73ab5e9f736c26d" + [[package]] name = "ct-logs" version = "0.6.0" @@ -620,11 +626,11 @@ version = "1.1.3" dependencies = [ "base64 0.13.0", "clap", + "cryptoxide", "hbb_common", "lazy_static", "mac_address", "machine-uid", - "rand 0.8.3", "reqwest", "rocksdb", "rust-ini", diff --git a/Cargo.toml b/Cargo.toml index b56b91c..fb8e43c 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -24,7 +24,7 @@ machine-uid = "0.2" mac_address = "1.1" whoami = "0.9" base64 = "0.13" -rand = "0.8" +cryptoxide = "0.3" [build-dependencies] hbb_common = { path = "libs/hbb_common" } diff --git a/src/lic.rs b/src/lic.rs index ad164b6..9f36063 100644 --- a/src/lic.rs +++ b/src/lic.rs @@ -1,12 +1,4 @@ -use hbb_common::{ - bail, log, - sodiumoxide::crypto::{ - secretbox::{self, Nonce}, - sign, - }, - ResultType, -}; -use rand::Rng; +use hbb_common::{bail, log, ResultType}; use serde_derive::{Deserialize, Serialize}; use std::io::prelude::*; use std::path::Path; @@ -24,13 +16,11 @@ pub struct Machine { #[derive(Debug, PartialEq, Default, Serialize, Deserialize, Clone)] pub struct Post { #[serde(default)] - machine: Machine, + machine: String, #[serde(default)] email: String, #[serde(default)] status: String, - #[serde(default)] - nonce: usize, } const LICENSE_FILE: &'static str = ".license.txt"; @@ -40,10 +30,8 @@ pub fn check_lic(email: &str) -> bool { let path = Path::new(LICENSE_FILE); if Path::is_file(&path) { let contents = std::fs::read_to_string(&path).unwrap_or("".to_owned()); - if let Ok(old_lic) = dec_machine(&contents) { - if machine == old_lic { - return true; - } + if verify(&contents, &machine) { + return true; } } @@ -52,11 +40,8 @@ pub fn check_lic(email: &str) -> bool { return false; } - match check_email(machine.clone(), email.to_owned()) { + match check_email(machine, email.to_owned()) { Ok(v) => { - if v { - write_lic(&machine); - } return v; } Err(err) => { @@ -66,96 +51,59 @@ pub fn check_lic(email: &str) -> bool { } } -fn write_lic(machine: &Machine) { - if let Ok(s) = enc_machine(&machine) { - if let Ok(mut f) = std::fs::File::create(LICENSE_FILE) { - f.write_all(s.as_bytes()).ok(); - f.sync_all().ok(); - } +fn write_lic(lic: &str) { + if let Ok(mut f) = std::fs::File::create(LICENSE_FILE) { + f.write_all(lic.as_bytes()).ok(); + f.sync_all().ok(); } } -fn check_email(machine: Machine, email: String) -> ResultType { +fn check_email(machine: String, email: String) -> ResultType { log::info!("Checking email with the server ..."); - let mut rng = rand::thread_rng(); - let nonce: usize = rng.gen(); use reqwest::blocking::Client; let resp = Client::new() .post("http://rustdesk.com/api/check-email") .json(&Post { - machine, + machine: machine.clone(), email, - nonce, ..Default::default() }) .send()?; if resp.status().is_success() { - let text = base64::decode(resp.text()?)?; - let p = dec_data(&text, nonce)?; + let p: Post = resp.json()?; + if !verify(&p.machine, &machine) { + bail!("Verification failure"); + } if !p.status.is_empty() { bail!("{}", p.status); } + write_lic(&p.machine); } else { bail!("Server error: {}", resp.status()); } Ok(true) } -fn get_lic() -> Machine { +fn get_lic() -> String { let hostname = whoami::hostname(); let uid = machine_uid::get().unwrap_or("".to_owned()); let mac = if let Ok(Some(ma)) = mac_address::get_mac_address() { - base64::encode_config(ma.bytes(), base64::URL_SAFE_NO_PAD) + base64::encode(ma.bytes()) } else { "".to_owned() }; - Machine { hostname, uid, mac } + serde_json::to_string(&Machine { hostname, uid, mac }).unwrap() } -fn enc_machine(machine: &Machine) -> ResultType { - let tmp = serde_json::to_vec::(machine)?; - const SK: &[u64] = &[ - 139, 164, 88, 86, 6, 123, 221, 248, 96, 36, 106, 207, 99, 124, 27, 196, 5, 159, 58, 253, - 238, 94, 3, 184, 237, 236, 122, 59, 205, 95, 6, 189, 88, 168, 68, 104, 60, 5, 163, 198, - 165, 38, 12, 85, 114, 203, 96, 163, 70, 48, 0, 131, 57, 12, 46, 129, 83, 17, 84, 193, 119, - 197, 130, 103, - ]; - let sk: Vec = SK.iter().map(|x| *x as u8).collect(); - let mut sk_ = [0u8; sign::SECRETKEYBYTES]; - sk_[..].copy_from_slice(&sk); - let sk = sign::SecretKey(sk_); - let tmp = base64::encode_config(sign::sign(&tmp, &sk), base64::URL_SAFE_NO_PAD); - let tmp: String = tmp.chars().rev().collect(); - Ok(tmp) -} - -fn dec_machine(s: &str) -> ResultType { - let tmp: String = s.chars().rev().collect(); - const PK: &[u64] = &[ - 88, 168, 68, 104, 60, 5, 163, 198, 165, 38, 12, 85, 114, 203, 96, 163, 70, 48, 0, 131, 57, - 12, 46, 129, 83, 17, 84, 193, 119, 197, 130, 103, - ]; - let pk: Vec = PK.iter().map(|x| *x as u8).collect(); - let mut pk_ = [0u8; sign::PUBLICKEYBYTES]; - pk_[..].copy_from_slice(&pk); - let pk = sign::PublicKey(pk_); - if let Ok(data) = sign::verify(&base64::decode_config(tmp, base64::URL_SAFE_NO_PAD)?, &pk) { - Ok(serde_json::from_slice::(&data)?) +fn verify(enc_str: &str, msg: &str) -> bool { + if let Ok(data) = base64::decode(enc_str) { + let key = + b"\xf1T\xc0\x1c\xffee\x86,S*\xd9.\x91\xcd\x85\x12:\xec\xa9 \x99:\x8a\xa2S\x1f Yy\x93R"; + cryptoxide::ed25519::verify(msg.as_bytes(), &key[..], &data) } else { - bail!("sign:verify failed"); + false } } -fn dec_data(data: &[u8], n: usize) -> ResultType { - let key = b"\xa94\xb4\xb4\xda\xf82\x96\x8b\xb0\x9d\x04d\"\x94T\xa6\xdb\xf6\xd5i=Y.\xf5\xf5i\xa9\x14\x91\xa7\xa9"; - let mut nonce = Nonce([0u8; secretbox::NONCEBYTES]); - nonce.0[..std::mem::size_of_val(&n)].copy_from_slice(&n.to_le_bytes()); - let key = secretbox::Key(*key); - if let Ok(res) = secretbox::open(&data, &nonce, &key) { - return Ok(serde_json::from_slice::(&res)?); - } - bail!("Encryption error"); -} - pub const EMAIL_ARG: &'static str = "-m, --email=[EMAIL] 'Sets your email address registered with RustDesk'";