Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

#22 password hasing threadpool #24

Merged
merged 5 commits into from
May 12, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ sha3 = "0.10.8"
x25519-dalek = {version = "2.0.0", features = ["static_secrets"]}
rand_07 = { package = "rand", version = "0.7.0" }
ascon-aead = "0.4.2"
rayon = "1.10.0"

[profile.dev.package.num-bigint-dig]
opt-level = 3
Expand Down
6 changes: 6 additions & 0 deletions index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,17 @@
/* auto-generated by NAPI-RS */

export function argon2Hash(password: string): string
export function argon2HashThreadPool(password: string): string
export function argon2Verify(hashedPassword: string, passwordToVerify: string): boolean
export function argon2VerifyThreadpool(hashedPassword: string, passwordToVerify: string): boolean
export function bcryptHash(passwordToHash: string): string
export function bcryptHashThreadpool(passwordToHash: string): string
export function bcryptVerify(hashedPassword: string, passwordToVerify: string): boolean
export function bcryptVerifyThreadpool(passwordToHash: string, passwordToVerify: string): boolean
export function scryptHash(passwordToHash: string): string
export function scryptVerify(hashedPassword: string, passwordToVerify: string): boolean
export function scryptHashThreadpool(passwordToHash: string): string
export function scryptVerifyThreadpool(hashedPassword: string, passwordToVerify: string): boolean
export function sha512(dataToHash: Array<number>): Array<number>
export function sha512Verify(dataToHash: Array<number>, dataToVerify: Array<number>): boolean
export function sha256(dataToHash: Array<number>): Array<number>
Expand Down
Binary file modified index.node
Binary file not shown.
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@

{
"name": "cas-typescript-sdk",
"version": "1.0.21",
"version": "1.0.22",
"description": "",
"main": "lib/index.js",
"types": "lib/index.d.ts",
Expand Down
28 changes: 24 additions & 4 deletions src-ts/password-hashers/argon2-wrapper.ts
Original file line number Diff line number Diff line change
@@ -1,17 +1,37 @@
import {argon2Hash, argon2Verify} from "./../../index";
import { IPasswordHasherBase} from "./password-hasher-base";
import { argon2Hash, argon2HashThreadPool, argon2Verify, argon2VerifyThreadpool } from "./../../index";
import { IPasswordHasherBase } from "./password-hasher-base";

export class Argon2Wrapper implements IPasswordHasherBase {

verifyThreadPool(hashedPassword: string, passwordToCheck: string): boolean {
if (!hashedPassword) {
throw new Error("You must provide a password to verify with Argon2");
}
if (!passwordToCheck) {
throw new Error("You must provide a password to check to verify with Argon2");
}
return argon2VerifyThreadpool(hashedPassword, passwordToCheck);
}

public hashPasswordThreadPool(password: string): string {
if (!password) {
throw new Error("You must provide a password to hash with Argon2");
}
return argon2HashThreadPool(password);
}

public hashPassword(password: string): string {
if (!password){
if (!password) {
throw new Error("You must provide a password to hash with Argon2");
}
return argon2Hash(password);
}

public verify(hashedPassword: string, passwordToVerify: string): boolean {
if (!hashedPassword || !passwordToVerify) {
throw new Error("You must provide a hashed password and a plaintext password to verify with Argon2");
throw new Error(
"You must provide a hashed password and a plaintext password to verify with Argon2",
);
}
return argon2Verify(hashedPassword, passwordToVerify);
}
Expand Down
19 changes: 18 additions & 1 deletion src-ts/password-hashers/bcrypt-wrapper.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,24 @@
import { IPasswordHasherBase } from "./password-hasher-base";
import { bcryptHash, bcryptVerify } from "./../../index";
import { bcryptHash, bcryptHashThreadpool, bcryptVerify, bcryptVerifyThreadpool } from "./../../index";

export class BCryptWrapper implements IPasswordHasherBase {

verifyThreadPool(hashedPassword: string, passwordToCheck: string): boolean {
if (!hashedPassword || !passwordToCheck) {
throw new Error(
"You must provide a hashed password and a plaintext password to verify with Argon2",
);
}
return bcryptVerifyThreadpool(hashedPassword, passwordToCheck);
}

public hashPasswordThreadPool(password: string): string {
if (!password) {
throw new Error("You must provide a password to hash with Argon2");
}
return bcryptHashThreadpool(password);
}

public hashPassword(password: string): string {
if (!password) {
throw new Error("You must provide a password to hash with Argon2");
Expand Down
2 changes: 2 additions & 0 deletions src-ts/password-hashers/password-hasher-base.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
export interface IPasswordHasherBase {
hashPassword(password: string): string;
verify(hashedPassword: string, passwordToVerify: string): boolean;
hashPasswordThreadPool(password: string): string;
verifyThreadPool(hashedPassword: string, passwordToCheck: string): boolean;
}
47 changes: 32 additions & 15 deletions src-ts/password-hashers/scrypt-wrapper.ts
Original file line number Diff line number Diff line change
@@ -1,20 +1,37 @@
import { scryptHash, scryptVerify } from "../../index";
import { scryptHash, scryptHashThreadpool, scryptVerify, scryptVerifyThreadpool } from "../../index";
import { IPasswordHasherBase } from "./password-hasher-base";

export class ScryptWrapper implements IPasswordHasherBase {

public hashPassword(password: string): string {
if (!password){
throw new Error("You must provide a password to hash with Scrypt");
}
return scryptHash(password);
}

public verify(hashedPassword: string, passwordToVerify: string): boolean {
if (!hashedPassword || !passwordToVerify) {
throw new Error("You must provide a hashed password and a plaintext password to verify with Scrypt");
}
return scryptVerify(hashedPassword, passwordToVerify);
}
verifyThreadPool(hashedPassword: string, passwordToCheck: string): boolean {
if (!hashedPassword || !passwordToCheck) {
throw new Error(
"You must provide a hashed password and a plaintext password to verify with Scrypt",
);
}
return scryptVerifyThreadpool(hashedPassword, passwordToCheck);
}

}
hashPasswordThreadPool(password: string): string {
if (!password) {
throw new Error("You must provide a password to hash with Scrypt");
}
return scryptHashThreadpool(password);
}

public hashPassword(password: string): string {
if (!password) {
throw new Error("You must provide a password to hash with Scrypt");
}
return scryptHash(password);
}

public verify(hashedPassword: string, passwordToVerify: string): boolean {
if (!hashedPassword || !passwordToVerify) {
throw new Error(
"You must provide a hashed password and a plaintext password to verify with Scrypt",
);
}
return scryptVerify(hashedPassword, passwordToVerify);
}
}
41 changes: 40 additions & 1 deletion src/password_hashers/argon2.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
use std::net::ToSocketAddrs;

use napi_derive::napi;

Expand All @@ -7,6 +6,8 @@ use argon2::{
Argon2, PasswordHash, PasswordHasher, PasswordVerifier,
};

use crate::symmetric::aes::CASAES128;

use super::cas_password_hasher::CASPasswordHasher;

pub struct CASArgon;
Expand Down Expand Up @@ -35,11 +36,49 @@ pub fn argon2_hash(password: String) -> String {
return <CASArgon as CASPasswordHasher>::hash_password(password);
}

#[napi]
pub fn argon2_hash_thread_pool(password: String) -> String {
let (sender, receiver) = std::sync::mpsc::channel();
rayon::spawn(move || {
let hash_result = <CASArgon as CASPasswordHasher>::hash_password(password);
sender.send(hash_result);
});
let result = receiver.recv().unwrap();
result
}

#[napi]
pub fn argon2_verify(hashed_password: String, password_to_verify: String) -> bool {
return <CASArgon as CASPasswordHasher>::verify_password(hashed_password, password_to_verify);
}

#[napi]
pub fn argon2_verify_threadpool(hashed_password: String, password_to_verify: String) -> bool {
let (sender, receiver) = std::sync::mpsc::channel();
rayon::spawn(move || {
let verify_result = <CASArgon as CASPasswordHasher>::verify_password(hashed_password, password_to_verify);
sender.send(verify_result);
});
let result = receiver.recv().unwrap();
result
}

#[test]
pub fn argon2_hash_threadpool_test() {
let password = "ThisIsNotMyPasswolrd".to_string();
let hashed = argon2_hash_thread_pool(password.clone());
assert_ne!(password, hashed);
}

#[test]
pub fn argon2_verify_threadpool_test() {
let password = "ThisIsNotMyPasswolrd".to_string();
let passwordToCheck = "ThisIsNotMyPasswolrd".to_string();
let hashed = argon2_hash_thread_pool(password);
let result = argon2_verify_threadpool(hashed, passwordToCheck);
assert_eq!(result, true);
}

#[test]
pub fn argon2_hash_test() {
let password = "ThisIsNotMyPasswolrd".to_string();
Expand Down
39 changes: 39 additions & 0 deletions src/password_hashers/bcrypt.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use std::sync::mpsc;

use bcrypt::{hash, verify, DEFAULT_COST};
use napi_derive::napi;

Expand All @@ -20,18 +22,47 @@ pub fn bcrypt_hash(password_to_hash: String) -> String {
return <CASBCrypt as CASPasswordHasher>::hash_password(password_to_hash);
}

#[napi]
pub fn bcrypt_hash_threadpool(password_to_hash: String) -> String {
let (sender, receiver) = mpsc::channel();
rayon::spawn(move || {
let thread_result = <CASBCrypt as CASPasswordHasher>::hash_password(password_to_hash);
sender.send(thread_result);
});
let result = receiver.recv().unwrap();
result
}

#[napi]
pub fn bcrypt_verify(hashed_password: String, password_to_verify: String) -> bool {
return <CASBCrypt as CASPasswordHasher>::verify_password(hashed_password, password_to_verify);
}

#[napi]
pub fn bcrypt_verify_threadpool(password_to_hash: String, password_to_verify: String) -> bool {
let (sender, receiver) = mpsc::channel();
rayon::spawn(move || {
let thread_result = <CASBCrypt as CASPasswordHasher>::verify_password(password_to_hash, password_to_verify);
sender.send(thread_result);
});
let result = receiver.recv().unwrap();
result
}

#[test]
pub fn bcrypt_hash_test() {
let password = "ThisIsNotMyPasswolrd".to_string();
let hashed = bcrypt_hash(password.clone());
assert_ne!(password, hashed);
}

#[test]
pub fn bcrypt_hash_threadpool_test() {
let password = "ThisIsNotMyPasswolrd".to_string();
let hashed = bcrypt_hash_threadpool(password.clone());
assert_ne!(password, hashed);
}

#[test]
pub fn bcrypt_verify_test() {
let password = "ThisIsNotMyPasswolrd".to_string();
Expand All @@ -40,6 +71,14 @@ pub fn bcrypt_verify_test() {
assert_eq!(true, verified);
}

#[test]
pub fn bcrypt_verify_threadpool_test() {
let password = "ThisIsNotMyPasswolrd".to_string();
let hashed = bcrypt_hash_threadpool(password.clone());
let verified = bcrypt_verify_threadpool(hashed, password);
assert_eq!(true, verified);
}

#[test]
pub fn bcrypt_verify_fail_test() {
let password = "ThisIsNotMyPasswolrd".to_string();
Expand Down
39 changes: 39 additions & 0 deletions src/password_hashers/scrypt.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use std::sync::mpsc;

use napi_derive::napi;

use scrypt::{
Expand Down Expand Up @@ -36,6 +38,43 @@ pub fn scrypt_verify(hashed_password: String, password_to_verify: String) -> boo
return <CASScrypt as CASPasswordHasher>::verify_password(hashed_password, password_to_verify);
}

#[napi]
pub fn scrypt_hash_threadpool(password_to_hash: String) -> String {
let (sender, receiver) = mpsc::channel();
rayon::spawn(move || {
let thread_result = <CASScrypt as CASPasswordHasher>::hash_password(password_to_hash);
sender.send(thread_result);
});
let result = receiver.recv().unwrap();
result
}

#[napi]
pub fn scrypt_verify_threadpool(hashed_password: String, password_to_verify: String) -> bool {
let (sender, receiver) = mpsc::channel();
rayon::spawn(move || {
let thread_result = <CASScrypt as CASPasswordHasher>::verify_password(hashed_password, password_to_verify);
sender.send(thread_result);
});
let result = receiver.recv().unwrap();
result
}

#[test]
pub fn scrypt_hash_threadpool_test() {
let password = "BadPassword".to_string();
let hashed_password = scrypt_hash_threadpool(password.clone());
assert_ne!(password, hashed_password);
}

#[test]
pub fn scrypt_verify_threadpool_test() {
let password = "BadPassword".to_string();
let hashed_password = scrypt_hash_threadpool(password.clone());
let verified = scrypt_verify_threadpool(hashed_password, password);
assert_eq!(true, verified);
}

#[test]
pub fn scrypt_hash_test() {
let password = "BadPassword".to_string();
Expand Down
Loading
Loading