From 1a7b3c31095762afebeab1cc1717259c0e3c5cc9 Mon Sep 17 00:00:00 2001 From: Rob Austein Date: Thu, 24 Dec 2015 13:55:55 -0500 Subject: hal_rpc_logout_all(), hal_rpc_is_logged_in(). --- hal.h | 6 ++++++ hal_internal.h | 5 +++++ rpc_api.c | 13 +++++++++++++ rpc_client.c | 27 ++++++++++++++++++++++++++- rpc_misc.c | 31 +++++++++++++++++++++++++------ 5 files changed, 75 insertions(+), 7 deletions(-) diff --git a/hal.h b/hal.h index 36b69dc..bf5ca6f 100644 --- a/hal.h +++ b/hal.h @@ -124,6 +124,7 @@ DEFINE_HAL_ERROR(HAL_ERROR_NO_KEY_SLOTS_AVAILABLE, "No key slots available") \ DEFINE_HAL_ERROR(HAL_ERROR_PIN_INCORRECT, "PIN incorrect") \ DEFINE_HAL_ERROR(HAL_ERROR_NO_CLIENT_SLOTS_AVAILABLE, "No client slots available") \ + DEFINE_HAL_ERROR(HAL_ERROR_FORBIDDEN, "Forbidden") \ END_OF_HAL_ERROR_LIST /* Marker to forestall silly line continuation errors */ @@ -554,6 +555,11 @@ extern hal_error_t hal_rpc_login(const hal_client_handle_t client, extern hal_error_t hal_rpc_logout(const hal_client_handle_t client); +extern hal_error_t hal_rpc_logout_all(void); + +extern hal_error_t hal_rpc_is_logged_in(const hal_client_handle_t client, + const hal_user_t user); + /* * Get random bytes. */ diff --git a/hal_internal.h b/hal_internal.h index 1c6489f..ea760cf 100644 --- a/hal_internal.h +++ b/hal_internal.h @@ -95,6 +95,11 @@ typedef struct { hal_error_t (*logout)(const hal_client_handle_t client); + hal_error_t (*logout_all)(void); + + hal_error_t (*is_logged_in)(const hal_client_handle_t client, + const hal_user_t user); + hal_error_t (*get_random)(void *buffer, const size_t length); } hal_rpc_misc_dispatch_t; diff --git a/rpc_api.c b/rpc_api.c index 08ba4cd..d0ed25c 100644 --- a/rpc_api.c +++ b/rpc_api.c @@ -148,6 +148,19 @@ hal_error_t hal_rpc_logout(const hal_client_handle_t client) return misc_dispatch->logout(client); } +hal_error_t hal_rpc_logout_all(void) +{ + return misc_dispatch->logout_all(); +} + +hal_error_t hal_rpc_is_logged_in(const hal_client_handle_t client, + const hal_user_t user) +{ + if (user != HAL_USER_NORMAL && user != HAL_USER_SO && user != HAL_USER_WHEEL) + return HAL_ERROR_BAD_ARGUMENTS; + return misc_dispatch->is_logged_in(client, user); +} + hal_error_t hal_rpc_hash_get_digest_length(const hal_digest_algorithm_t alg, size_t *length) { if (length == NULL) diff --git a/rpc_client.c b/rpc_client.c index 1fcc914..3d4fcee 100644 --- a/rpc_client.c +++ b/rpc_client.c @@ -54,6 +54,20 @@ static hal_error_t set_pin(const hal_client_handle_t client, return HAL_ERROR_IMPOSSIBLE; } +/* + * We may end up wanting to wrap a client-side cache around the + * login()/logout()/logout_all() calls and reimplement is_logged_in() + * on the client side using that cache, so that access checks don't + * need to cross the RPC boundary. Then again, we might not, if the + * RPC call is fast enough, so implementing all before the RPC would + * qualify as premature optimization. There aren't all that many + * things on the client side that would use this anyway, so the whole + * question may be moot. + * + * For now, we leave all of these as plain RPC calls, but we may want + * to revisit this if the is_logged_in() call turns into a bottleneck. + */ + static hal_error_t login(const hal_client_handle_t client, const hal_user_t user, const char * const pin, const size_t pin_len) @@ -66,6 +80,17 @@ static hal_error_t logout(const hal_client_handle_t client) return HAL_ERROR_IMPOSSIBLE; } +static hal_error_t logout_all(void) +{ + return HAL_ERROR_IMPOSSIBLE; +} + +static hal_error_t is_logged_in(const hal_client_handle_t client, + const hal_user_t user) +{ + return HAL_ERROR_IMPOSSIBLE; +} + static hal_error_t hash_get_digest_len(const hal_digest_algorithm_t alg, size_t *length) { return HAL_ERROR_IMPOSSIBLE; @@ -270,7 +295,7 @@ static hal_error_t pkey_mixed_verify(const hal_session_handle_t session, */ const hal_rpc_misc_dispatch_t hal_rpc_remote_misc_dispatch = { - set_pin, login, logout, get_random + set_pin, login, logout, logout_all, is_logged_in, get_random }; const hal_rpc_hash_dispatch_t hal_rpc_remote_hash_dispatch = { diff --git a/rpc_misc.c b/rpc_misc.c index 695e0df..2a7c610 100644 --- a/rpc_misc.c +++ b/rpc_misc.c @@ -64,10 +64,6 @@ static hal_error_t get_random(void *buffer, const size_t length) * * More interesting question is whether we should ever allow the WHEEL * PIN to be changed a second time without toasting the keystore. - * - * We also need a function which the rest of the library can use to - * check current login status for a particular hal_client_t. Don't - * know yet whether we need anything else. */ #warning PIN code not yet fully implemented @@ -180,7 +176,7 @@ static hal_error_t login(const hal_client_handle_t client, client_slot_t *slot = find_handle(client); - if (slot != NULL && (slot = alloc_slot()) == NULL) + if (slot == NULL && (slot = alloc_slot()) == NULL) return HAL_ERROR_NO_CLIENT_SLOTS_AVAILABLE; slot->handle = client; @@ -189,6 +185,19 @@ static hal_error_t login(const hal_client_handle_t client, return HAL_OK; } +static hal_error_t is_logged_in(const hal_client_handle_t client, + const hal_user_t user) +{ + assert(user == HAL_USER_NORMAL || user == HAL_USER_SO || user == HAL_USER_WHEEL); + + client_slot_t *slot = find_handle(client); + + if (slot == NULL || slot->logged_in != user) + return HAL_ERROR_FORBIDDEN; + + return HAL_OK; +} + static hal_error_t logout(const hal_client_handle_t client) { client_slot_t *slot = find_handle(client); @@ -199,8 +208,18 @@ static hal_error_t logout(const hal_client_handle_t client) return HAL_OK; } +static hal_error_t logout_all(void) +{ +#if HAL_STATIC_CLIENT_STATE_BLOCKS > 0 + for (int i = 0; i < sizeof(client_handle)/sizeof(*client_handle); i++) + client_handle[i].logged_in = HAL_USER_NONE; +#endif + + return HAL_OK; +} + const hal_rpc_misc_dispatch_t hal_rpc_remote_misc_dispatch = { - set_pin, login, logout, get_random + set_pin, login, logout, logout_all, is_logged_in, get_random }; /* -- cgit v1.2.3