mirror of
https://git.ethanthesleepy.one/ethanaobrien/ew.git
synced 2025-05-13 11:37:33 -05:00
Implement password salting + hashing
This commit is contained in:
parent
000406280c
commit
f20deec47d
3 changed files with 57 additions and 4 deletions
12
Cargo.lock
generated
12
Cargo.lock
generated
|
@ -541,6 +541,7 @@ dependencies = [
|
||||||
"rsa",
|
"rsa",
|
||||||
"rusqlite",
|
"rusqlite",
|
||||||
"sha1",
|
"sha1",
|
||||||
|
"sha2",
|
||||||
"substring",
|
"substring",
|
||||||
"urlencoding",
|
"urlencoding",
|
||||||
"uuid",
|
"uuid",
|
||||||
|
@ -1319,6 +1320,17 @@ dependencies = [
|
||||||
"digest",
|
"digest",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "sha2"
|
||||||
|
version = "0.10.8"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "793db75ad2bcafc3ffa7c68b215fee268f537982cd901d132f89c6343f3a3dc8"
|
||||||
|
dependencies = [
|
||||||
|
"cfg-if",
|
||||||
|
"cpufeatures",
|
||||||
|
"digest",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "signal-hook-registry"
|
name = "signal-hook-registry"
|
||||||
version = "1.4.1"
|
version = "1.4.1"
|
||||||
|
|
|
@ -21,3 +21,4 @@ substring = "1.4.5"
|
||||||
uuid = { version = "1.8.0", features = ["v4"] }
|
uuid = { version = "1.8.0", features = ["v4"] }
|
||||||
rsa = "0.9.6"
|
rsa = "0.9.6"
|
||||||
mime = "0.3.17"
|
mime = "0.3.17"
|
||||||
|
sha2 = "0.10.8"
|
||||||
|
|
|
@ -5,6 +5,8 @@ use json::{JsonValue, array, object};
|
||||||
use crate::router::global;
|
use crate::router::global;
|
||||||
use uuid::Uuid;
|
use uuid::Uuid;
|
||||||
use rand::Rng;
|
use rand::Rng;
|
||||||
|
use sha2::{Digest, Sha256};
|
||||||
|
use base64::{Engine as _, engine::general_purpose};
|
||||||
|
|
||||||
lazy_static! {
|
lazy_static! {
|
||||||
static ref ENGINE: Mutex<Option<Connection>> = Mutex::new(None);
|
static ref ENGINE: Mutex<Option<Connection>> = Mutex::new(None);
|
||||||
|
@ -256,13 +258,51 @@ pub fn save_acc_friends(auth_key: &str, data: JsonValue) {
|
||||||
save_data(auth_key, "friends", data);
|
save_data(auth_key, "friends", data);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn generate_salt() -> Vec<u8> {
|
||||||
|
let mut rng = rand::thread_rng();
|
||||||
|
let mut bytes = vec![0u8; 16];
|
||||||
|
rng.fill(&mut bytes[..]);
|
||||||
|
bytes
|
||||||
|
}
|
||||||
|
|
||||||
|
fn hash_password(password: &str) -> String {
|
||||||
|
let salt = &generate_salt();
|
||||||
|
let mut hasher = Sha256::new();
|
||||||
|
hasher.update(password.as_bytes());
|
||||||
|
hasher.update(salt);
|
||||||
|
let hashed_password = hasher.finalize();
|
||||||
|
|
||||||
|
let salt_hash = [&salt[..], &hashed_password[..]].concat();
|
||||||
|
general_purpose::STANDARD.encode(&salt_hash)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn verify_password(password: &str, salted_hash: &str) -> bool {
|
||||||
|
if password == "" || salted_hash == "" {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
let bytes = general_purpose::STANDARD.decode(salted_hash);
|
||||||
|
if !bytes.is_ok() {
|
||||||
|
return password == salted_hash;
|
||||||
|
}
|
||||||
|
let bytes = bytes.unwrap();
|
||||||
|
let (salt, hashed_password) = bytes.split_at(16);
|
||||||
|
let hashed_password = &hashed_password[0..32];
|
||||||
|
|
||||||
|
let mut hasher = Sha256::new();
|
||||||
|
hasher.update(password.as_bytes());
|
||||||
|
hasher.update(salt);
|
||||||
|
let input_hash = hasher.finalize();
|
||||||
|
|
||||||
|
input_hash.as_slice() == hashed_password
|
||||||
|
}
|
||||||
|
|
||||||
pub fn get_acc_transfer(uid: i64, token: &str, password: &str) -> JsonValue {
|
pub fn get_acc_transfer(uid: i64, token: &str, password: &str) -> JsonValue {
|
||||||
create_migration_store();
|
create_migration_store();
|
||||||
let data = lock_and_select("SELECT password FROM migration WHERE token=?1", params!(token));
|
let data = lock_and_select("SELECT password FROM migration WHERE token=?1", params!(token));
|
||||||
if !data.is_ok() {
|
if !data.is_ok() {
|
||||||
return object!{success: false};
|
return object!{success: false};
|
||||||
}
|
}
|
||||||
if data.unwrap().to_string() == password.to_string() {
|
if verify_password(password, &data.unwrap()) {
|
||||||
let login_token = get_login_token(uid);
|
let login_token = get_login_token(uid);
|
||||||
if login_token == String::new() {
|
if login_token == String::new() {
|
||||||
return object!{success: false};
|
return object!{success: false};
|
||||||
|
@ -275,7 +315,7 @@ pub fn get_acc_transfer(uid: i64, token: &str, password: &str) -> JsonValue {
|
||||||
pub fn save_acc_transfer(token: &str, password: &str) {
|
pub fn save_acc_transfer(token: &str, password: &str) {
|
||||||
create_migration_store();
|
create_migration_store();
|
||||||
lock_and_exec("DELETE FROM migration WHERE token=?1", params!(token));
|
lock_and_exec("DELETE FROM migration WHERE token=?1", params!(token));
|
||||||
lock_and_exec("INSERT INTO migration (token, password) VALUES (?1, ?2)", params!(token, password));
|
lock_and_exec("INSERT INTO migration (token, password) VALUES (?1, ?2)", params!(token, hash_password(password)));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_name_and_rank(uid: i64) -> JsonValue {
|
pub fn get_name_and_rank(uid: i64) -> JsonValue {
|
||||||
|
@ -406,8 +446,8 @@ pub fn webui_login(uid: i64, password: &str) -> Result<String, String> {
|
||||||
create_webui_store();
|
create_webui_store();
|
||||||
create_migration_store();
|
create_migration_store();
|
||||||
let pass = lock_and_select("SELECT password FROM migration WHERE token=?1", params!(crate::router::user::uid_to_code(uid.to_string()))).unwrap_or(String::new());
|
let pass = lock_and_select("SELECT password FROM migration WHERE token=?1", params!(crate::router::user::uid_to_code(uid.to_string()))).unwrap_or(String::new());
|
||||||
if pass != password.to_string() || password == "" {
|
if !verify_password(password, &pass) {
|
||||||
if acc_exists(uid) {
|
if acc_exists(uid) && pass == "" {
|
||||||
return Err(String::from("Migration token not set. Set token in game settings."));
|
return Err(String::from("Migration token not set. Set token in game settings."));
|
||||||
}
|
}
|
||||||
return Err(String::from("User/password don't match"));
|
return Err(String::from("User/password don't match"));
|
||||||
|
|
Loading…
Add table
Reference in a new issue