diff options
| author | Stef Walter <stef@memberwebs.com> | 2008-12-09 17:13:39 +0000 | 
|---|---|---|
| committer | Stef Walter <stef@memberwebs.com> | 2008-12-09 17:13:39 +0000 | 
| commit | c99cd6c23327788196dd96eb7b6a1718546a4cf0 (patch) | |
| tree | a90768fa7c54d2734176aaf366d558c62473d31f | |
| parent | d44882432b1534c8cfca3057ad59765a949adacc (diff) | |
Add testing of key objects.
| -rw-r--r-- | src/certificate.c | 33 | ||||
| -rw-r--r-- | src/key.c | 497 | ||||
| -rw-r--r-- | src/object.c | 47 | ||||
| -rw-r--r-- | src/p11-tests.c | 1 | ||||
| -rw-r--r-- | src/p11-tests.h | 4 | ||||
| -rw-r--r-- | src/slot.c | 18 | 
6 files changed, 590 insertions, 10 deletions
| diff --git a/src/certificate.c b/src/certificate.c index acb7b37..36e6b5b 100644 --- a/src/certificate.c +++ b/src/certificate.c @@ -17,7 +17,7 @@ test_x509_name(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object,  {  	CK_BYTE_PTR ptr, encoded;  	CK_ATTRIBUTE attr; -	X509_NAME* name; +	const char *msg;  	CK_RV rv;  	int len; @@ -40,13 +40,9 @@ test_x509_name(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object,  	if(rv != CKR_OK)  		return p11t_msg_rv(rv); -	/* Let openssl parse it */ -	ptr = attr.pValue; -	name = d2i_X509_NAME(NULL, (const unsigned char**)&ptr, attr.ulValueLen); -	if(name == NULL) -		return p11t_msg_openssl(); -	if(ptr - (CK_BYTE_PTR)attr.pValue != attr.ulValueLen) -		return "Extra trailing bytes"; +	msg = p11t_certificate_validate_dn(attr.pValue, attr.ulValueLen); +	if(msg != NULL) +		return msg;  	/* Serialize the compare one */  	len = i2d_X509_NAME(compare, NULL); @@ -63,8 +59,6 @@ test_x509_name(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object,  	free(attr.pValue);  	free(encoded); -	X509_NAME_free(name); -  	return NULL;  } @@ -355,3 +349,22 @@ p11t_certificate_tests(void)  		p11t_session_close(session);  	}  } + +const char* +p11t_certificate_validate_dn(CK_BYTE_PTR der, CK_ULONG n_der) +{ +	CK_BYTE_PTR ptr; +	X509_NAME* name; + +	/* Let openssl parse it */ +	ptr = der; +	name = d2i_X509_NAME(NULL, (const unsigned char**)&ptr, n_der); +	if(name == NULL) +		return p11t_msg_openssl(); +	if(ptr - der != n_der) +		return "Extra trailing bytes"; + +	X509_NAME_free(name); + +	return NULL; +} @@ -1,6 +1,503 @@  #include "p11-tests.h" +/* ---------------------------------------------------------------------------------- + * TESTS + */ + +static int +test_key_attributes(CK_SLOT_ID slot, CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object, CK_KEY_TYPE* key_type) +{ +	CK_BYTE buffer[4096]; +	CK_ATTRIBUTE attr; +	CK_MECHANISM_TYPE mech_type; +	CK_MECHANISM_TYPE_PTR mechanisms; +	CK_ULONG n_mechanisms, i; +	CK_BBOOL bval, local; +	CK_DATE date; +	CK_RV rv; + +	P11T_SECTION("Key Object"); + +	attr.type = CKA_KEY_TYPE; +	attr.ulValueLen = sizeof(*key_type); +	attr.pValue = key_type; +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_KEY_TYPE", rv, CKR_OK); + +	attr.type = CKA_ID; +	attr.ulValueLen = sizeof(buffer); +	attr.pValue = buffer; +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_ID", rv, CKR_OK); + +	attr.type = CKA_DERIVE; +	attr.ulValueLen = sizeof(bval); +	attr.pValue = &bval; +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_DERIVE", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_DERIVE", bval); + +	if(p11t_test_unexpected) +	{ +		attr.type = CKA_START_DATE; +		attr.ulValueLen = sizeof(date); +		attr.pValue = &date; +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		P11T_CHECK_RV("CKA_START_DATE", rv, CKR_OK); +		if(attr.ulValueLen > 0) +			P11T_CHECK_DATE("CKA_START_DATE", &date); + +		attr.type = CKA_END_DATE; +		attr.ulValueLen = sizeof(date); +		attr.pValue = &date; +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		P11T_CHECK_RV("CKA_END_DATE", rv, CKR_OK); +		if(attr.ulValueLen > 0) +			P11T_CHECK_DATE("CKA_END_DATE", &date); + +		attr.type = CKA_LOCAL; +		attr.ulValueLen = sizeof(local); +		attr.pValue = &local; +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		P11T_CHECK_RV("CKA_LOCAL", rv, CKR_OK); +		P11T_CHECK_BOOL("CKA_LOCAL", local); + +		attr.type = CKA_KEY_GEN_MECHANISM; +		attr.ulValueLen = sizeof(mech_type); +		attr.pValue = &mech_type; +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		P11T_CHECK_RV("CKA_KEY_GEN_MECHANISM", rv, CKR_OK); + +		/* Key was generated with this */ +		if(mech_type != CK_UNAVAILABLE_INFORMATION) +		{ +			if(!local) +				P11T_CHECK_FAIL_MSG("CKA_KEY_GEN_MECHANISM", "Non locally generated key has key gen mechanism"); +			if(!p11t_slot_get_mech_info(slot, mech_type)) +				P11T_CHECK_FAIL_MSG("CKA_KEY_GEN_MECHANISM", "Mechanism not present on slot"); +		} + +		attr.type = CKA_ALLOWED_MECHANISMS; +		attr.ulValueLen = sizeof(buffer); +		attr.pValue = buffer; +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		P11T_CHECK_RV("CKA_ALLOWED_MECHANISMS", rv, CKR_OK); + +		if(attr.ulValueLen % sizeof(CK_MECHANISM_TYPE) != 0) +			P11T_CHECK_FAIL_MSG("CKA_ALLOWED_MECHANISMS", "Invalid size memory returned"); + +		mechanisms = (CK_MECHANISM_TYPE_PTR)buffer; +		n_mechanisms = attr.ulValueLen / sizeof(CK_MECHANISM_TYPE); +		for(i = 0; i < n_mechanisms; ++i) +		{ +			if(!p11t_slot_get_mech_info(slot, mechanisms[i])) +				P11T_CHECK_FAIL_MSG("CKA_ALLOWED_MECHANISMS", "Mechanism not present in slot"); +		} +	} + +	return CONTINUE; +} + +static int +test_rsa_public(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) +{ +	CK_ATTRIBUTE attr; +	CK_BYTE modulus[16384]; +	CK_ULONG n_modulus; +	CK_BYTE exponent[1024]; +	CK_ULONG n_exponent; +	CK_ULONG bits; +	CK_RV rv; +	RSA* rsa; + +	P11T_SECTION("CKK_RSA Public"); + +	attr.type = CKA_MODULUS; +	attr.pValue = modulus; +	attr.ulValueLen = sizeof(modulus); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_MODULUS", rv, CKR_OK); +	n_modulus = attr.ulValueLen; + +	attr.type = CKA_PUBLIC_EXPONENT; +	attr.pValue = exponent; +	attr.ulValueLen = sizeof(exponent); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_PUBLIC_EXPONENT", rv, CKR_OK); +	n_exponent = attr.ulValueLen; + +	attr.type = CKA_MODULUS_BITS; +	attr.pValue = &bits; +	attr.ulValueLen = sizeof(bits); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_MODULUS_BITS", rv, CKR_OK); + +	rsa = RSA_new(); +	assert(rsa); +	rsa->n = BN_bin2bn(modulus, n_modulus, NULL); +	if(!rsa->n) +		P11T_CHECK_FAIL_MSG("CKA_MODULUS", "Couldn't parse"); +	rsa->e = BN_bin2bn(exponent, n_exponent, NULL); +	if(!rsa->e) +		P11T_CHECK_FAIL_MSG("CKA_PUBLIC_EXPONENT", "Couldn't parse"); + +	if(RSA_size(rsa) != bits / 8) +		P11T_CHECK_FAIL_MSG("CKA_MODULUS_BITS", "Does not match bits in actual modulus"); + +	return CONTINUE; +} + +static int +test_rsa_private(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) +{ +	CK_ATTRIBUTE attr; +	CK_BYTE buffer[32768]; +	CK_RV rv; +	RSA* rsa; + +	P11T_SECTION("CKK_RSA Private"); + +	rsa = RSA_new(); +	assert(rsa); + +	attr.type = CKA_MODULUS; +	attr.pValue = buffer; +	attr.ulValueLen = sizeof(buffer); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_MODULUS", rv, CKR_OK); +	rsa->n = BN_bin2bn(attr.pValue, attr.ulValueLen, NULL); +	if(rsa->n == NULL) +		P11T_CHECK_FAIL_MSG("CKA_MODULUS", p11t_msg_openssl()); + +	attr.type = CKA_PRIVATE_EXPONENT; +	attr.pValue = buffer; +	attr.ulValueLen = sizeof(buffer); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	if(rv == CKR_ATTRIBUTE_SENSITIVE) +		return CONTINUE; +	P11T_CHECK_RV("CKA_PRIVATE_EXPONENT", rv, CKR_OK); +	rsa->d = BN_bin2bn(attr.pValue, attr.ulValueLen, NULL); +	if(rsa->d == NULL) +		P11T_CHECK_FAIL_MSG("CKA_PRIVATE_EXPONENT", p11t_msg_openssl()); + +	if(p11t_test_unexpected) +	{ +		attr.type = CKA_PUBLIC_EXPONENT; +		attr.pValue = buffer; +		attr.ulValueLen = sizeof(buffer); +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		if(rv != CKR_ATTRIBUTE_SENSITIVE || rv != CKR_ATTRIBUTE_TYPE_INVALID) +		{ +			P11T_CHECK_RV("CKA_PUBLIC_EXPONENT", rv, CKR_OK); +			rsa->e = BN_bin2bn(attr.pValue, attr.ulValueLen, NULL); +			if(rsa->e == NULL) +				P11T_CHECK_FAIL_MSG("CKA_PUBLIC_EXPONENT", p11t_msg_openssl()); + +		} + +		attr.type = CKA_PRIME_1; +		attr.pValue = buffer; +		attr.ulValueLen = sizeof(buffer); +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		if(rv != CKR_ATTRIBUTE_SENSITIVE || rv != CKR_ATTRIBUTE_TYPE_INVALID) +		{ +			P11T_CHECK_RV("CKA_PRIME_1", rv, CKR_OK); +			rsa->p = BN_bin2bn(attr.pValue, attr.ulValueLen, NULL); +			if(rsa->p == NULL) +				P11T_CHECK_FAIL_MSG("CKA_PRIME_1", p11t_msg_openssl()); +		} + +		attr.type = CKA_PRIME_2; +		attr.pValue = buffer; +		attr.ulValueLen = sizeof(buffer); +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		if(rv != CKR_ATTRIBUTE_SENSITIVE || rv != CKR_ATTRIBUTE_TYPE_INVALID) +		{ +			P11T_CHECK_RV("CKA_PRIME_2", rv, CKR_OK); +			rsa->q = BN_bin2bn(attr.pValue, attr.ulValueLen, NULL); +			if(rsa->q == NULL) +				P11T_CHECK_FAIL_MSG("CKA_PRIME_2", p11t_msg_openssl()); +		} + +		attr.type = CKA_EXPONENT_1; +		attr.pValue = buffer; +		attr.ulValueLen = sizeof(buffer); +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		if(rv != CKR_ATTRIBUTE_SENSITIVE || rv != CKR_ATTRIBUTE_TYPE_INVALID) +		{ +			P11T_CHECK_RV("CKA_EXPONENT_1", rv, CKR_OK); +			rsa->dmp1 = BN_bin2bn(attr.pValue, attr.ulValueLen, NULL); +			if(rsa->dmp1 == NULL) +				P11T_CHECK_FAIL_MSG("CKA_EXPONENT_1", p11t_msg_openssl()); +		} + +		attr.type = CKA_EXPONENT_2; +		attr.pValue = buffer; +		attr.ulValueLen = sizeof(buffer); +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		if(rv != CKR_ATTRIBUTE_SENSITIVE || rv != CKR_ATTRIBUTE_TYPE_INVALID) +		{ +			P11T_CHECK_RV("CKA_EXPONENT_2", rv, CKR_OK); +			rsa->dmq1 = BN_bin2bn(attr.pValue, attr.ulValueLen, NULL); +			if(rsa->dmq1 == NULL) +				P11T_CHECK_FAIL_MSG("CKA_EXPONENT_2", p11t_msg_openssl()); +		} + +		attr.type = CKA_COEFFICIENT; +		attr.pValue = buffer; +		attr.ulValueLen = sizeof(buffer); +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		if(rv != CKR_ATTRIBUTE_SENSITIVE || rv != CKR_ATTRIBUTE_TYPE_INVALID) +		{ +			P11T_CHECK_RV("CKA_COEFFICIENT", rv, CKR_OK); +			rsa->iqmp = BN_bin2bn(attr.pValue, attr.ulValueLen, NULL); +			if(rsa->iqmp == NULL) +				P11T_CHECK_FAIL_MSG("CKA_COEFFICIENT", p11t_msg_openssl()); +		} +	} + +	/* Can we validate the key? */ +	assert(rsa->n && rsa->d); +	if(rsa->e && rsa->p && rsa->q) +	{ +		int res = RSA_check_key(rsa); +		if(res < 0) +			P11T_CHECK_FAIL_MSG("Check RSA private key", p11t_msg_openssl()); +		else if(res == 0) +			P11T_CHECK_FAIL_MSG("Check RSA private key", "RSA key is not valid"); +	} + +	return CONTINUE; +} + +static int +test_public_attributes(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) +{ +	CK_BYTE buffer[4096]; +	CK_ATTRIBUTE attr; +	CK_BBOOL bval, wrap; +	const char *msg; +	CK_RV rv; + +	P11T_SECTION("CKO_PUBLIC_KEY"); + +	attr.type = CKA_SUBJECT; +	attr.pValue = buffer; +	attr.ulValueLen = sizeof(buffer); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_SUBJECT", rv, CKR_OK); + +	if(attr.ulValueLen) +	{ +		msg = p11t_certificate_validate_dn(attr.pValue, attr.ulValueLen); +		if(msg != NULL) +			P11T_CHECK_FAIL_MSG("CKA_SUBJECT", msg); +	} + +	attr.type = CKA_ENCRYPT; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_ENCRYPT", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_ENCRYPT", bval); + +	attr.type = CKA_VERIFY; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_VERIFY", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_VERIFY", bval); + +	attr.type = CKA_VERIFY_RECOVER; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_VERIFY_RECOVER", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_VERIFY_RECOVER", bval); + +	attr.type = CKA_TRUSTED; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_TRUSTED", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_TRUSTED", bval); + +	attr.type = CKA_WRAP; +	attr.pValue = &wrap; +	attr.ulValueLen = sizeof(wrap); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_WRAP", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_WRAP", wrap); + +	return CONTINUE; +} + +static int +test_private_attributes(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE object) +{ +	CK_BYTE buffer[4096]; +	CK_ATTRIBUTE attr; +	CK_BBOOL bval; +	const char *msg; +	CK_RV rv; + +	P11T_SECTION("CKO_PRIVATE_KEY"); + +	attr.type = CKA_SUBJECT; +	attr.pValue = buffer; +	attr.ulValueLen = sizeof(buffer); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_SUBJECT", rv, CKR_OK); + +	if(attr.ulValueLen) +	{ +		msg = p11t_certificate_validate_dn(attr.pValue, attr.ulValueLen); +		if(msg != NULL) +			P11T_CHECK_FAIL_MSG("CKA_SUBJECT", msg); +	} + +	attr.type = CKA_SENSITIVE; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_SENSITIVE", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_SENSITIVE", bval); + +	attr.type = CKA_DECRYPT; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_DECRYPT", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_DECRYPT", bval); + +	attr.type = CKA_SIGN; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_SIGN", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_SIGN", bval); + +	attr.type = CKA_SIGN_RECOVER; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_SIGN_RECOVER", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_SIGN_RECOVER", bval); + +	attr.type = CKA_UNWRAP; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_UNWRAP", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_UNWRAP", bval); + +	attr.type = CKA_EXTRACTABLE; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_EXTRACTABLE", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_EXTRACTABLE", bval); + +	attr.type = CKA_ALWAYS_SENSITIVE; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_ALWAYS_SENSITIVE", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_ALWAYS_SENSITIVE", bval); + +	attr.type = CKA_NEVER_EXTRACTABLE; +	attr.pValue = &bval; +	attr.ulValueLen = sizeof(bval); +	rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +	P11T_CHECK_RV("CKA_NEVER_EXTRACTABLE", rv, CKR_OK); +	P11T_CHECK_BOOL("CKA_NEVER_EXTRACTABLE", bval); + +	if(p11t_test_unexpected) +	{ +		attr.type = CKA_WRAP_WITH_TRUSTED; +		attr.pValue = &bval; +		attr.ulValueLen = sizeof(bval); +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		P11T_CHECK_RV("CKA_WRAP_WITH_TRUSTED", rv, CKR_OK); +		P11T_CHECK_BOOL("CKA_WRAP_WITH_TRUSTED", bval); + +		attr.type = CKA_ALWAYS_AUTHENTICATE; +		attr.pValue = &bval; +		attr.ulValueLen = sizeof(bval); +		rv = (p11t_module_funcs->C_GetAttributeValue)(session, object, &attr, 1); +		P11T_CHECK_RV("CKA_ALWAYS_AUTHENTICATE", rv, CKR_OK); +		P11T_CHECK_BOOL("CKA_ALWAYS_AUTHENTICATE", bval); +	} + +	return CONTINUE; +} + +void +p11t_key_tests(void) +{ +	CK_OBJECT_CLASS klass; +	CK_OBJECT_HANDLE_PTR objects; +	CK_SESSION_HANDLE session; +	CK_OBJECT_HANDLE object; +	CK_ATTRIBUTE attrs[1]; +	CK_ULONG j, i, n_objects; +	CK_SLOT_ID slot; +	CK_KEY_TYPE key_type; + +	attrs[0].type = CKA_CLASS; +	attrs[0].ulValueLen = sizeof(klass); +	attrs[0].pValue = &klass; + +	for(j = 0; j < p11t_slot_count; ++j) +	{ +		slot = p11t_slot_get_id(j); +		session = p11t_session_open(slot, 0); +		if(!session) +			continue; + +		klass = CKO_PUBLIC_KEY; + +		objects = p11t_object_find(session, attrs, 1, &n_objects); +		for(i = 0; objects && i < n_objects; ++i) +		{ +			object = objects[i]; +			if(test_key_attributes(slot, session, object, &key_type)) +			{ +				test_public_attributes(session, object); +				if(key_type == CKK_RSA) +					test_rsa_public(session, object); +			} +		} +		free(objects); + +		if(p11t_session_login(session)) +		{ +			klass = CKO_PRIVATE_KEY; + +			objects = p11t_object_find(session, attrs, 1, &n_objects); +			for(i = 0; objects && i < n_objects; ++i) +			{ +				object = objects[i]; +				if(test_key_attributes(slot, session, object, &key_type)) +				{ +					test_private_attributes(session, object); +					if(key_type == CKK_RSA) +						test_rsa_private(session, object); +				} +			} +			free(objects); +		} + +		p11t_session_close(session); +	} +} + + +/* ---------------------------------------------------------------------------------- + * METHODS + */ +  CK_OBJECT_HANDLE  find_related_object(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE key, CK_OBJECT_CLASS klass)  { diff --git a/src/object.c b/src/object.c index 1b9427a..db82fbc 100644 --- a/src/object.c +++ b/src/object.c @@ -36,6 +36,51 @@ test_destroy_object(CK_SESSION_HANDLE session_rw, CK_SESSION_HANDLE session_ro)  }  static int +compar_object_handles(const void *one, const void *two) +{ +	CK_OBJECT_HANDLE a = *((CK_SLOT_ID*)one); +	CK_OBJECT_HANDLE b = *((CK_SLOT_ID*)two); +	if(a == b) +		return 0; +	if(a > b) +		return 1; +	return -1; +} + +static int +test_find_consistent(CK_SESSION_HANDLE session) +{ +	CK_OBJECT_HANDLE_PTR objects; +	CK_OBJECT_HANDLE_PTR check; +	CK_ULONG n_objects; +	CK_ULONG i, n_check; + +	objects = p11t_object_find(session, NULL, 0, &n_objects); +	if(!objects) +		return CONTINUE; + +	qsort(objects, n_objects, sizeof(CK_OBJECT_HANDLE), compar_object_handles); + +	for(i = 0; i < 10; ++i) +	{ +		check = p11t_object_find(session, NULL, 0, &n_check); +		if(check == NULL) +			P11T_CHECK_FAIL_MSG("Consistently finds same objects", "no objects found"); +		if(n_objects != n_check) +			P11T_CHECK_FAIL_MSG("Consistently finds same objects", "wrong number of objects found"); +		qsort(check, n_check, sizeof(CK_OBJECT_HANDLE), compar_object_handles); +		if(memcmp(objects, check, n_check * sizeof(CK_OBJECT_HANDLE)) != 0) +			P11T_CHECK_FAIL_MSG("Consistently finds same objects", "different objects found"); + +		free(check); +	} + +	free(objects); + +	return CONTINUE; +} + +static int  test_find_objects(CK_SESSION_HANDLE session)  {  	CK_OBJECT_HANDLE objects[1024]; @@ -311,6 +356,7 @@ p11t_object_tests(void)  			continue;  		test_find_objects(session_ro); +		test_find_consistent(session_ro);  		test_objects(session_ro);  		if(!p11t_session_login(session_ro)) @@ -322,6 +368,7 @@ p11t_object_tests(void)  		if(session_rw != CK_INVALID)  		{  			test_find_objects(session_rw); +			test_find_consistent(session_rw);  			test_objects(session_rw);  			test_create_object(session_rw, session_ro);  			test_copy_object(session_rw, session_ro); diff --git a/src/p11-tests.c b/src/p11-tests.c index 0d54172..7950fdd 100644 --- a/src/p11-tests.c +++ b/src/p11-tests.c @@ -63,6 +63,7 @@ main(int argc, char* argv[])  	p11t_slot_tests();  	p11t_session_tests();  	p11t_object_tests(); +	p11t_key_tests();  	p11t_certificate_tests();  	p11t_rsa_tests(); diff --git a/src/p11-tests.h b/src/p11-tests.h index efacace..ffca8f8 100644 --- a/src/p11-tests.h +++ b/src/p11-tests.h @@ -24,6 +24,8 @@ extern int p11t_test_unexpected;   * certificate.c   */ +const char* p11t_certificate_validate_dn(CK_BYTE_PTR der, CK_ULONG n_der); +  void p11t_certificate_tests(void);  /* ------------------------------------------------------------------- @@ -201,6 +203,8 @@ typedef void (*P11tSlotMechCallback)(CK_SLOT_ID slot, CK_MECHANISM_TYPE mech_typ  void p11t_slot_for_each_mech(CK_MECHANISM_TYPE mech_type, P11tSlotMechCallback callback); +CK_MECHANISM_INFO_PTR p11t_slot_get_mech_info(CK_SLOT_ID slot, CK_MECHANISM_TYPE mech_type); +  /* ------------------------------------------------------------------   * test-data.c   */ @@ -437,6 +437,24 @@ p11t_slot_get_token_info(CK_SLOT_ID slot)  	return NULL;  } +CK_MECHANISM_INFO_PTR +p11t_slot_get_mech_info(CK_SLOT_ID slot, CK_MECHANISM_TYPE mech) +{ +	int i; +	CK_ULONG j; + +	i = get_slot_index(slot); +	assert(i >= 0); + +	for(j = 0; j < slot_mech_count[i]; ++j) +	{ +		if(mech == slot_mech_type[i][j]) +			return &slot_mech_info[i][j]; +	} + +	return CK_FALSE; +} +  void  p11t_slot_for_each_mech(CK_MECHANISM_TYPE mech_type,                          P11tSlotMechCallback callback) | 
