add UUID and FASC-N

pull/415/head
JacobBarthelmeh 2022-05-22 14:05:33 -07:00
parent 91f2ea7e97
commit c507c77431
4 changed files with 151 additions and 11 deletions

View File

@ -34,7 +34,9 @@
#include <wolfssl/wolfcrypt/hash.h>
#include <wolfssl/wolfcrypt/coding.h>
#include <wolfssl/wolfcrypt/wc_port.h>
#include <wolfssl/wolfcrypt/asn.h>
#include <wolfssl/wolfcrypt/asn_public.h>
#include <wolfssl/wolfcrypt/error-crypt.h>
#include <wolfssh/ssh.h>
#include <wolfssh/internal.h>
#include <wolfssh/wolfsftp.h>
@ -1854,6 +1856,18 @@ static int LoadPubKeyList(StrList* strList, int format, PwMapList* mapList)
}
static int wsUserAuthResult(byte res,
WS_UserAuthData* authData,
void* ctx)
{
printf("In auth result callback, auth = %s\n",
(res == WOLFSSH_USERAUTH_SUCCESS) ? "Success" : "Failure");
(void)authData;
(void)ctx;
return WS_SUCCESS;
}
static int wsUserAuth(byte authType,
WS_UserAuthData* authData,
void* ctx)
@ -1886,6 +1900,69 @@ static int wsUserAuth(byte authType,
wc_Sha256Hash(authData->sf.publicKey.publicKey,
authData->sf.publicKey.publicKeySz,
authHash);
#ifndef WOLFSSH_NO_FPKI
/* Display FPKI info UUID and FASC-N */
if (authData->sf.publicKey.isCert) {
DecodedCert cert;
byte* uuid;
word32 fascnSz;
word32 uuidSz;
word32 i;
printf("Peer connected with FPKI certificate\n");
wc_InitDecodedCert(&cert, authData->sf.publicKey.publicKey,
authData->sf.publicKey.publicKeySz, NULL);
ret = wc_ParseCert(&cert, CERT_TYPE, 0, NULL);
/* some profiles supported due not require FASC-N */
if (ret == 0 &&
wc_GetFASCNFromCert(&cert, NULL, &fascnSz) == LENGTH_ONLY_E) {
byte* fascn;
fascn = (byte*)WMALLOC(fascnSz, NULL, 0);
if (fascn != NULL &&
wc_GetFASCNFromCert(&cert, fascn, &fascnSz) == 0) {
printf("HEX of FASC-N :");
for (i = 0; i < fascnSz; i++)
printf("%02X", fascn[i]);
printf("\n");
}
if (fascn != NULL)
WFREE(fascn, NULL, 0);
}
/* all profiles supported must have a UUID */
if (ret == 0) {
ret = wc_GetUUIDFromCert(&cert, NULL, &uuidSz);
if (ret == LENGTH_ONLY_E) { /* expected error value */
ret = 0;
}
if (ret == 0 ) {
uuid = (byte*)WMALLOC(uuidSz, NULL, 0);
if (uuid == NULL) {
ret = WS_MEMORY_E;
}
}
if (ret == 0) {
ret = wc_GetUUIDFromCert(&cert, uuid, &uuidSz);
printf("UUID string : ");
for (i = 0; i < uuidSz; i++)
printf("%c", uuid[i]);
printf("\n");
}
if (uuid != NULL)
WFREE(uuid, NULL, 0);
}
/* failed to at least get UUID string */
if (ret != 0) {
return WOLFSSH_USERAUTH_INVALID_PUBLICKEY;
}
}
#endif
}
list = (PwMapList*)ctx;
@ -2147,6 +2224,7 @@ THREAD_RETURN WOLFSSH_THREAD echoserver_test(void* args)
wolfSSH_SetUserAuth(ctx, wsUserAuth);
else
wolfSSH_SetUserAuth(ctx, ((func_args*)args)->user_auth);
wolfSSH_SetUserAuthResult(ctx, wsUserAuthResult);
wolfSSH_CTX_SetBanner(ctx, echoserverBanner);
#ifdef WOLFSSH_AGENT
wolfSSH_CTX_set_agent_cb(ctx, wolfSSH_AGENT_DefaultActions, NULL);

View File

@ -181,12 +181,14 @@ int wolfSSH_CERTMAN_LoadRootCA_buffer(WOLFSSH_CERTMAN* cm,
}
#ifndef WOLFSSH_NO_FPKI
static int CheckProfile(DecodedCert* cert, int profile);
enum {
PROFILE_FPKI_WORKSHEET_6 = 6,
PROFILE_FPKI_WORKSHEET_10 = 10,
PROFILE_FPKI_WORKSHEET_16 = 16
};
#endif /* WOLFSSH_NO_FPKI */
int wolfSSH_CERTMAN_VerifyCert_buffer(WOLFSSH_CERTMAN* cm,
const unsigned char* cert, word32 certSz)
@ -236,6 +238,7 @@ int wolfSSH_CERTMAN_VerifyCert_buffer(WOLFSSH_CERTMAN* cm,
}
}
#ifndef WOLFSSH_NO_FPKI
if (ret == WS_SUCCESS) {
DecodedCert decoded;
@ -259,12 +262,14 @@ int wolfSSH_CERTMAN_VerifyCert_buffer(WOLFSSH_CERTMAN* cm,
FreeDecodedCert(&decoded);
}
#endif /* WOLFSSH_NO_FPKI */
WLOG_LEAVE(ret);
return ret;
}
#ifndef WOLFSSH_NO_FPKI
static int CheckProfile(DecodedCert* cert, int profile)
{
int valid = (cert != NULL);
@ -298,26 +303,33 @@ static int CheckProfile(DecodedCert* cert, int profile)
if (valid) {
valid = WSTRCMP(cert->countryOfCitizenship, "US") == 0;
if (valid != 1)
WLOG(WS_LOG_CERTMAN, "cert contry of citizenship invalid");
}
if (valid) {
valid = !cert->isCA;
if (valid != 1)
WLOG(WS_LOG_CERTMAN, "cert basic constraint invalid");
}
if (valid) {
valid =
WMEMCMP(cert->extAuthKeyId, cert->extSubjKeyId, KEYID_SIZE) != 0;
if (valid != 1)
WLOG(WS_LOG_CERTMAN, "cert auth key and subject key mismatch");
}
if (valid) {
valid =
((certPolicies[1] != NULL) &&
(WSTRCMP(certPolicies[1], cert->extCertPolicies[0]) == 0 ||
WSTRCMP(certPolicies[1], cert->extCertPolicies[1]) == 0)) ||
((certPolicies[0] != NULL) &&
(WSTRCMP(certPolicies[0], cert->extCertPolicies[0]) == 0 ||
WSTRCMP(certPolicies[0], cert->extCertPolicies[1]) == 0));
valid =
((certPolicies[1] != NULL) &&
(WSTRCMP(certPolicies[1], cert->extCertPolicies[0]) == 0 ||
WSTRCMP(certPolicies[1], cert->extCertPolicies[1]) == 0)) ||
((certPolicies[0] != NULL) &&
(WSTRCMP(certPolicies[0], cert->extCertPolicies[0]) == 0 ||
WSTRCMP(certPolicies[0], cert->extCertPolicies[1]) == 0));
if (valid != 1)
WLOG(WS_LOG_CERTMAN, "cert policy invalid");
}
/* validity period must be utc up to and including 2049, general time
@ -364,6 +376,41 @@ static int CheckProfile(DecodedCert* cert, int profile)
}
}
/* check on FASC-N and UUID */
if (valid) {
DNS_entry* current;
byte hasFascN = 0;
byte hasUUID = 0;
byte uuid[DEFAULT_UUID_SZ];
word32 uuidSz = DEFAULT_UUID_SZ;
/* cycle through alt names to check for needed types */
current = cert->altNames;
while (current != NULL) {
if (current->oidSum == FASCN_OID) {
hasFascN = 1;
}
current = current->next;
}
if (wc_GetUUIDFromCert(cert, uuid, &uuidSz) == 0) {
hasUUID = 1;
}
/* all must have UUID and worksheet 6 must have FASC-N in addition to
* UUID */
if (profile == PROFILE_FPKI_WORKSHEET_6 && hasFascN == 0) {
WLOG(WS_LOG_CERTMAN, "cert did not inclue a FASC-N");
valid = 0;
}
if (valid && hasUUID == 0) {
WLOG(WS_LOG_CERTMAN, "cert did not inclue a UUID");
valid = 0;
}
}
if (valid) {
valid =
/* Must include all in extKeyUsage */
@ -373,6 +420,9 @@ static int CheckProfile(DecodedCert* cert, int profile)
((extKeyUsageSsh == 0) ||
((cert->extExtKeyUsageSsh & extKeyUsageSsh)
== extKeyUsageSsh));
if (valid != 1) {
WLOG(WS_LOG_CERTMAN, "cert did not inclue all ext. key usage");
}
}
#ifdef DEBUG_WOLFSSH
@ -402,5 +452,6 @@ static int CheckProfile(DecodedCert* cert, int profile)
return valid;
}
#endif /* WOLFSSH_NO_FPKI */
#endif /* WOLFSSH_CERTS */

View File

@ -5054,6 +5054,7 @@ static int DoUserAuthRequestPublicKey(WOLFSSH* ssh, WS_UserAuthData* authData,
ret = GetSize(&l, pk->publicKey, pk->publicKeySz, &m);
pk->publicKeySz = l;
pk->publicKey = pk->publicKey + m;
pk->isCert = 1;
}
#endif /* WOLFSSH_CERTS */
@ -5216,10 +5217,19 @@ static int DoUserAuthRequestPublicKey(WOLFSSH* ssh, WS_UserAuthData* authData,
}
else {
if (ssh->ctx->userAuthResultCb) {
ssh->ctx->userAuthResultCb(WOLFSSH_USERAUTH_SUCCESS,
authData, ssh->userAuthResultCtx);
if (ssh->ctx->userAuthResultCb(WOLFSSH_USERAUTH_SUCCESS,
authData, ssh->userAuthResultCtx) != WS_SUCCESS) {
WLOG(WS_LOG_DEBUG, "DUARPK: user overriding success");
ret = SendUserAuthFailure(ssh, 0);
}
else {
ssh->clientState = CLIENT_USERAUTH_DONE;
}
}
else {
ssh->clientState = CLIENT_USERAUTH_DONE;
}
ssh->clientState = CLIENT_USERAUTH_DONE;
}
}
}

View File

@ -191,6 +191,7 @@ typedef struct WS_UserAuthData_PublicKey {
byte hasSignature;
const byte* signature;
word32 signatureSz;
byte isCert:1;
} WS_UserAuthData_PublicKey;
typedef struct WS_UserAuthData {