diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/check.c | 106 | ||||
-rw-r--r-- | src/config.c | 8 | ||||
-rw-r--r-- | src/module.c | 277 | ||||
-rw-r--r-- | src/msg.c | 30 | ||||
-rw-r--r-- | src/object.c | 202 | ||||
-rw-r--r-- | src/p11-tests.h | 73 | ||||
-rw-r--r-- | src/rsa.c | 123 | ||||
-rw-r--r-- | src/session.c | 222 | ||||
-rw-r--r-- | src/slot.c | 193 |
9 files changed, 650 insertions, 584 deletions
diff --git a/src/check.c b/src/check.c index d76f0e9..9609779 100644 --- a/src/check.c +++ b/src/check.c @@ -9,27 +9,47 @@ p11t_check_fail(const char *message, ...) { va_list va; va_start(va, message); - p11t_msg_va(message, va); + p11t_msg_code("FAIL", message, va); va_end(va); - return 0; + return STOP; } int -p11t_check_returns(const char *message, CK_RV have, CK_RV want) +p11t_check_info(const char *message, ...) +{ + va_list va; + va_start(va, message); + p11t_msg_code("INFO", message, va); + va_end(va); + return CONTINUE; +} + +int +p11t_check_warn(const char *message, ...) +{ + va_list va; + va_start(va, message); + p11t_msg_code("WARN", message, va); + va_end(va); + return CONTINUE; +} + +int +_p11t_check_rv(const char *what, CK_RV have, CK_RV want) { if(have != want) { - p11t_msg_print("%s: expected %s but got %s", message, - p11t_msg_rv(want), p11t_msg_rv(have)); - return 0; + p11t_check_fail("%s: expected %s but got %s", what, + p11t_msg_rv(want), p11t_msg_rv(have)); + return STOP; } - return 1; + return CONTINUE; } int -p11t_check_padded_len(const char *message, const CK_UTF8CHAR_PTR padded, - CK_ULONG length) +_p11t_check_padded(const char *what, const CK_UTF8CHAR_PTR padded, + CK_ULONG length) { CK_ULONG i; @@ -37,48 +57,48 @@ p11t_check_padded_len(const char *message, const CK_UTF8CHAR_PTR padded, { if(!isprint(padded[i])) { - p11t_msg_print("%s: non printable character: %d", message, padded[i]); - return 0; + p11t_check_fail("%s: non printable character: %d", what, padded[i]); + return STOP; } if(!padded[i]) { - p11t_msg_print("%s: not blank padded", message); - return 0; + p11t_check_fail("%s: not blank padded", what); + return STOP; } } - return 1; + return CONTINUE; } int -p11t_check_ulong(const char *message, CK_ULONG have, CK_ULONG want) +_p11t_check_ulong(const char *what, CK_ULONG have, CK_ULONG want) { if(have != want) { - p11t_msg_print("%s: expected 0x%08x but have 0x%08x", message, - want, have); - return 0; + p11t_check_fail("%s: expected 0x%08x but have 0x%08x", what, + want, have); + return STOP; } - return 1; + return CONTINUE; } int -p11t_check_bool(const char *message, CK_BBOOL value) +_p11t_check_bool(const char *what, CK_BBOOL value) { if(value != CK_FALSE && value != CK_TRUE) { - p11t_msg_print("%s: expected CK_TRUE or CK_FALSE but got 0x%02x", - message, (int)value); - return 0; + p11t_check_fail("%s: expected CK_TRUE or CK_FALSE but got 0x%02x", + what, (int)value); + return STOP; } - return 1; + return CONTINUE; } int -p11t_check_string(const char *message, CK_UTF8CHAR_PTR value, CK_ULONG length) +_p11t_check_string(const char *what, CK_UTF8CHAR_PTR value, CK_ULONG length) { CK_ULONG i; @@ -86,49 +106,49 @@ p11t_check_string(const char *message, CK_UTF8CHAR_PTR value, CK_ULONG length) { if(!value[i]) { - p11t_msg_print("%s: is null terminated", message); - return 0; + p11t_check_fail("%s: is null terminated", what); + return STOP; } } - return 1; + return CONTINUE; } int -p11t_check_mask(const char *message, CK_ULONG flags, CK_ULONG mask) +_p11t_check_mask(const char *what, CK_ULONG flags, CK_ULONG mask) { if((flags & ~mask) != 0) { - p11t_msg_print("%s: extra flags outside of mask: 0x%08x", - message, (flags & ~mask)); - return 0; + p11t_check_fail("%s: extra flags outside of mask: 0x%08x", + what, (flags & ~mask)); + return STOP; } - return 1; + return CONTINUE; } int -p11t_check_flag(const char *message, CK_ULONG flags, CK_ULONG flag) +_p11t_check_flag(const char *what, CK_ULONG flags, CK_ULONG flag) { if((flags & flag) != flag) { - p11t_msg_print("%s: flag 0x%08x should be set in: 0x%08x", - message, flag, flags); - return 0; + p11t_check_fail("%s: flag 0x%08x should be set in: 0x%08x", + what, flag, flags); + return STOP; } - return 1; + return CONTINUE; } int -p11t_check_nflag(const char *message, CK_ULONG flags, CK_ULONG nflag) +_p11t_check_nflag(const char *what, CK_ULONG flags, CK_ULONG nflag) { if((flags & nflag) != 0) { - p11t_msg_print("%s: flag 0x%08x should not be set in: 0x%08x", - message, nflag, flags); - return 0; + p11t_check_fail("%s: flag 0x%08x should not be set in: 0x%08x", + what, nflag, flags); + return STOP; } - return 1; + return CONTINUE; } diff --git a/src/config.c b/src/config.c index 48b4151..652556e 100644 --- a/src/config.c +++ b/src/config.c @@ -38,20 +38,20 @@ p11t_config_parse(const char* filename) f = fopen(filename, "r"); if(f == NULL) - p11t_msg_exit(1, "couldn't open config file: %s", filename); + p11t_msg_fatal("couldn't open config file: %s", filename); /* Figure out size */ if(fseek(f, 0, SEEK_END) == -1 || (len = ftell(f)) == -1 || fseek(f, 0, SEEK_SET) == -1) - p11t_msg_exit(1, "couldn't seek config file: %s", filename); + p11t_msg_fatal("couldn't seek config file: %s", filename); assert(!config_data); config_data = malloc(len + 2); if(!config_data) - p11t_msg_exit(1, "out of memory"); + p11t_msg_fatal("out of memory"); /* And read in one block */ if(fread(config_data, 1, len, f) != len) - p11t_msg_exit(1, "couldn't read config file: %s", filename); + p11t_msg_fatal("couldn't read config file: %s", filename); fclose(f); diff --git a/src/module.c b/src/module.c index 453acd4..7911bf2 100644 --- a/src/module.c +++ b/src/module.c @@ -26,7 +26,7 @@ CK_FUNCTION_LIST_PTR p11t_module_funcs = NULL; static const char *init_string = NULL; static CK_C_INITIALIZE_ARGS init_args; -static void (*init_func)(void) = NULL; +static int (*init_func)(void) = NULL; static int is_initialized = 0; void @@ -39,20 +39,23 @@ p11t_module_config(const char *name, const char *value) static CK_RV create_mutex(void **mutex) { + const char *old = P11T_SECTION("CreateMutex"); + CK_RV ret = CKR_OK; + if(!mutex) { - p11t_msg_print("CreateMutex: null mutex passed"); - return CKR_ARGUMENTS_BAD; + P11T_CHECK_FAIL("Arguments should not be null"); + ret = CKR_ARGUMENTS_BAD; } - + else + { #ifdef _WIN32 - *mutex = CreateMutex(NULL, FALSE, NULL); - assert(*mutex != NULL); + *mutex = CreateMutex(NULL, FALSE, NULL); + assert(*mutex != NULL); #else /* !_WIN32 */ - { pthread_mutex_t *mut; mut = malloc(sizeof(pthread_mutex_t)); assert(mut); @@ -60,190 +63,200 @@ create_mutex(void **mutex) if(pthread_mutex_init(mut, NULL) != 0) assert(0); *mutex = mut; - } #endif /* !_WIN32 */ + } - return CKR_OK; + p11t_msg_prefix(old); + return ret; } static CK_RV destroy_mutex (void *mutex) { + const char *old = P11T_SECTION("DestroyMutex"); + CK_RV ret = CKR_OK; + if(!mutex) { - p11t_msg_print("DestroyMutex: null mutex"); - return CKR_MUTEX_BAD; + P11T_CHECK_FAIL("Mutex should not be null"); + ret = CKR_MUTEX_BAD; } - + else + { #ifdef _WIN32 - if(!CloseHandle((HANDLE)mutex)) - { - DWORD error = GetLastError(); - if(error == ERROR_INVALID_HANDLE) + if(!CloseHandle((HANDLE)mutex)) { - p11t_msg_print("DestroyMutex: mutex is invalid"); - return CKR_MUTEX_BAD; - } - else - { - p11t_msg_print("DestroyMutex: failed: %d", GetLastError()); - return CKR_GENERAL_ERROR; + DWORD error = GetLastError(); + if(error == ERROR_INVALID_HANDLE) + { + P11T_CHECK_FAIL("Mutex should not be invalid"); + ret = CKR_MUTEX_BAD; + } + else + { + p11t_check_warn("failed: %d", GetLastError()); + ret = CKR_GENERAL_ERROR; + } } - } - #else /* !_WIN32 */ - { int res = pthread_mutex_destroy(mutex); if(res != 0) { if(res == EBUSY) { - p11t_msg_print("DestroyMutex: mutex is locked"); - return CKR_GENERAL_ERROR; + P11T_CHECK_FAIL("Mutex should not be locked"); + ret = CKR_GENERAL_ERROR; } else if(res == EINVAL) { - p11t_msg_print("DestroyMutex: mutex is invalid"); - return CKR_MUTEX_BAD; + P11T_CHECK_FAIL("Mutex should not be invalid"); + ret = CKR_MUTEX_BAD; } else { - p11t_msg_print("DestroyMutex: failed: %d", res); - return CKR_GENERAL_ERROR; + p11t_check_warn("failed: %d", res); + ret = CKR_GENERAL_ERROR; } } - } #endif /* !_WIN32 */ + } - return CKR_OK; + p11t_msg_prefix(old); + return ret; } static CK_RV lock_mutex (void *mutex) { + const char *old = P11T_SECTION("LockMutex"); + CK_RV ret = CKR_OK; + if(!mutex) { - p11t_msg_print("LockMutex: null mutex"); - return CKR_MUTEX_BAD; + P11T_CHECK_FAIL("null mutex"); + ret = CKR_MUTEX_BAD; } - + else + { #ifdef _WIN32 - { DWORD result = WaitForSingleObject((HANDLE)mutex, INFINITE); if(result == WAIT_ABANDONED) { - p11t_msg_print("LockMutex: thread exited without releasing mutex"); - return CKR_CANT_LOCK; + P11T_CHECK_FAIL("Thread should not exit without releasing mutex"); + ret = CKR_CANT_LOCK; } else if(result == WAIT_FAILED) { DWORD error = GetLastError(); if(error == ERROR_INVALID_HANDLE) { - p11t_msg_print("LockMutex: invalid handle"); - return CKR_MUTEX_BAD; + P11T_CHECK_FAIL("Mutex should not be invalid"); + ret = CKR_MUTEX_BAD; } else { - p11t_msg_print("LockMutex: failed: %d", error); - return CKR_GENERAL_ERROR; + p11t_check_warn("failed: %d", error); + ret = CKR_GENERAL_ERROR; } } else if(result != WAIT_OBJECT_0) { - p11t_msg_print("LockMutex: couldn't lock"); - return CKR_CANT_LOCK; + p11t_check_warn("couldn't lock"); + ret = CKR_CANT_LOCK; } - } #else /* !_WIN32 */ - { int res = pthread_mutex_lock(mutex); if(res != 0) { if(res == EDEADLK) { - p11t_msg_print("LockMutex: would deadlock"); - return CKR_CANT_LOCK; + P11T_CHECK_FAIL("Mutex should not deadlock"); + ret = CKR_CANT_LOCK; } else if(res == EINVAL) { - p11t_msg_print("LockMutex: invalid mutex used"); - return CKR_MUTEX_BAD; + P11T_CHECK_FAIL("Mutex should not be invalid"); + ret = CKR_MUTEX_BAD; } else { - p11t_msg_print("LockMutex: failed: %d", res); - return CKR_GENERAL_ERROR; + p11t_check_warn("failed: %d", res); + ret = CKR_GENERAL_ERROR; } } - } #endif /* !_WIN32 */ + } - return CKR_OK; + p11t_msg_prefix(old); + return ret; } static CK_RV unlock_mutex (void *mutex) { + const char *old = P11T_SECTION("UnlockMutex"); + CK_RV ret = CKR_OK; + if(!mutex) { - p11t_msg_print("UnlockMutex: null mutex"); - return CKR_MUTEX_BAD; + P11T_CHECK_FAIL("Mutex should not be null"); + ret = CKR_MUTEX_BAD; } + else + { #ifdef _WIN32 - if(!ReleaseMutex((HANDLE)mutex)) - { - DWORD error = GetLastError(); - if(error == ERROR_NOT_OWNER) + if(!ReleaseMutex((HANDLE)mutex)) { - p11t_msg_print("UnlockMutex: mutex not locked"); - return CKR_MUTEX_NOT_LOCKED; - } - else if(error == ERROR_INVALID_HANDLE) - { - p11t_msg_print("UnlockMutex: invalid mutex used"); - return CKR_MUTEX_BAD; - } - else - { - p11t_msg_print("UnlockMutex: failed: %d", error); - return CKR_GENERAL_ERROR; + DWORD error = GetLastError(); + if(error == ERROR_NOT_OWNER) + { + P11T_CHECK_FAIL("Mutex should be locked"); + ret = CKR_MUTEX_NOT_LOCKED; + } + else if(error == ERROR_INVALID_HANDLE) + { + P11T_CHECK_FAIL("Mutex should not be invalid"); + ret = CKR_MUTEX_BAD; + } + else + { + p11t_check_warn("failed: %d", error); + ret = CKR_GENERAL_ERROR; + } } - } #else /* !_WIN32 */ - { int res = pthread_mutex_lock(mutex); if(res != 0) { if(res == EPERM) { - p11t_msg_print("UnlockMutex: mutex not locked"); - return CKR_MUTEX_NOT_LOCKED; + P11T_CHECK_FAIL("Mutex should not be locked"); + ret = CKR_MUTEX_NOT_LOCKED; } else if(res == EINVAL) { - p11t_msg_print("UnlockMutex: invalid mutex used"); - return CKR_MUTEX_BAD; + P11T_CHECK_FAIL("Mutex should be valid"); + ret = CKR_MUTEX_BAD; } else { - p11t_msg_print("UnlockMutex: failed: %d", res); - return CKR_GENERAL_ERROR; + p11t_check_warn("failed: %d", res); + ret = CKR_GENERAL_ERROR; } } @@ -251,14 +264,15 @@ unlock_mutex (void *mutex) { free(mutex); } - } #endif /* !_WIN32 */ + } - return CKR_OK; + p11t_msg_prefix(old); + return ret; } -void +int p11t_module_load(const char *filename) { CK_FUNCTION_LIST_PTR list; @@ -298,15 +312,16 @@ p11t_module_load(const char *filename) if(p11t_test_unexpected) { - /** C_GetFunctionList */ + P11T_SECTION("C_GetFunctionList"); + rv = (p11t_module_funcs->C_GetFunctionList)(&list); - if(rv != CKR_OK) - p11t_msg_print("C_GetFunctionList: call through function list failed: %s", p11t_msg_rv(rv)); + P11T_CHECK_RV("Call through function list", rv, CKR_OK); - /** - See if returns same data as library entry point */ if(!memcmp(list, p11t_module_funcs, sizeof(*list)) != 0) - p11t_msg_print("C_GetFunctionList: function lists returned directly and recursively differ"); + P11T_CHECK_FAIL("See if returns same data as library entry point"); } + + return CONTINUE; } static int @@ -314,50 +329,54 @@ initialize_common(const char *mode) { CK_RV rv; - /** C_Initialize **/ + P11T_SECTION("C_Initialize"); assert(p11t_module_funcs); - /** - Normal call */ rv = (p11t_module_funcs->C_Initialize) (&init_args); - if (rv != CKR_OK) + if(rv == CKR_CANT_LOCK) { - if(rv != CKR_CANT_LOCK) - p11t_msg_print("C_Initialize: failed (%s): %s", mode, p11t_msg_rv(rv)); + p11t_check_info("Module didn't accept %s", mode); return 0; } - else + + if(rv != CKR_OK) { - is_initialized = 1; - return 1; + p11t_check_fail("Couldn't initialize with %s: %s", mode, p11t_msg_rv(rv)); + return 0; } + + is_initialized = 1; + return 1; } -static void +static int initialize_locking_1(void) { - /** - Locking: no threads */ + P11T_CHECK_NOTE("Locking: no threads"); memset(&init_args, 0, sizeof (init_args)); init_args.pReserved = (void*)init_string; if(initialize_common("locking mode 1: no threads")) init_func = initialize_locking_1; + return CONTINUE; } -static void +static int initialize_locking_2(void) { - /** - Locking: os locking */ + P11T_CHECK_NOTE("Locking: os locking"); memset(&init_args, 0, sizeof (init_args)); init_args.flags = CKF_OS_LOCKING_OK; init_args.pReserved = (void*)init_string; if(initialize_common("locking mode 2: os locking")) init_func = initialize_locking_2; + return CONTINUE; } -static void +static int initialize_locking_3(void) { - /** - Locking: app locking */ + P11T_CHECK_NOTE("Locking: app locking"); memset(&init_args, 0, sizeof (init_args)); init_args.flags = 0; init_args.CreateMutex = create_mutex; @@ -367,12 +386,13 @@ initialize_locking_3(void) init_args.pReserved = (void*)init_string; if(initialize_common("locking mode 3: app locking")) init_func = initialize_locking_3; + return CONTINUE; } -static void +static int initialize_locking_4(void) { - /** - Locking: either locking */ + P11T_CHECK_NOTE("Locking: either locking"); memset(&init_args, 0, sizeof (init_args)); init_args.flags = CKF_OS_LOCKING_OK; init_args.CreateMutex = create_mutex; @@ -382,9 +402,10 @@ initialize_locking_4(void) init_args.pReserved = (void*)init_string; if(initialize_common("locking mode 4: either locking")) init_func = initialize_locking_4; + return CONTINUE; } -void +int p11t_module_initialize(void) { CK_INFO info; @@ -392,20 +413,22 @@ p11t_module_initialize(void) assert(p11t_module_funcs); + P11T_SECTION("C_Initialize"); + if(p11t_test_unexpected) { - /** - Calls without initializing */ rv = (p11t_module_funcs->C_GetInfo)(&info); - p11t_check_returns("C_GetInfo: shouldn't run without initialize", rv, CKR_CRYPTOKI_NOT_INITIALIZED); + P11T_CHECK_RV("Calls without initializing", rv, CKR_CRYPTOKI_NOT_INITIALIZED); - /** - NULL argument */ rv = (p11t_module_funcs->C_Initialize) (NULL); - p11t_check_returns("C_Initialize: should succeed with null argument", rv, CKR_OK); + P11T_CHECK_RV("Null argument", rv, CKR_OK); + is_initialized = 1; p11t_module_finalize(); } - /** - Multiple initialize with C_Finalize between */ + P11T_CHECK_NOTE("Multiple initialize with C_Finalize between"); + initialize_locking_1(); p11t_module_finalize(); initialize_locking_2(); @@ -417,55 +440,52 @@ p11t_module_initialize(void) /* Actually initialize with whatever succeeded last */ if(!init_func) - p11t_msg_fatal("C_Initialize: no initialize succeded cannot continue"); + p11t_msg_fatal("Couldn't initialize module via any method"); (init_func)(); if(!is_initialized) - p11t_msg_fatal("C_Initialize: couldn't initialize pkcs11 module"); + p11t_msg_fatal("Failed to initialize module"); if(p11t_test_unexpected) { - /** - Double initialize in a row */ rv = (p11t_module_funcs->C_Initialize) (&init_args); - if(rv != CKR_CRYPTOKI_ALREADY_INITIALIZED) - { - p11t_msg_print("C_Initialize: double initialize should return CKR_CRYPTOKI_ALREADY_INITIALIZED: %s", p11t_msg_rv(rv)); - } + P11T_CHECK_RV("Double initialize in a row", rv, CKR_CRYPTOKI_ALREADY_INITIALIZED); } is_initialized = 1; + return CONTINUE; } -void +int p11t_module_finalize(void) { CK_RV rv; - /** C_Finalize */ + P11T_SECTION("C_Finalize"); + if(is_initialized) { if(p11t_test_unexpected) { - /** - With invalid argument */ rv = p11t_module_funcs->C_Finalize(&rv); - p11t_check_returns("C_Finalize: bad argument", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("With invalid argument", rv, CKR_ARGUMENTS_BAD); } - /** - Normal call */ assert(p11t_module_funcs); rv = p11t_module_funcs->C_Finalize(NULL); - p11t_check_returns("C_Finalize", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); is_initialized = 0; } if(p11t_test_unexpected) { - /** - Double finalize in a row */ rv = p11t_module_funcs->C_Finalize(NULL); - p11t_check_returns("C_Finalize: double finalize", rv, CKR_CRYPTOKI_NOT_INITIALIZED); + P11T_CHECK_RV("Double finalize in a row", rv, CKR_CRYPTOKI_NOT_INITIALIZED); } + + return CONTINUE; } -void +int p11t_module_unload(void) { if(module) @@ -477,4 +497,5 @@ p11t_module_unload(void) #endif } module = NULL; + return CONTINUE; } @@ -108,7 +108,7 @@ p11t_msg_rv(CK_RV rv) CT(CKR_VENDOR_DEFINED) #undef CT default: - p11t_msg_print("unknown or invalid CK_RV value: 0x%08X", rv); + p11t_check_warn("unknown or invalid CK_RV value encountered: 0x%08X", rv); return ""; } } @@ -164,36 +164,44 @@ p11t_msg_va(const char *message, va_list va) } void -p11t_msg_print(const char *message, ...) +p11t_msg_code(const char *code, const char *message, va_list va) { - va_list va; - va_start(va, message); - p11t_msg_va(message, va); - va_end(va); + size_t len; + + fprintf(stdout, "%s: ", code); + if(the_prefix) + fprintf(stdout, "%s: ", the_prefix); + vfprintf(stdout, message, va); + len = strlen(message); + if(len && message[len - 1] != '\n') + fputc('\n', stdout); + fflush(stdout); } + void -p11t_msg_fatal(const char *message, ...) +p11t_msg_print(const char *message, ...) { va_list va; va_start(va, message); p11t_msg_va(message, va); va_end(va); - exit(1); } void -p11t_msg_exit(int code, const char *message, ...) +p11t_msg_fatal(const char *message, ...) { va_list va; va_start(va, message); p11t_msg_va(message, va); va_end(va); - exit(code); + exit(1); } -void +const char* p11t_msg_prefix(const char *prefix) { + const char *old = the_prefix; the_prefix = prefix; + return old; } diff --git a/src/object.c b/src/object.c index bce527c..c8acd77 100644 --- a/src/object.c +++ b/src/object.c @@ -11,32 +11,32 @@ * TESTS */ -static void -create_object(CK_SESSION_HANDLE session_rw, CK_SESSION_HANDLE session_ro) +static int +test_create_object(CK_SESSION_HANDLE session_rw, CK_SESSION_HANDLE session_ro) { - /** C_CreateObject */ - - /** - Not Implemented */ + P11T_SECTION("C_CreateObject"); + P11T_CHECK_NOTE("Not Tested"); + return CONTINUE; } -static void -copy_object(CK_SESSION_HANDLE session_rw, CK_SESSION_HANDLE session_ro) +static int +test_copy_object(CK_SESSION_HANDLE session_rw, CK_SESSION_HANDLE session_ro) { - /** C_CopyObject */ - - /** - Not Implemented */ + P11T_SECTION("C_CopyObject"); + P11T_CHECK_NOTE("Not Tested"); + return CONTINUE; } -static void -destroy_object(CK_SESSION_HANDLE session_rw, CK_SESSION_HANDLE session_ro) +static int +test_destroy_object(CK_SESSION_HANDLE session_rw, CK_SESSION_HANDLE session_ro) { - /** C_DestroyObject */ - - /** - Not Implemented */ + P11T_SECTION("C_DestroyObject"); + P11T_CHECK_NOTE("Not Tested"); + return CONTINUE; } -static void -find_objects(CK_SESSION_HANDLE session) +static int +test_find_objects(CK_SESSION_HANDLE session) { CK_OBJECT_HANDLE objects[1024]; CK_OBJECT_HANDLE extra; @@ -46,94 +46,84 @@ find_objects(CK_SESSION_HANDLE session) assert(p11t_module_funcs); - /** C_FindObjectsInit */ + P11T_SECTION("C_FindObjectsInit"); if(p11t_test_unexpected) { - /** - Invalid session */ rv = (p11t_module_funcs->C_FindObjectsInit)((CK_SESSION_HANDLE)-99, &dummy, 0); - p11t_check_returns("C_FindObjectsInit: invalid session", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Invalid session", rv, CKR_SESSION_HANDLE_INVALID); - /** - Attribute count without buffer */ rv = (p11t_module_funcs->C_FindObjectsInit)((CK_SESSION_HANDLE)-99, NULL, 1); - p11t_check_returns("C_FindObjectsInit: count without buffer", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Attribute count without buffer", rv, CKR_ARGUMENTS_BAD); } rv = (p11t_module_funcs->C_FindObjectsInit)(session, &dummy, 0); - p11t_check_returns("C_FindObjectsInit: all", rv, CKR_OK); + P11T_CHECK_RV("Find all objects", rv, CKR_OK); if(p11t_test_unexpected) { - /** - Double call. */ rv = (p11t_module_funcs->C_FindObjectsInit)(session, &dummy, 0); - p11t_check_returns("C_FindObjectsInit: all", rv, CKR_OPERATION_ACTIVE); + P11T_CHECK_RV("Double call", rv, CKR_OPERATION_ACTIVE); } - /** C_FindObjects */ + P11T_SECTION("C_FindObjects"); if(p11t_test_unexpected) { - /** - Invalid session */ rv = (p11t_module_funcs->C_FindObjects)((CK_SESSION_HANDLE)-99, NULL, 0, &object_count); - p11t_check_returns("C_FindObjects: invalid session", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Invalid session", rv, CKR_SESSION_HANDLE_INVALID); - /** - Null object count */ rv = (p11t_module_funcs->C_FindObjects)(session, NULL, 0, NULL); - p11t_check_returns("C_FindObjects: invalid session", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null object count", rv, CKR_ARGUMENTS_BAD); - /** - Retrieve a single object before remainder */ rv = (p11t_module_funcs->C_FindObjects)(session, objects, 1, &count); - p11t_check_returns("C_FindObjects: single object", rv, CKR_OK); + P11T_CHECK_RV("Retrieve a single object before remainder", rv, CKR_OK); if(count != 0) - p11t_check_ulong("C_FindObjects: should return one object", count, 1); + P11T_CHECK_ULONG("If asked for a single object, return one.", count, 1); } do { - /** - Retrieve remaining objects */ rv = (p11t_module_funcs->C_FindObjects)(session, objects, 1024, &count); - p11t_check_returns("C_FindObjects: all objects", rv, CKR_OK); + P11T_CHECK_RV("Retrieve remaining objects", rv, CKR_OK); } while(count == 1024); if(p11t_test_unexpected) { - /** - Extra call after retrieving all objects. */ rv = (p11t_module_funcs->C_FindObjects(session, &extra, 1, &count)); - p11t_check_returns("C_FindObjects: extra call", rv, CKR_OK); - p11t_check_ulong("C_FindObjects: should return no objects in extra call", count, 0); + P11T_CHECK_RV("Extra call after retrieving all objects", rv, CKR_OK); + P11T_CHECK_ULONG("Should return no objects in extra call", count, 0); } - /** C_FindObjectsFinal */ + P11T_SECTION("C_FindObjectsFinal"); if(p11t_test_unexpected) { - /** - Invalid session */ rv = (p11t_module_funcs->C_FindObjectsFinal)((CK_SESSION_HANDLE)-88); - p11t_check_returns("C_FindObjectsFinal: invalid session", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Invalid session", rv, CKR_SESSION_HANDLE_INVALID); } - /** - Normal call */ rv = (p11t_module_funcs->C_FindObjectsFinal)(session); - p11t_check_returns("C_FindObjectsFinal", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); if(p11t_test_unexpected) { - /** - Extra call */ rv = (p11t_module_funcs->C_FindObjectsFinal)(session); - p11t_check_returns("C_FindObjectsFinal: extra call", rv, CKR_OPERATION_NOT_INITIALIZED); + P11T_CHECK_RV("Extra call", rv, CKR_OPERATION_NOT_INITIALIZED); - /** C_FindObjects */ + P11T_SECTION("C_FindObjects"); - /** - Out of order call */ rv = (p11t_module_funcs->C_FindObjects)(session, &extra, 1, &count); - p11t_check_returns("C_FindObjectsFinal: extra call", rv, CKR_OPERATION_NOT_INITIALIZED); + P11T_CHECK_RV("Out of order call", rv, CKR_OPERATION_NOT_INITIALIZED); } + + return CONTINUE; } -static void +static int test_get_attribute_value(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) { CK_OBJECT_CLASS klass; @@ -144,43 +134,37 @@ test_get_attribute_value(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) assert(p11t_module_funcs); - /** C_GetAttributeValue */ + P11T_SECTION("C_GetAttributeValue"); attrs[0].type = CKA_CLASS; if(p11t_test_unexpected) { - /** - Invalid session */ rv = (p11t_module_funcs->C_GetAttributeValue)((CK_SESSION_HANDLE)-57, object, attrs, 1); - p11t_check_returns("C_GetAttributeValue: invalid session", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Invalid session", rv, CKR_SESSION_HANDLE_INVALID); - /** - Invalid object */ rv = (p11t_module_funcs->C_GetAttributeValue)(session, (CK_OBJECT_HANDLE)-58, attrs, 1); - p11t_check_returns("C_GetAttributeValue: invalid object", rv, CKR_OBJECT_HANDLE_INVALID); + P11T_CHECK_RV("Invalid object", rv, CKR_OBJECT_HANDLE_INVALID); - /** - No template */ rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, NULL, 0); - p11t_check_returns("C_GetAttributeValue: no template", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("No template", rv, CKR_ARGUMENTS_BAD); - /** - Buffer too small */ attrs[0].pValue = buffer; attrs[0].ulValueLen = 2; rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 1); - p11t_check_returns("C_GetAttributeValue: buffer too small", rv, CKR_BUFFER_TOO_SMALL); - p11t_check_ulong("C_GetAttributeValue: should return size", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); + P11T_CHECK_RV("Buffer too small", rv, CKR_BUFFER_TOO_SMALL); + P11T_CHECK_ULONG("Buffer too small should return size", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); } - /** - Retrieve attribute length */ attrs[0].pValue = NULL; attrs[0].ulValueLen = 0; rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 1); - p11t_check_returns("C_GetAttributeValue: get size", rv, CKR_OK); - p11t_check_ulong("C_GetAttributeValue: size of class", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); + P11T_CHECK_RV("Retrieve attribute length", rv, CKR_OK); + P11T_CHECK_ULONG("Size of object class attribute.", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); - /** - Retrieve single attribute */ attrs[0].pValue = buffer; rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 1); - p11t_check_returns("C_GetAttributeValue: get object", rv, CKR_OK); + P11T_CHECK_RV("Retrieve single attribute", rv, CKR_OK); /* The actual class of this object */ klass = *((CK_OBJECT_CLASS*)attrs[0].pValue); @@ -197,19 +181,17 @@ test_get_attribute_value(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) attrs[0].ulValueLen = attrs[1].ulValueLen = 0; attrs[0].pValue = attrs[0].pValue = NULL; - /** - With one invalid attribute, no buffer. */ rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 2); - p11t_check_returns("C_GetAttributeValue: with one invalid attribute", rv, CKR_ATTRIBUTE_TYPE_INVALID); - p11t_check_ulong("C_GetAttributeValue: should set invalid attribute to -1", attrs[0].ulValueLen, CK_INVALID); - p11t_check_ulong("C_GetAttributeValue: should set valid attribute to size", attrs[1].ulValueLen, sizeof(CK_OBJECT_CLASS)); + P11T_CHECK_RV("With one invalid attribute, no buffer", rv, CKR_ATTRIBUTE_TYPE_INVALID); + P11T_CHECK_ULONG("Should set invalid attribute to -1", attrs[0].ulValueLen, CK_INVALID); + P11T_CHECK_ULONG("Should set valid attribute to size", attrs[1].ulValueLen, sizeof(CK_OBJECT_CLASS)); - /** - With one invalid attribute, with buffer. */ attrs[1].pValue = buffer; rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 2); - p11t_check_returns("C_GetAttributeValue: with one invalid attribute, buffer", rv, CKR_ATTRIBUTE_TYPE_INVALID); - p11t_check_ulong("C_GetAttributeValue: should set invalid attribute to -1", attrs[0].ulValueLen, CK_INVALID); - p11t_check_ulong("C_GetAttributeValue: should set valid attribute to size", attrs[1].ulValueLen, sizeof(CK_OBJECT_CLASS)); - p11t_check_ulong("C_GetAttributeValue: should set valid attribute", *((CK_OBJECT_CLASS*)attrs[1].pValue), klass); + P11T_CHECK_RV("With one invalid attribute, with buffer", rv, CKR_ATTRIBUTE_TYPE_INVALID); + P11T_CHECK_ULONG("Should set invalid attribute to -1", attrs[0].ulValueLen, CK_INVALID); + P11T_CHECK_ULONG("Should set attribute size, in partially valid set", attrs[1].ulValueLen, sizeof(CK_OBJECT_CLASS)); + P11T_CHECK_ULONG("Should set valid attribute, in partially valid set", *((CK_OBJECT_CLASS*)attrs[1].pValue), klass); } /* @@ -227,7 +209,7 @@ test_get_attribute_value(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) case CKO_SECRET_KEY: break; default: - return; + return CONTINUE; } memset(attrs, 0, sizeof(attrs)); @@ -237,13 +219,12 @@ test_get_attribute_value(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) attrs[3].type = CKA_MODIFIABLE; attrs[4].type = CKA_LABEL; - /** - Multiple attributes, no buffer. */ rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 5); - p11t_check_returns("C_GetAttributeValue: multiple attrs, no buffer", rv, CKR_OK); - p11t_check_ulong("C_GetAttributeValue: CKA_CLASS size", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); - p11t_check_ulong("C_GetAttributeValue: CKA_TOKEN size", attrs[1].ulValueLen, sizeof(CK_BBOOL)); - p11t_check_ulong("C_GetAttributeValue: CKA_PRIVATE size", attrs[2].ulValueLen, sizeof(CK_BBOOL)); - p11t_check_ulong("C_GetAttributeValue: CKA_MODIFIABLE size", attrs[3].ulValueLen, sizeof(CK_BBOOL)); + P11T_CHECK_RV("Multiple attributes, no buffer", rv, CKR_OK); + P11T_CHECK_ULONG("Size of CKA_CLASS", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); + P11T_CHECK_ULONG("Size of CKA_TOKEN", attrs[1].ulValueLen, sizeof(CK_BBOOL)); + P11T_CHECK_ULONG("Size of CKA_PRIVATE", attrs[2].ulValueLen, sizeof(CK_BBOOL)); + P11T_CHECK_ULONG("Size of CKA_MODIFIABLE", attrs[3].ulValueLen, sizeof(CK_BBOOL)); if(attrs[4].ulValueLen) attrs[4].pValue = malloc(attrs[4].ulValueLen); @@ -253,41 +234,40 @@ test_get_attribute_value(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) if(p11t_test_unexpected) { - /** - Multiple attributes, some buffers */ rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 5); - p11t_check_returns("C_GetAttributeValue: multiple attrs, some buffer", rv, CKR_OK); - p11t_check_ulong("C_GetAttributeValue: CKA_CLASS no buffer, size", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); - p11t_check_bool("C_GetAttributeValue: CKA_TOKEN", *((CK_BBOOL*)attrs[1].pValue)); - p11t_check_bool("C_GetAttributeValue: CKA_PRIVATE", *((CK_BBOOL*)attrs[2].pValue)); - p11t_check_bool("C_GetAttributeValue: CKA_MODIFIABLE", *((CK_BBOOL*)attrs[3].pValue)); + P11T_CHECK_RV("Multiple attributes, some buffers", rv, CKR_OK); + P11T_CHECK_ULONG("Size of CKA_CLASS", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); + P11T_CHECK_BOOL("CKA_TOKEN boolean value", *((CK_BBOOL*)attrs[1].pValue)); + P11T_CHECK_BOOL("CKA_PRIVATE boolean value", *((CK_BBOOL*)attrs[2].pValue)); + P11T_CHECK_BOOL("CKA_MODIFIABLE boolean value", *((CK_BBOOL*)attrs[3].pValue)); attrs[0].pValue = buffer; attrs[0].ulValueLen = 2; - /** - Multiple attributes, one small buffer */ rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 5); - p11t_check_returns("C_GetAttributeValue: multiple attrs, one small buffer", rv, CKR_BUFFER_TOO_SMALL); - p11t_check_ulong("C_GetAttributeValue: CKA_CLASS no buffer, size", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); - p11t_check_bool("C_GetAttributeValue: CKA_TOKEN", *((CK_BBOOL*)attrs[1].pValue)); - p11t_check_bool("C_GetAttributeValue: CKA_PRIVATE", *((CK_BBOOL*)attrs[2].pValue)); - p11t_check_bool("C_GetAttributeValue: CKA_MODIFIABLE", *((CK_BBOOL*)attrs[3].pValue)); + P11T_CHECK_RV("Multiple attributes, one small buffer", rv, CKR_BUFFER_TOO_SMALL); + P11T_CHECK_ULONG("Size of CKA_CLASS", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); + P11T_CHECK_BOOL("CKA_TOKEN boolean value", *((CK_BBOOL*)attrs[1].pValue)); + P11T_CHECK_BOOL("CKA_PRIVATE boolean value", *((CK_BBOOL*)attrs[2].pValue)); + P11T_CHECK_BOOL("CKA_MODIFIABLE boolean value", *((CK_BBOOL*)attrs[3].pValue)); } attrs[0].pValue = buffer; attrs[0].ulValueLen = sizeof(CK_OBJECT_CLASS); - /** - Multiple attributes, with buffers */ rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, attrs, 5); - p11t_check_returns("C_GetAttributeValue: multiple attrs, with buffers", rv, CKR_OK); - p11t_check_ulong("C_GetAttributeValue: CKA_CLASS no buffer, size", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); - p11t_check_ulong("C_GetAttributeValue: CKA_CLASS value", *((CK_ULONG*)attrs[0].pValue), klass); - p11t_check_bool("C_GetAttributeValue: CKA_TOKEN", *((CK_BBOOL*)attrs[1].pValue)); - p11t_check_bool("C_GetAttributeValue: CKA_PRIVATE", *((CK_BBOOL*)attrs[2].pValue)); - p11t_check_bool("C_GetAttributeValue: CKA_MODIFIABLE", *((CK_BBOOL*)attrs[3].pValue)); - p11t_check_string("C_GetAttributeValue: CKA_LABEL", attrs[4].pValue, attrs[4].ulValueLen); + P11T_CHECK_RV("Multiple attributes, with buffers", rv, CKR_OK); + P11T_CHECK_ULONG("Size of CKA_CLASS", attrs[0].ulValueLen, sizeof(CK_OBJECT_CLASS)); + P11T_CHECK_ULONG("CKA_CLASS value", *((CK_ULONG*)attrs[0].pValue), klass); + P11T_CHECK_BOOL("CKA_TOKEN boolean value", *((CK_BBOOL*)attrs[1].pValue)); + P11T_CHECK_BOOL("CKA_PRIVATE boolean value", *((CK_BBOOL*)attrs[2].pValue)); + P11T_CHECK_BOOL("CKA_MODIFIABLE boolean value", *((CK_BBOOL*)attrs[3].pValue)); + P11T_CHECK_STRING("CKA_LABEL boolean value", attrs[4].pValue, attrs[4].ulValueLen); + + return CONTINUE; } -static void +static int test_objects(CK_SESSION_HANDLE session) { CK_OBJECT_HANDLE_PTR objects; @@ -298,18 +278,18 @@ test_objects(CK_SESSION_HANDLE session) objects = p11t_object_find(session, NULL, 0, &n_objects); if(!objects || !n_objects) - return; + return CONTINUE; for(i = 0; i < n_objects; ++i) { - /** C_GetObjectSize */ - - /** - Not Implemented */ + P11T_SECTION("C_GetObjectSize"); + P11T_CHECK_NOTE("Not Tested"); test_get_attribute_value(session, objects[i]); } free (objects); + return CONTINUE; } void @@ -330,22 +310,22 @@ p11t_object_tests(void) if(session_ro == CK_INVALID) continue; - find_objects(session_ro); + test_find_objects(session_ro); test_objects(session_ro); if(!p11t_session_login(session_ro)) continue; - find_objects(session_ro); + test_find_objects(session_ro); test_objects(session_ro); if(session_rw != CK_INVALID) { - find_objects(session_rw); + test_find_objects(session_rw); test_objects(session_rw); - create_object(session_rw, session_ro); - copy_object(session_rw, session_ro); - destroy_object(session_rw, session_ro); + test_create_object(session_rw, session_ro); + test_copy_object(session_rw, session_ro); + test_destroy_object(session_rw, session_ro); } p11t_session_close_all(slot); diff --git a/src/p11-tests.h b/src/p11-tests.h index 9be69da..525e964 100644 --- a/src/p11-tests.h +++ b/src/p11-tests.h @@ -28,10 +28,10 @@ const char* p11t_msg_rv(CK_RV rv); const char* p11t_msg_lasterr(void); void p11t_msg_va(const char *message, va_list va); +void p11t_msg_code(const char* code, const char *message, va_list va); void p11t_msg_print(const char *message, ...); void p11t_msg_fatal(const char *message, ...); -void p11t_msg_exit(int code, const char *message, ...); -void p11t_msg_prefix(const char *prefix); +const char* p11t_msg_prefix(const char *prefix); #define p11t_msg_here() \ (__func__ "() at " __FILE__ ":" __LINE__) @@ -40,26 +40,67 @@ void p11t_msg_prefix(const char *prefix); * check.c */ +enum +{ + STOP = 0, + CONTINUE = 1 +}; + +#define P11T_SECTION(check) \ + p11t_msg_prefix(check) + + +#define _P11T_BEGIN do { +#define _P11T_END } while(0) + +#define P11T_CHECK_FAIL(what) \ + _P11T_BEGIN p11t_check_fail("%s", (what)); return STOP; _P11T_END + int p11t_check_fail(const char *message, ...); +int p11t_check_warn(const char *message, ...); +int p11t_check_info(const char *message, ...); + +#define P11T_CHECK_RV(what, have, want) \ + _P11T_BEGIN if(!_p11t_check_rv((what), (have), (want))) return STOP; _P11T_END + +int _p11t_check_rv(const char *what, CK_RV have, CK_RV want); + +#define P11T_CHECK_PADDED(what, padded) \ + _P11T_BEGIN if(!_p11t_check_padded((what), (padded), sizeof(padded))) return STOP; _P11T_END + +int _p11t_check_padded(const char *what, const CK_UTF8CHAR_PTR padded, CK_ULONG length); + +#define P11T_CHECK_ULONG(what, have, want) \ + _P11T_BEGIN if(!_p11t_check_ulong((what), (have), (want))) return STOP; _P11T_END + +int _p11t_check_ulong(const char *what, CK_ULONG have, CK_ULONG want); + +#define P11T_CHECK_MASK(what, have, want) \ + _P11T_BEGIN if(!_p11t_check_mask((what), (have), (want))) return STOP; _P11T_END + +int _p11t_check_mask(const char *what, CK_ULONG flags, CK_ULONG mask); -int p11t_check_returns(const char *message, CK_RV have, CK_RV want); +#define P11T_CHECK_FLAG(what, have, want) \ + _P11T_BEGIN if(!_p11t_check_flag((what), (have), (want))) return STOP; _P11T_END -#define p11t_check_padded(msg, padded) \ - (p11t_check_padded_len((msg), (padded), sizeof(padded))) +int _p11t_check_flag(const char *what, CK_ULONG flags, CK_ULONG flag); -int p11t_check_padded_len(const char *message, const CK_UTF8CHAR_PTR padded, CK_ULONG length); +#define P11T_CHECK_NFLAG(what, have, want) \ + _P11T_BEGIN if(!_p11t_check_nflag((what), (have), (want))) return STOP; _P11T_END -int p11t_check_ulong(const char *message, CK_ULONG have, CK_ULONG want); +int _p11t_check_nflag(const char *what, CK_ULONG flags, CK_ULONG nflag); -int p11t_check_mask(const char *message, CK_ULONG flags, CK_ULONG mask); +#define P11T_CHECK_BOOL(what, value) \ + _P11T_BEGIN if(!_p11t_check_bool((what), (value))) return STOP; _P11T_END -int p11t_check_flag(const char *message, CK_ULONG flags, CK_ULONG flag); +int _p11t_check_bool(const char *what, CK_BBOOL value); -int p11t_check_nflag(const char *message, CK_ULONG flags, CK_ULONG nflag); +#define P11T_CHECK_STRING(what, value, length) \ + _P11T_BEGIN if(!_p11t_check_string((what), (value), (length))) return STOP; _P11T_END -int p11t_check_bool(const char *message, CK_BBOOL value); +int _p11t_check_string(const char *what, CK_UTF8CHAR_PTR value, CK_ULONG length); -int p11t_check_string(const char *message, CK_UTF8CHAR_PTR value, CK_ULONG length); +#define P11T_CHECK_NOTE(what) /* ------------------------------------------------------------------- * config.c @@ -86,11 +127,11 @@ extern CK_FUNCTION_LIST_PTR p11t_module_funcs; void p11t_module_config(const char *name, const char *value); -void p11t_module_load(const char *filename); -void p11t_module_unload(void); +int p11t_module_load(const char *filename); +int p11t_module_unload(void); -void p11t_module_initialize(void); -void p11t_module_finalize(void); +int p11t_module_initialize(void); +int p11t_module_finalize(void); /* ------------------------------------------------------------------- * object.c @@ -11,7 +11,7 @@ #include <openssl/objects.h> #include <openssl/x509.h> -static void +static int test_rsa_decrypt(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, CK_MECHANISM_TYPE mech_type, RSA* rsa) { @@ -23,8 +23,6 @@ test_rsa_decrypt(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, int size, n_encrypted; CK_RV rv; - /** C_Decrypt */ - data = p11t_test_data; n_data = p11t_test_data_size; @@ -37,36 +35,42 @@ test_rsa_decrypt(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, switch(mech_type) { case CKM_RSA_PKCS: - /** - CKM_RSA_PKCS */ + P11T_CHECK_NOTE("CKM_RSA_PKCS"); n_data = size - 11; n_encrypted = RSA_public_encrypt(n_data, data, encrypted, rsa, RSA_PKCS1_PADDING); assert(n_encrypted == size); break; case CKM_RSA_X_509: - /** - CKM_RSA_X_509 */ + P11T_CHECK_NOTE("CKM_RSA_X_509"); n_data = size; n_encrypted = RSA_public_encrypt(n_data, data, encrypted, rsa, RSA_NO_PADDING); assert(n_encrypted == size); break; default: - return; + return CONTINUE; }; mech.mechanism = mech_type; mech.pParameter = NULL; mech.ulParameterLen = 0; + P11T_SECTION("C_DecryptInit"); + rv = (p11t_module_funcs->C_DecryptInit)(session, &mech, key); - p11t_check_returns("C_DecryptInit: rsa", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); + + P11T_SECTION("C_Decrypt"); n_decrypted = sizeof(decrypted); rv = (p11t_module_funcs->C_Decrypt)(session, encrypted, n_encrypted, decrypted, &n_decrypted); - p11t_check_returns("C_Decrypt: rsa", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); if(n_decrypted != n_data) - p11t_check_fail("C_Decrypt: rsa decrypt failed, wrong length"); + P11T_CHECK_FAIL("RSA decrypt failed, wrong length"); if(memcmp(data, decrypted, n_data) != 0) - p11t_check_fail("C_Decrypt: rsa decrypt failed, bad data"); + P11T_CHECK_FAIL("RSA decrypt failed, mangled data"); + + return CONTINUE; } static void @@ -132,7 +136,7 @@ hash_for_rsa_pkcs_sign(int algo, int wrap, const CK_BYTE* data, *n_output = val; } -static void +static int test_rsa_pkcs_sign_hash(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, RSA* rsa, int algo) { @@ -151,12 +155,16 @@ test_rsa_pkcs_sign_hash(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, mech.pParameter = NULL; mech.ulParameterLen = 0; + P11T_SECTION("C_SignInit"); + rv = (p11t_module_funcs->C_SignInit)(session, &mech, key); - p11t_check_returns("C_SignInit: rsa pkcs", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); + + P11T_SECTION("C_Sign"); n_sig = sizeof(sig); rv = (p11t_module_funcs->C_Sign)(session, hash, n_hash, sig, &n_sig); - p11t_check_returns("C_Sign: rsa pkcs", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); /* Hash the data again this time without wrapping */ n_hash = sizeof(hash); @@ -165,10 +173,12 @@ test_rsa_pkcs_sign_hash(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, /* Verify the signature */ res = RSA_verify(algo, hash, n_hash, sig, n_sig, rsa); if(res != 1) - p11t_check_fail("C_Sign: rsa pkcs signature did not verify"); + P11T_CHECK_FAIL("RSA PKCS#1.5 or SSLv3 signature did not verify"); + + return CONTINUE; } -static void +static int test_rsa_x509_sign(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, RSA* rsa) { const CK_BYTE* data; @@ -188,48 +198,55 @@ test_rsa_x509_sign(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, RSA* rsa) mech.pParameter = NULL; mech.ulParameterLen = 0; + P11T_SECTION("C_SignInit"); + rv = (p11t_module_funcs->C_SignInit)(session, &mech, key); - p11t_check_returns("C_SignInit: rsa x509", rv, CKR_OK); + P11T_CHECK_RV("RSA X509 Call", rv, CKR_OK); + + P11T_SECTION("C_Sign"); n_sig = sizeof(sig); rv = (p11t_module_funcs->C_Sign)(session, (CK_BYTE*)data, n_data, sig, &n_sig); - p11t_check_returns("C_Sign: rsa x509", rv, CKR_OK); - p11t_check_ulong("C_Sign: rsa x509 result length", n_sig, size); + P11T_CHECK_RV("RSA X509 Call", rv, CKR_OK); + P11T_CHECK_ULONG("C_Sign: rsa x509 result length", n_sig, size); res = RSA_public_decrypt(n_sig, sig, check, rsa, RSA_NO_PADDING); if(res < 0) - p11t_check_fail("C_Sign: rsa x509 signature was invalid"); + P11T_CHECK_FAIL("RSA x509 signature was invalid"); assert(res > (int)n_data); if(memcmp(check + (res - n_data), data, n_data) != 0) - p11t_check_fail("C_Sign: rsa x509 signature did not verify"); + P11T_CHECK_FAIL("RSA x509 signature did not verify"); + + return CONTINUE; } -static void +static int test_rsa_sign(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, CK_MECHANISM_TYPE mech_type, RSA* rsa) { - /** C_Sign */ + P11T_SECTION("C_Sign"); switch(mech_type) { case CKM_RSA_PKCS: - /** - CKM_RSA_PKCS (SHA1) */ + P11T_CHECK_NOTE("CKM_RSA_PKCS (SHA1)"); test_rsa_pkcs_sign_hash(session, key, rsa, NID_sha1); - /** - CKM_RSA_PKCS (MD5) */ + P11T_CHECK_NOTE("CKM_RSA_PKCS (MD5)"); test_rsa_pkcs_sign_hash(session, key, rsa, NID_md5); - /** - CKM_RSA_PKCS (SHA1/MD5/SSL3) */ + P11T_CHECK_NOTE("CKM_RSA_PKCS (SHA1/MD5/SSL3)"); test_rsa_pkcs_sign_hash(session, key, rsa, NID_md5_sha1); break; case CKM_RSA_X_509: + P11T_CHECK_NOTE("CKM_RSA_X_509"); test_rsa_x509_sign(session, key, rsa); break; - default: - return; }; + + return CONTINUE; } -static void +static int test_rsa_private_key(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, CK_MECHANISM_TYPE mech_type) { @@ -246,11 +263,11 @@ test_rsa_private_key(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, attrs[1].pValue = &can_sign; if(!p11t_object_get(session, key, attrs, 2)) - return; + return CONTINUE; rsa = p11t_key_export_public_rsa(session, key); if(!rsa) - return; + return CONTINUE; if(can_decrypt) test_rsa_decrypt(session, key, mech_type, rsa); @@ -259,9 +276,11 @@ test_rsa_private_key(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, test_rsa_sign(session, key, mech_type, rsa); RSA_free(rsa); + + return CONTINUE; } -static void +static int test_rsa_encrypt(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, CK_MECHANISM_TYPE mech_type, RSA* rsa) { @@ -277,7 +296,7 @@ test_rsa_encrypt(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, data = p11t_test_data; n_data = p11t_test_data_size; - /** C_Encrypt */ + P11T_SECTION("C_Encrypt"); size = RSA_size(rsa); assert(size); @@ -288,51 +307,61 @@ test_rsa_encrypt(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, switch(mech_type) { case CKM_RSA_PKCS: - /** - CKM_RSA_PKCS */ + P11T_CHECK_NOTE("CKM_RSA_PKCS"); n_data = size - 11; break; case CKM_RSA_X_509: - /** - CKM_RSA_X_509 */ + P11T_CHECK_NOTE("CKM_RSA_X_509"); n_data = size; break; default: - return; + return CONTINUE; }; mech.mechanism = mech_type; mech.pParameter = NULL; mech.ulParameterLen = 0; + P11T_SECTION("C_EncryptInit"); + /* Now ask PKCS#11 to decrypt it */ rv = (p11t_module_funcs->C_EncryptInit)(session, &mech, key); - p11t_check_returns("C_EncryptInit: rsa", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); + + P11T_SECTION("C_Encrypt"); n_encrypted = sizeof(encrypted); rv = (p11t_module_funcs->C_Encrypt)(session, (CK_BYTE*)data, n_data, encrypted, &n_encrypted); - p11t_check_returns("C_Encrypt: rsa", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); if(size != n_encrypted) - p11t_check_fail("C_Encrypt: rsa encrypt failed, wrong length"); + P11T_CHECK_FAIL("RSA encrypt failed, wrong length"); /* We need to find a private key in order to validate */ privkey = p11t_key_get_private(session, key); if(privkey == CK_INVALID) - return; + return CONTINUE; + + P11T_SECTION("C_DecryptInit"); rv = (p11t_module_funcs->C_DecryptInit)(session, &mech, privkey); - p11t_check_returns("C_DecryptInit: rsa validate", rv, CKR_OK); + P11T_CHECK_RV("Module encrypted data", rv, CKR_OK); + + P11T_SECTION("C_Decrypt"); n_check = sizeof(check); rv = (p11t_module_funcs->C_Decrypt)(session, encrypted, n_encrypted, check, &n_check); - p11t_check_returns("C_Decrypt: rsa validate", rv, CKR_OK); + P11T_CHECK_RV("Module encrypted data", rv, CKR_OK); if(n_check != n_data) - p11t_check_fail("C_Decrypt: rsa validate failed, wrong length"); + P11T_CHECK_FAIL("RSA validate failed, wrong length"); if(memcmp(data, check, n_data) != 0) - p11t_check_fail("C_Decrypt: rsa validate failed, bad data"); + P11T_CHECK_FAIL("RSA validate failed, bad data"); + + return CONTINUE; } -static void +static int test_rsa_public_key(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, CK_MECHANISM_TYPE mech_type) { @@ -349,16 +378,18 @@ test_rsa_public_key(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, attrs[1].pValue = &can_verify; if(!p11t_object_get(session, key, attrs, 2)) - return; + return CONTINUE; rsa = p11t_key_export_public_rsa(session, key); if(!rsa) - return; + return CONTINUE; if(can_encrypt) test_rsa_encrypt(session, key, mech_type, rsa); RSA_free(rsa); + + return CONTINUE; } static void diff --git a/src/session.c b/src/session.c index 356fd8e..81e7dc6 100644 --- a/src/session.c +++ b/src/session.c @@ -20,41 +20,36 @@ p11t_session_config(const char *name, const char *value) * TESTS */ -void -session_info(CK_SESSION_HANDLE session, CK_SLOT_ID slot, CK_FLAGS flags, CK_STATE state) +static int +test_session_info(CK_SESSION_HANDLE session, CK_SLOT_ID slot, CK_FLAGS flags, CK_STATE state) { CK_SESSION_INFO info; CK_RV rv; if(session == CK_INVALID) - return; + return CONTINUE; - /** C_GetSessionInfo */ + P11T_SECTION("C_GetSessionInfo"); if(p11t_test_unexpected) { - /** - Invalid session */ rv = (p11t_module_funcs->C_GetSessionInfo)((CK_SESSION_HANDLE)-33, &info); - p11t_check_returns("C_GetSessionInfo: with invalid session", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Invalid session", rv, CKR_SESSION_HANDLE_INVALID); - /** - NULL arguments */ rv = (p11t_module_funcs->C_GetSessionInfo)(session, NULL); - p11t_check_returns("C_GetSessionInfo: with null", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null arguments", rv, CKR_ARGUMENTS_BAD); } - /** - Valid call */ rv = (p11t_module_funcs->C_GetSessionInfo)(session, &info); - if(!p11t_check_returns("C_GetSessionInfo", rv, CKR_OK)) - return; + P11T_CHECK_RV("Valid call", rv, CKR_OK); - /** - Valid slot id */ - p11t_check_ulong("CK_SESSION_INFO.slotID", info.slotID, slot); + P11T_SECTION("CK_SESSION_INFO"); - /** - Valid state for session */ - p11t_check_ulong("CK_SESSION_INFO.state", info.state, state); + P11T_CHECK_ULONG("slotID", info.slotID, slot); + P11T_CHECK_ULONG("state", info.state, state); + P11T_CHECK_FLAG("flags", info.flags, flags); - /** - Valid flags for session */ - p11t_check_flag("CK_SESSION_INFO.flags", info.flags, flags); + return CONTINUE; } static CK_UTF8CHAR_PTR @@ -82,8 +77,8 @@ calculate_pin(CK_SLOT_ID slot, CK_USER_TYPE user, CK_ULONG_PTR n_pin) return (CK_UTF8CHAR_PTR)pin; } -void -session_user_login(CK_SLOT_ID slot) +static int +test_session_user_login(CK_SLOT_ID slot) { CK_SESSION_HANDLE session_ro = CK_INVALID; CK_SESSION_HANDLE session_rw = CK_INVALID; @@ -94,58 +89,54 @@ session_user_login(CK_SLOT_ID slot) pin = calculate_pin(slot, CKU_USER, &n_pin); rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION, NULL, NULL, &session_ro); - p11t_check_returns("C_Login: open RO session", rv, CKR_OK); + P11T_CHECK_RV("C_Login: open RO session", rv, CKR_OK); rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session_rw); - p11t_check_returns("C_Login: open RW session", rv, CKR_OK); + P11T_CHECK_RV("C_Login: open RW session", rv, CKR_OK); /* Check the session state before login */ - session_info(session_ro, slot, CKF_SERIAL_SESSION, CKS_RO_PUBLIC_SESSION); - session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); + test_session_info(session_ro, slot, CKF_SERIAL_SESSION, CKS_RO_PUBLIC_SESSION); + test_session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); - /** C_Login */ + P11T_SECTION("C_Login"); if(p11t_test_unexpected) { - /** - Invalid session */ rv = (p11t_module_funcs->C_Login)((CK_ULONG)-55, CKU_USER, pin, n_pin); - p11t_check_returns("C_Login: invalid session", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Invalid session", rv, CKR_SESSION_HANDLE_INVALID); - /** - Invalid user type */ rv = (p11t_module_funcs->C_Login)(session_ro, CK_INVALID, pin, n_pin); - p11t_check_returns("C_Login: invalid user type", rv, CKR_USER_TYPE_INVALID); + P11T_CHECK_RV("Invalid user type", rv, CKR_USER_TYPE_INVALID); } - /** - Normal login */ rv = (p11t_module_funcs->C_Login)(session_ro, CKU_USER, pin, n_pin); if(rv == CKR_USER_TYPE_INVALID) - return; - if(!p11t_check_returns("C_Login", rv, CKR_OK)) - return; + return CONTINUE; + P11T_CHECK_RV("Normal login", rv, CKR_OK); - /** - Login changes all session state */ - session_info(session_ro, slot, CKF_SERIAL_SESSION, CKS_RO_USER_FUNCTIONS); - session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_USER_FUNCTIONS); + P11T_CHECK_NOTE("Login changes all session's state"); + test_session_info(session_ro, slot, CKF_SERIAL_SESSION, CKS_RO_USER_FUNCTIONS); + test_session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_USER_FUNCTIONS); - /** C_Logout */ + P11T_SECTION("C_Logout"); if(p11t_test_unexpected) { - /** - Invalid session */ rv = (p11t_module_funcs->C_Logout)((CK_ULONG)-55); - p11t_check_returns("C_Logout: invalid session", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Invalid session", rv, CKR_SESSION_HANDLE_INVALID); } - /** - Normal logout */ rv = (p11t_module_funcs->C_Logout)(session_rw); - p11t_check_returns("C_Logout", rv, CKR_OK); + P11T_CHECK_RV("Normal logout", rv, CKR_OK); - /** - Logout changes all session state */ - session_info(session_ro, slot, CKF_SERIAL_SESSION, CKS_RO_PUBLIC_SESSION); - session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); + P11T_CHECK_NOTE("Logout changes all session state"); + test_session_info(session_ro, slot, CKF_SERIAL_SESSION, CKS_RO_PUBLIC_SESSION); + test_session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); + + return CONTINUE; } -void -session_so_login(CK_SLOT_ID slot) +static int +test_session_so_login(CK_SLOT_ID slot) { CK_SESSION_HANDLE session_ro = CK_INVALID; CK_SESSION_HANDLE session_rw = CK_INVALID; @@ -156,53 +147,54 @@ session_so_login(CK_SLOT_ID slot) pin = calculate_pin(slot, CKU_SO, &n_pin); rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session_rw); - p11t_check_returns("C_OpenSession: open RW session", rv, CKR_OK); + P11T_CHECK_RV("C_OpenSession: open RW session", rv, CKR_OK); /* Check the session state before login */ - session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); + test_session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); - /** C_Login */ + P11T_SECTION("C_Login"); if(p11t_test_unexpected) { rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION, NULL, NULL, &session_ro); - p11t_check_returns("C_OpenSession: open RO session because SO", rv, CKR_OK); + P11T_CHECK_RV("Test opening RO session before login as SO", rv, CKR_OK); - /** - Login as SO not allowed with RO session */ rv = (p11t_module_funcs->C_Login)(session_ro, CKU_SO, pin, n_pin); - p11t_check_returns("C_Login: with RO as SO", rv, CKR_SESSION_READ_ONLY_EXISTS); + P11T_CHECK_RV("Login as SO not allowed with RO session", rv, CKR_SESSION_READ_ONLY_EXISTS); rv = (p11t_module_funcs->C_CloseSession)(session_ro); - p11t_check_returns("C_CloseSession: close RO session because SO", rv, CKR_OK); + P11T_CHECK_RV("Test closing RO session before login as SO", rv, CKR_OK); } - /** - Login as SO */ rv = (p11t_module_funcs->C_Login)(session_rw, CKU_SO, pin, n_pin); if(rv == CKR_USER_TYPE_INVALID) - return; - if(!p11t_check_returns("C_Login: as SO", rv, CKR_OK)) - return; + return CONTINUE; + P11T_CHECK_RV("Login as SO", rv, CKR_OK); - /** - Login changes all session state */ - session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_SO_FUNCTIONS); + P11T_CHECK_NOTE("SO login changes all session state"); + test_session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_SO_FUNCTIONS); if(p11t_test_unexpected) { - /** - Can't open RO session when logged in as SO */ + P11T_SECTION("C_OpenSession"); + rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION, NULL, NULL, &session_ro); - p11t_check_returns("C_OpenSession: open RO when SO logged in", rv, CKR_SESSION_READ_WRITE_SO_EXISTS); + P11T_CHECK_RV("Can't open RO session when logged in as SO", rv, CKR_SESSION_READ_WRITE_SO_EXISTS); } - /** - Logout from SO */ + P11T_SECTION("C_Logout"); + rv = (p11t_module_funcs->C_Logout)(session_rw); - p11t_check_returns("C_Logout", rv, CKR_OK); + P11T_CHECK_RV("Logout from SO", rv, CKR_OK); + + P11T_CHECK_NOTE("Logout SO changes goes back to public"); + test_session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); - /** - Logout SO changes goes back to public */ - session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); + return CONTINUE; } -void -session_main(CK_SLOT_ID slot) +static int +test_session_main(CK_SLOT_ID slot) { CK_SESSION_HANDLE session_ro = CK_INVALID; CK_SESSION_HANDLE session_rw = CK_INVALID; @@ -212,67 +204,56 @@ session_main(CK_SLOT_ID slot) assert(p11t_module_funcs); - /** C_OpenSession */ + P11T_SECTION("C_OpenSession"); if(p11t_test_unexpected) { - /** - Invalid slot */ rv = (p11t_module_funcs->C_OpenSession)((CK_SLOT_ID)-5, CKF_SERIAL_SESSION, NULL, NULL, &session_ro); - p11t_check_returns("C_OpenSession: with invalid slot", rv, CKR_SLOT_ID_INVALID); + P11T_CHECK_RV("Invalid slot", rv, CKR_SLOT_ID_INVALID); - /** - Null arguments */ rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION, NULL, NULL, NULL); - p11t_check_returns("C_OpenSession: with invalid slot", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null arguments", rv, CKR_ARGUMENTS_BAD); - /** - No flags */ rv = (p11t_module_funcs->C_OpenSession)(slot, 0, NULL, NULL, &session_ro); - p11t_check_returns("C_OpenSession: with 0 flags", rv, CKR_SESSION_PARALLEL_NOT_SUPPORTED); + P11T_CHECK_RV("No flags", rv, CKR_SESSION_PARALLEL_NOT_SUPPORTED); - /** - Without serial flag */ rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_RW_SESSION, NULL, NULL, &session_ro); - p11t_check_returns("C_OpenSession: with RW flags", rv, CKR_SESSION_PARALLEL_NOT_SUPPORTED); + P11T_CHECK_RV("Without serial flag", rv, CKR_SESSION_PARALLEL_NOT_SUPPORTED); } - /** - Valid flags */ rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION, NULL, NULL, &session_ro); - p11t_check_returns("C_OpenSession: with serial flags", rv, CKR_OK); + P11T_CHECK_RV("Valid flags", rv, CKR_OK); rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION, NULL, NULL, &session_ro2); - p11t_check_returns("C_OpenSession: with serial flags", rv, CKR_OK); + P11T_CHECK_RV("Valid flags", rv, CKR_OK); - /** - Read write session */ rv = (p11t_module_funcs->C_OpenSession)(slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session_rw); if(rv == CKR_TOKEN_WRITE_PROTECTED) session_rw = CK_INVALID; else - p11t_check_returns("C_OpenSession: with read write flags", rv, CKR_OK); + P11T_CHECK_RV("Read write session", rv, CKR_OK); /* Test all the sessions and validate their state */ - session_info(session_ro, slot, CKF_SERIAL_SESSION, CKS_RO_PUBLIC_SESSION); - session_info(session_ro2, slot, CKF_SERIAL_SESSION, CKS_RO_PUBLIC_SESSION); - session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); + test_session_info(session_ro, slot, CKF_SERIAL_SESSION, CKS_RO_PUBLIC_SESSION); + test_session_info(session_ro2, slot, CKF_SERIAL_SESSION, CKS_RO_PUBLIC_SESSION); + test_session_info(session_rw, slot, CKF_SERIAL_SESSION | CKF_RW_SESSION, CKS_RW_PUBLIC_SESSION); - /** C_CloseSession */ + P11T_SECTION("C_CloseSession"); if(p11t_test_unexpected) { - /** - Invalid session */ rv = (p11t_module_funcs->C_CloseSession)((CK_SESSION_HANDLE)-10); - p11t_check_returns("C_CloseSession: invalid handle", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Invalid session", rv, CKR_SESSION_HANDLE_INVALID); } if(session_ro != CK_INVALID) { - /** - Normal call */ rv = (p11t_module_funcs->C_CloseSession)(session_ro); - p11t_check_returns("C_CloseSession: valid", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); if(p11t_test_unexpected) { - /** - Check open session was closed */ rv = (p11t_module_funcs->C_GetSessionInfo)(session_ro, &info); - p11t_check_returns("C_GetSessionInfo: after close", rv, CKR_SESSION_HANDLE_INVALID); - - /** - Close twice */ + P11T_CHECK_RV("Check open session was closed", rv, CKR_SESSION_HANDLE_INVALID); /* * Note that CKR_SESSION_CLOSED is a valid return in this case. @@ -281,63 +262,61 @@ session_main(CK_SLOT_ID slot) */ rv = (p11t_module_funcs->C_CloseSession)(session_ro); - p11t_check_returns("C_CloseSession: valid", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Close twice", rv, CKR_SESSION_HANDLE_INVALID); } } if(session_rw != CK_INVALID) { rv = (p11t_module_funcs->C_CloseSession)(session_rw); - p11t_check_returns("C_CloseSession: read write", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); } - /** C_CloseAllSessions */ + P11T_SECTION("C_CloseAllSessions"); if(p11t_test_unexpected) { - /** - Invalid slot id */ rv = (p11t_module_funcs->C_CloseAllSessions)((CK_SLOT_ID)-34); - p11t_check_returns("C_CloseAllSessions: invalid slot", rv, CKR_SLOT_ID_INVALID); + P11T_CHECK_RV("Invalid slot id", rv, CKR_SLOT_ID_INVALID); } - /** - Normal call */ rv = (p11t_module_funcs->C_CloseAllSessions)(slot); - p11t_check_returns("C_CloseAllSessions", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); if(p11t_test_unexpected) { - /** - Check open session was closed */ rv = (p11t_module_funcs->C_GetSessionInfo)(session_ro2, &info); - p11t_check_returns("C_GetSessionInfo: after close all", rv, CKR_SESSION_HANDLE_INVALID); + P11T_CHECK_RV("Check open session was closed", rv, CKR_SESSION_HANDLE_INVALID); - /** - Call when no sessions open */ rv = (p11t_module_funcs->C_CloseAllSessions)(slot); - p11t_check_returns("C_CloseAllSessions", rv, CKR_OK); + P11T_CHECK_RV("Call when no sessions open", rv, CKR_OK); } + + return CONTINUE; } -void -session_pin(CK_SLOT_ID slot) +static int +test_session_pin(CK_SLOT_ID slot) { - /** C_InitPIN */ + P11T_SECTION("C_InitPIN"); + P11T_CHECK_NOTE("Not Tested"); - /** - Not Implemented */ + P11T_SECTION("C_SetPIN"); + P11T_CHECK_NOTE("Not Tested"); - /** C_SetPIN */ - - /** - Not Implemented */ + return CONTINUE; } -void -session_operation_state(CK_SLOT_ID slot) +static int +test_session_operation_state(CK_SLOT_ID slot) { - /** C_GetOperationState */ - - /** - Not Implemented */ + P11T_SECTION("C_GetOperationState"); + P11T_CHECK_NOTE("Not Tested"); - /** C_SetOperationState */ + P11T_SECTION("C_SetOperationState"); + P11T_CHECK_NOTE("Not Tested"); - /** - Not Implemented */ + return CONTINUE; } void @@ -348,10 +327,11 @@ p11t_session_tests() for(i = 0; i < p11t_slot_count; ++i) { CK_SLOT_ID slot = p11t_slot_get_id(i); - session_pin(slot); - session_main(slot); - session_user_login(slot); - session_so_login(slot); + test_session_pin(slot); + test_session_main(slot); + test_session_user_login(slot); + test_session_so_login(slot); + test_session_operation_state(slot); } } @@ -20,42 +20,38 @@ static CK_MECHANISM_INFO_PTR *slot_mech_info; * TESTS */ -void +static int test_slot_global(void) { CK_RV rv; - /** C_GetInfo */ + P11T_SECTION("C_GetInfo"); assert(p11t_module_funcs); if(p11t_test_unexpected) { - /** - NULL argument */ rv = (p11t_module_funcs->C_GetInfo)(NULL); - p11t_check_returns("C_GetInfo: null argument", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null argument", rv, CKR_ARGUMENTS_BAD); } /* Obvious crap fill */ memset(&slot_global, 0xFF, sizeof(CK_INFO)); - /** - Normal call */ rv = (p11t_module_funcs->C_GetInfo)(&slot_global); - if(!p11t_check_returns("C_GetInfo", rv, CKR_OK)) - { - memset(&slot_global, 0, sizeof(CK_INFO)); - return; - } + P11T_CHECK_RV("Normal call", rv, CKR_OK); - /** - Space padded strings in CK_INFO */ - p11t_check_padded("CK_INFO.manufacturerID", slot_global.manufacturerID); - p11t_check_padded("CK_INFO.libraryDescription", slot_global.libraryDescription); + P11T_SECTION("CK_INFO"); - /** - No flags set */ - p11t_check_ulong("CK_INFO.flags", slot_global.flags, 0); + P11T_CHECK_PADDED("manufacturerID", slot_global.manufacturerID); + P11T_CHECK_PADDED("libraryDescription", slot_global.libraryDescription); + + P11T_CHECK_ULONG("flags", slot_global.flags, 0); + + return CONTINUE; } -int +static int compar_slot_id(const void *one, const void *two) { CK_SLOT_ID a = *((CK_SLOT_ID*)one); @@ -67,7 +63,7 @@ compar_slot_id(const void *one, const void *two) return -1; } -void +static int test_slot_info(void) { CK_SLOT_ID_PTR present, only; @@ -75,25 +71,23 @@ test_slot_info(void) CK_ULONG i; CK_RV rv; - /** C_GetSlotList */ + P11T_SECTION("C_GetSlotList"); assert(p11t_module_funcs); if(p11t_test_unexpected) { - /** - NULL arguments */ rv = (p11t_module_funcs->C_GetSlotList)(FALSE, NULL, NULL); - p11t_check_returns("C_GetSlotList: null argument", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null arguments", rv, CKR_ARGUMENTS_BAD); } - /** - Retrieving the count */ rv = (p11t_module_funcs->C_GetSlotList)(FALSE, NULL, &p11t_slot_count); - p11t_check_returns("C_GetSlotList", rv, CKR_OK); + P11T_CHECK_RV("Retrieving the count", rv, CKR_OK); if(p11t_slot_count == 0) { - p11t_msg_print("C_GetSlotList: no slots to test"); - return; + p11t_check_info("no slots to test"); + return CONTINUE; } /* Allocate a bit extra. We're going to try and trip up module */ @@ -108,35 +102,29 @@ test_slot_info(void) if(p11t_test_unexpected) { - /** - Passing buffer space along with zero count. */ count = 0; rv = (p11t_module_funcs->C_GetSlotList)(FALSE, slot_ids, &count); - p11t_check_returns("C_GetSlotList: zero buffer", rv, CKR_BUFFER_TOO_SMALL); - p11t_check_ulong("C_GetSlotList: count invalid zero space passed", count, p11t_slot_count); + P11T_CHECK_RV("Passing buffer with zero count", rv, CKR_BUFFER_TOO_SMALL); + P11T_CHECK_ULONG("Resulting count when buffer with zero count passed", count, p11t_slot_count); if(p11t_slot_count > 1) { - /** - Passing buffer space along with low count. */ count = 1; rv = (p11t_module_funcs->C_GetSlotList)(FALSE, slot_ids, &count); - p11t_check_returns("C_GetSlotList: low buffer", rv, CKR_BUFFER_TOO_SMALL); - p11t_check_ulong("C_GetSlotList: count invalid when too little space passed", count, p11t_slot_count); + P11T_CHECK_RV("Passing buffer along with low count", rv, CKR_BUFFER_TOO_SMALL); + P11T_CHECK_ULONG("Resulting count when buffer with low count passed", count, p11t_slot_count); } } - /** - Passing too much buffer space. */ if(p11t_test_unexpected) count = p11t_slot_count + 5; else count = p11t_slot_count; rv = (p11t_module_funcs->C_GetSlotList)(FALSE, slot_ids, &count); - if(!p11t_check_returns("C_GetSlotList", rv, CKR_OK)) - { - p11t_slot_count = 0; - return; - } + P11T_CHECK_RV("Normal call", rv, CKR_OK); - p11t_check_ulong("C_GetSlotList: count invalid when too much space passed", count, p11t_slot_count); + if(p11t_test_unexpected) + P11T_CHECK_ULONG("Count invalid when too much buffer passed", count, p11t_slot_count); /* When we ask for just token valid ones, they should only be the ones we noted with flags */ present = calloc(p11t_slot_count, sizeof(CK_SLOT_ID)); @@ -147,54 +135,50 @@ test_slot_info(void) /* Now go through and load info about each slot */ for(i = 0; i < p11t_slot_count; ++i) { - /** C_GetSlotInfo */ + P11T_SECTION("C_GetSlotInfo"); if(p11t_test_unexpected) { - /** - NULL argument */ rv = (p11t_module_funcs->C_GetSlotInfo)(slot_ids[i], NULL); - p11t_check_returns("C_GetSlotInfo: null argument", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null argument", rv, CKR_ARGUMENTS_BAD); } - /** - Normal call */ rv = (p11t_module_funcs->C_GetSlotInfo)(slot_ids[i], &slot_info[i]); - p11t_check_returns("C_GetSlotInfo", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); + + P11T_SECTION("CK_SLOT_INFO"); - /** - Space padded CK_SLOT_INFO fields */ - p11t_check_padded("CK_SLOT_INFO.slotDescription", slot_info[i].slotDescription); - p11t_check_padded("CK_SLOT_INFO.manufacturerID", slot_info[i].manufacturerID); + P11T_CHECK_PADDED("slotDescription", slot_info[i].slotDescription); + P11T_CHECK_PADDED("manufacturerID", slot_info[i].manufacturerID); - /** - CK_SLOT_INFO flags are from valid set */ - p11t_check_mask("CK_SLOT_INFO.flags", slot_info[i].flags, + P11T_CHECK_MASK("flags", slot_info[i].flags, CKF_TOKEN_PRESENT | CKF_REMOVABLE_DEVICE | CKF_HW_SLOT); - /** - Track CKF_TOKEN_PRESENT flag and compare to C_GetSlotList(TRUE) */ + P11T_CHECK_NOTE("CKF_TOKEN_PRESENT flag is equivalent to C_GetSlotList(TRUE, ...)"); if((slot_info[i].flags & CKF_TOKEN_PRESENT) == CKF_TOKEN_PRESENT) { /* Note if token is present for later */ present[n_present++] = slot_ids[i]; - /** C_GetTokenInfo */ + P11T_SECTION("C_GetTokenInfo"); if(p11t_test_unexpected) { - /** - Null arguments */ rv = (p11t_module_funcs->C_GetTokenInfo)(slot_ids[i], NULL); - p11t_check_returns("C_GetTokenInfo: null arguments", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null arguments", rv, CKR_ARGUMENTS_BAD); } - /** - Normal call */ rv = (p11t_module_funcs->C_GetTokenInfo)(slot_ids[i], &slot_token_info[i]); - p11t_check_returns("C_GetTokenInfo", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); - /** - Space padded CK_TOKEN_INFO fields */ - p11t_check_padded("CK_TOKEN_INFO.label", slot_token_info[i].label); - p11t_check_padded("CK_TOKEN_INFO.manufacturerID", slot_token_info[i].manufacturerID); - p11t_check_padded("CK_TOKEN_INFO.model", slot_token_info[i].model); - p11t_check_padded("CK_TOKEN_INFO.serialNumber", slot_token_info[i].serialNumber); + P11T_SECTION("CK_TOKEN_INFO"); - /** - CK_TOKEN_INFO flags are from valid set */ - p11t_check_mask("CK_TOKEN_INFO.flags", slot_token_info[i].flags, + P11T_CHECK_PADDED("label", slot_token_info[i].label); + P11T_CHECK_PADDED("manufacturerID", slot_token_info[i].manufacturerID); + P11T_CHECK_PADDED("model", slot_token_info[i].model); + P11T_CHECK_PADDED("serialNumber", slot_token_info[i].serialNumber); + + P11T_CHECK_MASK("flags", slot_token_info[i].flags, CKF_RNG | CKF_WRITE_PROTECTED | CKF_LOGIN_REQUIRED | CKF_USER_PIN_INITIALIZED | CKF_RESTORE_KEY_NOT_NEEDED | CKF_CLOCK_ON_TOKEN | CKF_PROTECTED_AUTHENTICATION_PATH | CKF_DUAL_CRYPTO_OPERATIONS | CKF_TOKEN_INITIALIZED | CKF_SECONDARY_AUTHENTICATION | @@ -204,7 +188,7 @@ test_slot_info(void) /* Can't validate all the statistics, any number is valid */ - /** - Validate token time when CKF_CLOCK_ON_TOKEN */ + P11T_CHECK_NOTE("Validate token time when CKF_CLOCK_ON_TOKEN"); if((slot_token_info[i].flags & CKF_CLOCK_ON_TOKEN) == CKF_CLOCK_ON_TOKEN) { int year, month, day, hour, minute, second, extra, n; @@ -226,37 +210,43 @@ test_slot_info(void) second < 0 || second > 50 || extra != 0) { - p11t_msg_print("C_GetTokenInfo: invalid time on token: %s", buffer); + p11t_check_fail("C_GetTokenInfo: invalid time on token: %s", buffer); } } } else if(p11t_test_unexpected) { - /** - Calling on slot without token */ + P11T_SECTION("C_GetTokenInfo"); + rv = (p11t_module_funcs->C_GetTokenInfo)(slot_ids[i], &slot_token_info[i]); - p11t_check_returns("C_GetSlotInfo: without token", rv, CKR_TOKEN_NOT_PRESENT); + P11T_CHECK_RV("Calling on slot without token", rv, CKR_TOKEN_NOT_PRESENT); } } + P11T_SECTION("C_GetSlotList"); + rv = (p11t_module_funcs->C_GetSlotList)(TRUE, only, &n_only); - p11t_check_returns("C_GetSlotList: only tokens", rv, CKR_OK); + P11T_CHECK_RV("Listing only tokens", rv, CKR_OK); - p11t_check_ulong("C_GetSlotInfo: number of present tokens doesn't match token info flags. ie: CKF_TOKEN_PRESENT", n_only, n_present); + P11T_CHECK_ULONG("Number of present tokens doesn't match token info flags. ie: CKF_TOKEN_PRESENT", n_only, n_present); qsort(only, n_only, sizeof(CK_SLOT_ID), compar_slot_id); qsort(present, n_present, sizeof(CK_SLOT_ID), compar_slot_id); if(memcmp(only, present, sizeof(CK_SLOT_ID) * n_only) != 0) - p11t_msg_print("C_GetSlotInfo: present tokens don't match those in token info flags. ie: CKF_TOKEN_PRESENT"); + P11T_CHECK_FAIL("Present tokens don't match those in token info flags. ie: CKF_TOKEN_PRESENT"); + + return CONTINUE; } -void +static int test_slot_events(void) { - /** C_WaitForSlotEvent */ - /** - Not Implemented */ + P11T_SECTION("C_WaitForSlotEvent"); + P11T_CHECK_NOTE("Not Tested"); + return CONTINUE; } -void +static int test_slot_mechanisms(void) { CK_MECHANISM_TYPE_PTR mech_list; @@ -268,17 +258,16 @@ test_slot_mechanisms(void) assert(p11t_module_funcs); - /** C_GetMechanismList */ + P11T_SECTION("C_GetMechanismList"); if(!p11t_slot_count) - return; + return CONTINUE; if(p11t_test_unexpected) { - /* - Invalid Slot */ mech_count = 0; rv = (p11t_module_funcs->C_GetMechanismList)((CK_ULONG)-10, NULL, &mech_count); - p11t_check_returns("C_GetMechanismList: invalid slot id", rv, CKR_SLOT_ID_INVALID); + P11T_CHECK_RV("Invalid Slot", rv, CKR_SLOT_ID_INVALID); } slot_mech_count = calloc(p11t_slot_count, sizeof(CK_ULONG)); @@ -296,14 +285,12 @@ test_slot_mechanisms(void) if(p11t_test_unexpected) { - /** - Null arguments */ rv = (p11t_module_funcs->C_GetMechanismList)(slot_id, NULL, NULL); - p11t_check_returns("C_GetMechanismList: null arguments", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null arguments", rv, CKR_ARGUMENTS_BAD); } - /** - Without buffer */ rv = (p11t_module_funcs->C_GetMechanismList)(slot_id, NULL, &mech_count); - p11t_check_returns("C_GetMechanismList: without buffer", rv, CKR_OK); + P11T_CHECK_RV("Without buffer", rv, CKR_OK); mech_list = NULL; mech_info = NULL; @@ -315,67 +302,63 @@ test_slot_mechanisms(void) if(p11t_test_unexpected) { - /** - Zero count but buffer present */ value = 0; rv = (p11t_module_funcs->C_GetMechanismList)(slot_id, mech_list, &value); - p11t_check_returns("C_GetMechanismList: zero buffer", rv, CKR_BUFFER_TOO_SMALL); - p11t_check_ulong("C_GetMechanismList: should have number of mechs", value, mech_count); + P11T_CHECK_RV("Zero count but buffer present", rv, CKR_BUFFER_TOO_SMALL); + P11T_CHECK_ULONG("Should return number of mechs", value, mech_count); if(mech_count > 1) { - /** - Low count but buffer present */ value = 1; rv = (p11t_module_funcs->C_GetMechanismList)(slot_id, mech_list, &value); - p11t_check_returns("C_GetMechanismList: low buffer", rv, CKR_BUFFER_TOO_SMALL); - p11t_check_ulong("C_GetMechanismList: should have number of mechs", value, mech_count); + P11T_CHECK_RV("Low count but buffer present", rv, CKR_BUFFER_TOO_SMALL); + P11T_CHECK_ULONG("Should return number of mechs", value, mech_count); } } - /* - Call with too much buffer */ + /* - */ if(p11t_test_unexpected) value = mech_count + 5; else value = mech_count; rv = (p11t_module_funcs->C_GetMechanismList)(slot_id, mech_list, &value); - p11t_check_returns("C_GetMechanismList: high buffer", rv, CKR_OK); - p11t_check_ulong("C_GetMechanismList: should have number of mechs", value, mech_count); + P11T_CHECK_RV("Call with too much buffer", rv, CKR_OK); + P11T_CHECK_ULONG("Should return number of mechs", value, mech_count); mech_info = calloc(mech_count, sizeof(CK_MECHANISM_INFO)); assert(mech_info); - /** C_GetMechanismInfo */ + P11T_SECTION("C_GetMechanismInfo"); if(p11t_test_unexpected) { - /** - Invalid mechanism */ rv = (p11t_module_funcs->C_GetMechanismInfo)(slot_id, (CK_ULONG)-10, mech_info); - p11t_check_returns("C_GetMechanismInfo: with invalid mech", rv, CKR_MECHANISM_INVALID); + P11T_CHECK_RV("Invalid mechanism", rv, CKR_MECHANISM_INVALID); - /** - Null arguments */ rv = (p11t_module_funcs->C_GetMechanismInfo)(slot_id, mech_list[0], NULL); - p11t_check_returns("C_GetMechanismInfo: with null arg", rv, CKR_ARGUMENTS_BAD); + P11T_CHECK_RV("Null arguments", rv, CKR_ARGUMENTS_BAD); - /** - Invalid slot id */ rv = (p11t_module_funcs->C_GetMechanismInfo)((CK_ULONG)-11, mech_list[0], mech_info); - p11t_check_returns("C_GetMechanismInfo: with invalid slot", rv, CKR_SLOT_ID_INVALID); + P11T_CHECK_RV("Invalid slot id", rv, CKR_SLOT_ID_INVALID); } for(j = 0; j < mech_count; ++j) { - /** - Normal call */ rv = (p11t_module_funcs->C_GetMechanismInfo)(slot_id, mech_list[i], &mech_info[i]); - p11t_check_returns("C_GetMechanismInfo", rv, CKR_OK); + P11T_CHECK_RV("Normal call", rv, CKR_OK); + + P11T_SECTION("CK_MECHANISM_INFO"); if(mech_info[i].ulMinKeySize > mech_info[i].ulMaxKeySize) - p11t_msg_print("C_GetMechanismInfo: Mechanism min key size is greater than max"); + P11T_CHECK_FAIL("Mechanism min key size should not be greater than max"); - p11t_check_mask("CK_MECHANISM_INFO.flags", mech_info[i].flags, + P11T_CHECK_MASK("flags", mech_info[i].flags, CKF_HW | CKF_ENCRYPT | CKF_DECRYPT | CKF_DIGEST | CKF_SIGN | CKF_SIGN_RECOVER | CKF_VERIFY | CKF_VERIFY_RECOVER | CKF_GENERATE | CKF_GENERATE_KEY_PAIR | CKF_WRAP | CKF_UNWRAP | CKF_DERIVE); - p11t_check_nflag("CK_MECHANISM_INFO.flags", mech_info[i].flags, CKF_EXTENSION); + P11T_CHECK_NFLAG("flags", mech_info[i].flags, CKF_EXTENSION); } } @@ -384,14 +367,16 @@ test_slot_mechanisms(void) slot_mech_type[i] = mech_list; slot_mech_count[i] = mech_count; } + + return CONTINUE; } -void +static int test_init_token(void) { - /** C_InitToken */ - - /** - Not Implemented */ + P11T_SECTION("C_InitToken"); + P11T_CHECK_NOTE("Not Tested"); + return CONTINUE; } void |