Skip to content

Commit

Permalink
kbs: add ProtocolVersion error
Browse files Browse the repository at this point in the history
kbs already supports checking the Request version but
any version mismatch is not correctly returned to the
client (nor checked by the current RCAR client handshake).

Add an explicit kbs ProtocolVersion error that is returned
when the Request version is higher than what the KBS claims
to support.

Signed-off-by: Mikko Ylinen <[email protected]>
  • Loading branch information
mythi committed Jul 31, 2024
1 parent 5e27ab3 commit c42dea0
Show file tree
Hide file tree
Showing 4 changed files with 34 additions and 26 deletions.
27 changes: 27 additions & 0 deletions kbs/src/http/attest.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,27 @@ use base64::engine::general_purpose::{STANDARD, URL_SAFE_NO_PAD};
use base64::Engine;
use kbs_types::Challenge;
use log::{debug, error, info};
use semver::{BuildMetadata, Prerelease, Version, VersionReq};
use serde_json::json;

static KBS_MAJOR_VERSION: u64 = 0;
static KBS_MINOR_VERSION: u64 = 1;
static KBS_PATCH_VERSION: u64 = 0;

lazy_static! {
static ref VERSION_REQ: VersionReq = {
let kbs_version = Version {
major: KBS_MAJOR_VERSION,
minor: KBS_MINOR_VERSION,
patch: KBS_PATCH_VERSION,
pre: Prerelease::EMPTY,
build: BuildMetadata::EMPTY,
};

VersionReq::parse(&format!("<={kbs_version}")).unwrap()
};
}

/// POST /auth
pub(crate) async fn auth(
request: web::Json<Request>,
Expand All @@ -22,6 +41,14 @@ pub(crate) async fn auth(
) -> Result<HttpResponse> {
info!("Auth API called.");
debug!("Auth Request: {:?}", &request);
let version = Version::parse(&request.version).unwrap();
if !VERSION_REQ.matches(&version) {
raise_error!(Error::ProtocolVersion(format!(
"expected version: {}, requested version: {}",
*VERSION_REQ,
request.version.clone()
)));
}

let challenge = attestation_service
.generate_challenge(request.tee, request.extra_params.clone())
Expand Down
4 changes: 4 additions & 0 deletions kbs/src/http/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,9 @@ pub enum Error {
#[error("Resource not permitted.")]
PolicyReject,

#[error("KBS Client Protocol Version Mismatch: {0}")]
ProtocolVersion(String),

#[error("Public key get failed: {0}")]
PublicKeyGetFailed(String),

Expand Down Expand Up @@ -140,6 +143,7 @@ mod tests {
#[case(Error::JWEFailed("test".into()))]
#[case(Error::PolicyEndpoint("test".into()))]
#[case(Error::PolicyReject)]
#[case(Error::ProtocolVersion("test".into()))]
#[case(Error::PublicKeyGetFailed("test".into()))]
#[case(Error::ReadSecretFailed("test".into()))]
#[case(Error::SetSecretFailed("test".into()))]
Expand Down
22 changes: 2 additions & 20 deletions kbs/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@ use attestation::AttestationService;
use jwt_simple::prelude::Ed25519PublicKey;
#[cfg(feature = "resource")]
use resource::RepositoryConfig;
use semver::{BuildMetadata, Prerelease, Version, VersionReq};
#[cfg(feature = "as")]
use std::sync::Arc;
use std::{net::SocketAddr, path::PathBuf};
Expand Down Expand Up @@ -68,28 +67,11 @@ mod token;
/// Resource Policy Engine
pub mod policy_engine;

static KBS_PREFIX: &str = "/kbs";
static KBS_MAJOR_VERSION: u64 = 0;
static KBS_MINOR_VERSION: u64 = 1;
static KBS_PATCH_VERSION: u64 = 0;

lazy_static! {
static ref VERSION_REQ: VersionReq = {
let kbs_version = Version {
major: KBS_MAJOR_VERSION,
minor: KBS_MINOR_VERSION,
patch: KBS_PATCH_VERSION,
pre: Prerelease::EMPTY,
build: BuildMetadata::EMPTY,
};

VersionReq::parse(&format!("<={kbs_version}")).unwrap()
};
}
static KBS_PREFIX: &str = "/kbs/v0";

macro_rules! kbs_path {
($path:expr) => {
format!("{}/v{}/{}", KBS_PREFIX, KBS_MAJOR_VERSION, $path)
format!("{}/{}", KBS_PREFIX, $path)
};
}

Expand Down
7 changes: 1 addition & 6 deletions kbs/src/session.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,9 @@ use actix_web::cookie::{
time::{Duration, OffsetDateTime},
Cookie,
};
use anyhow::{bail, Result};
use anyhow::Result;
use kbs_types::{Challenge, Request};
use log::warn;
use semver::Version;
use uuid::Uuid;

pub(crate) static KBS_SESSION_ID: &str = "kbs-session-id";
Expand Down Expand Up @@ -52,10 +51,6 @@ macro_rules! impl_member {

impl SessionStatus {
pub fn auth(request: Request, timeout: i64, challenge: Challenge) -> Result<Self> {
let version = Version::parse(&request.version).map_err(anyhow::Error::from)?;
if !crate::VERSION_REQ.matches(&version) {
bail!("Invalid Request version {}", request.version);
}
let id = Uuid::new_v4().as_simple().to_string();

let timeout = OffsetDateTime::now_utc() + Duration::minutes(timeout);
Expand Down

0 comments on commit c42dea0

Please sign in to comment.