Skip to content

Commit

Permalink
Improve multithreaded performance (#173)
Browse files Browse the repository at this point in the history
* Remove uses of Arc in statics

* Increase the number of idle connections in the HTTP clients pools

* Remove unneded path specefication

* Remove discarded enumerate call

* Use rayon to simplify key fetching

* Fix compilation

* Make the number of idle configuration configurable
  • Loading branch information
sosthene-nitrokey authored Jan 12, 2024
1 parent 457fc9a commit 50c8223
Show file tree
Hide file tree
Showing 11 changed files with 150 additions and 125 deletions.
96 changes: 74 additions & 22 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions p11nethsm.conf
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ slots:
password: "Administrator"
instances:
- url: "https://localhost:8443/api/v1"
max_idle_connections: 16
danger_insecure_cert: true
# sha256_fingerprints:
# - "31:92:8E:A4:5E:16:5C:A7:33:44:E8:E9:8E:64:C4:AE:7B:2A:57:E5:77:43:49:F3:69:C9:8F:C4:2F:3A:3B:6E"
Expand Down
1 change: 1 addition & 0 deletions pkcs11/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -35,3 +35,4 @@ x509-cert = { features = ["pem"], default-features = false, version = "0.2" }
sha2 = { default-features = false, version = "0.10" }
sha1 = { default-features = false, version = "0.10" }
digest = { default-features = false, version = "0.10" }
rayon = "1.8.0"
6 changes: 5 additions & 1 deletion pkcs11/src/api/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ pub mod sign;
pub mod token;
pub mod verify;

use std::sync::atomic::Ordering;

use crate::{
backend::events::{fetch_slots_state, EventsManager},
data::{self, DEVICE, DEVICE_INIT, EVENTS_MANAGER, THREADS_ALLOWED, TOKENS_STATE},
Expand Down Expand Up @@ -93,7 +95,9 @@ pub extern "C" fn C_Initialize(pInitArgs: CK_VOID_PTR) -> CK_RV {
}

if flags & cryptoki_sys::CKF_LIBRARY_CANT_CREATE_OS_THREADS != 0 {
*THREADS_ALLOWED.lock().unwrap() = false;
THREADS_ALLOWED.store(false, Ordering::Relaxed);
} else {
THREADS_ALLOWED.store(true, Ordering::Relaxed);
}
}

Expand Down
5 changes: 2 additions & 3 deletions pkcs11/src/backend/db/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,11 +52,10 @@ impl Db {
self.objects.clear();
}

pub fn enumerate(&self) -> impl Iterator<Item = (CK_OBJECT_HANDLE, &Object)> {
pub fn iter(&self) -> impl Iterator<Item = (CK_OBJECT_HANDLE, &Object)> {
self.objects
.iter()
.enumerate()
.map(|(_, (handle, object))| (*handle, object))
.map(|(handle, object)| (*handle, object))
}

pub fn add_object(&mut self, object: Object) -> (CK_OBJECT_HANDLE, Object) {
Expand Down
2 changes: 1 addition & 1 deletion pkcs11/src/backend/events.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ pub struct EventsManager {
}

impl EventsManager {
pub fn new() -> Self {
pub const fn new() -> Self {
EventsManager {
events: Vec::new(),
finalized: false,
Expand Down
64 changes: 28 additions & 36 deletions pkcs11/src/backend/key.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ use der::{oid::ObjectIdentifier, Decode};
use log::{debug, error, trace};
use nethsm_sdk_rs::{
apis::default_api,
models::{KeyGenerateRequestData, KeyPrivateData, KeyType, PrivateKey},
models::{KeyGenerateRequestData, KeyItem, KeyPrivateData, KeyType, PrivateKey},
};

#[derive(Debug, Default)]
Expand Down Expand Up @@ -545,43 +545,35 @@ fn extract_key_id_location_header(headers: HashMap<String, String>) -> Result<St
Ok(key_id)
}

pub type WorkResult = Result<Vec<(CK_ULONG, Object)>, Error>;

pub fn fetch_loop(
keys: Arc<Mutex<Vec<nethsm_sdk_rs::models::KeyItem>>>,
db: Arc<Mutex<Db>>,
login_ctx: LoginCtx,
results: Arc<Mutex<Vec<WorkResult>>>,
pub fn fetch_one(
key: &KeyItem,
db: &Arc<Mutex<Db>>,
login_ctx: &LoginCtx,
kind: Option<ObjectKind>,
) {
while let Some(key) = keys.lock().unwrap().pop() {
let key_id = key.id.clone();

if matches!(
kind,
None | Some(ObjectKind::Other)
| Some(ObjectKind::PrivateKey)
| Some(ObjectKind::PublicKey)
| Some(ObjectKind::SecretKey)
) {
let login_ctx = login_ctx.clone();
let db = db.clone();
let res = fetch_key(&key_id, None, login_ctx, db);
results.lock().unwrap().push(res);
}

if matches!(kind, None | Some(ObjectKind::Certificate)) {
let login_ctx = login_ctx.clone();
let db = db.clone();
let res = match fetch_certificate(&key_id, None, login_ctx, db) {
Ok(vec) => Ok(vec),
Err(err) => {
debug!("Failed to fetch certificate: {:?}", err);
Ok(Vec::new())
}
};
) -> Result<Vec<(CK_ULONG, Object)>, Error> {
let mut acc = Vec::new();

if matches!(
kind,
None | Some(ObjectKind::Other)
| Some(ObjectKind::PrivateKey)
| Some(ObjectKind::PublicKey)
| Some(ObjectKind::SecretKey)
) {
let login_ctx = login_ctx.clone();
let db = db.clone();
acc = fetch_key(&key.id, None, login_ctx, db)?;
}

results.lock().unwrap().push(res);
if matches!(kind, None | Some(ObjectKind::Certificate)) {
let login_ctx = login_ctx.clone();
let db = db.clone();
match fetch_certificate(&key.id, None, login_ctx, db) {
Ok(mut vec) => acc.append(&mut vec),
Err(err) => {
debug!("Failed to fetch certificate: {:?}", err);
}
}
}
Ok(acc)
}
Loading

0 comments on commit 50c8223

Please sign in to comment.