Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
112 changes: 97 additions & 15 deletions apps/wolfsshd/auth.c
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,12 @@ struct WOLFSSHD_AUTH {
#endif

#ifndef MAX_LINE_SZ
#define MAX_LINE_SZ 900
/* Sized to hold the largest authorized_keys entry. */
#ifndef WOLFSSH_NO_MLDSA
#define MAX_LINE_SZ (WC_MLDSA_87_PUB_KEY_SIZE * 4 / 3 + 640)
#else
#define MAX_LINE_SZ 900
#endif
#endif
#ifndef MAX_PATH_SZ
#define MAX_PATH_SZ 80
Expand Down Expand Up @@ -174,11 +179,55 @@ static int CheckAuthKeysLine(char* line, word32 lineSz, const byte* key,
char* last = NULL;

enum {
NUM_BASE_TYPES = 5,
#ifdef WOLFSSH_CERTS
NUM_ALLOWED_TYPES = 9
NUM_CERT_TYPES = 4,
#else
NUM_ALLOWED_TYPES = 5
NUM_CERT_TYPES = 0,
#endif
#ifndef WOLFSSH_NO_MLDSA
#ifndef WOLFSSH_NO_MLDSA44
MLDSA44_COUNT = 1,
#else
MLDSA44_COUNT = 0,
#endif
#ifndef WOLFSSH_NO_MLDSA65
MLDSA65_COUNT = 1,
#else
MLDSA65_COUNT = 0,
#endif
#ifndef WOLFSSH_NO_MLDSA87
MLDSA87_COUNT = 1,
#else
MLDSA87_COUNT = 0,
#endif
NUM_MLDSA_TYPES = MLDSA44_COUNT + MLDSA65_COUNT + MLDSA87_COUNT,
#else
NUM_MLDSA_TYPES = 0,
#endif
#if !defined(WOLFSSH_NO_MLDSA) && defined(WOLFSSH_CERTS)
#ifndef WOLFSSH_NO_MLDSA44
MLDSA44_CERT_COUNT = 1,
#else
MLDSA44_CERT_COUNT = 0,
#endif
#ifndef WOLFSSH_NO_MLDSA65
MLDSA65_CERT_COUNT = 1,
#else
MLDSA65_CERT_COUNT = 0,
#endif
#ifndef WOLFSSH_NO_MLDSA87
MLDSA87_CERT_COUNT = 1,
#else
MLDSA87_CERT_COUNT = 0,
#endif
NUM_MLDSA_CERT_TYPES = MLDSA44_CERT_COUNT + MLDSA65_CERT_COUNT +
MLDSA87_CERT_COUNT,
#else
NUM_MLDSA_CERT_TYPES = 0,
#endif
NUM_ALLOWED_TYPES = NUM_BASE_TYPES + NUM_CERT_TYPES +
NUM_MLDSA_TYPES + NUM_MLDSA_CERT_TYPES
};
static const char* allowedTypes[NUM_ALLOWED_TYPES] = {
"ssh-rsa",
Expand All @@ -192,6 +241,28 @@ static int CheckAuthKeysLine(char* line, word32 lineSz, const byte* key,
"x509v3-ecdsa-sha2-nistp384",
"x509v3-ecdsa-sha2-nistp521",
#endif
#ifndef WOLFSSH_NO_MLDSA
#ifndef WOLFSSH_NO_MLDSA44
"ssh-mldsa-44",
#endif
#ifndef WOLFSSH_NO_MLDSA65
"ssh-mldsa-65",
#endif
#ifndef WOLFSSH_NO_MLDSA87
"ssh-mldsa-87",
#endif
#ifdef WOLFSSH_CERTS
#ifndef WOLFSSH_NO_MLDSA44
"x509v3-ssh-mldsa-44",
#endif
#ifndef WOLFSSH_NO_MLDSA65
"x509v3-ssh-mldsa-65",
#endif
#ifndef WOLFSSH_NO_MLDSA87
"x509v3-ssh-mldsa-87",
#endif
#endif
#endif
};
int typeOk = 0;
int i;
Expand Down Expand Up @@ -1573,6 +1644,11 @@ static int SetDefualtUserID(WOLFSSHD_AUTH* auth)
struct passwd* pwInfo;
int ret = WS_SUCCESS;

if (wolfSSHD_ConfigGetPrivilegeSeparation(auth->conf) ==
WOLFSSHD_PRIV_OFF) {
return WS_SUCCESS;
}

pwInfo = getpwnam(WOLFSSH_USER_STRING(WOLFSSH_SSHD_USER));
if (pwInfo == NULL) {
/* user name not found on system */
Expand Down Expand Up @@ -1665,24 +1741,30 @@ int wolfSSHD_AuthFreeUser(WOLFSSHD_AUTH* auth)
/* return WS_SUCCESS on success */
int wolfSSHD_AuthRaisePermissions(WOLFSSHD_AUTH* auth)
{
int ret = 0;
int ret = WS_SUCCESS;

wolfSSH_Log(WS_LOG_INFO, "[SSHD] Attempting to raise permissions level");
#ifndef WIN32
if (auth) {
if (setegid(auth->sGid) != 0) {
wolfSSH_Log(WS_LOG_ERROR, "[SSHD] Error raising gid");
ret = WS_FATAL_ERROR;
{
byte flag = 0;

if (!auth) {
return WS_BAD_ARGUMENT;
}

if (seteuid(auth->sUid) != 0) {
wolfSSH_Log(WS_LOG_ERROR, "[SSHD] Error raising uid");
ret = WS_FATAL_ERROR;
flag = wolfSSHD_ConfigGetPrivilegeSeparation(auth->conf);
if (flag == WOLFSSHD_PRIV_SEPARAT || flag == WOLFSSHD_PRIV_SANDBOX) {
wolfSSH_Log(WS_LOG_INFO, "[SSHD] Attempting to raise permissions level");
if (setegid(auth->sGid) != 0) {
wolfSSH_Log(WS_LOG_ERROR, "[SSHD] Error raising gid");
ret = WS_FATAL_ERROR;
}

if (seteuid(auth->sUid) != 0) {
wolfSSH_Log(WS_LOG_ERROR, "[SSHD] Error raising uid");
ret = WS_FATAL_ERROR;
}
}
}
else {
ret = WS_BAD_ARGUMENT;
}
#endif

return ret;
Expand Down
107 changes: 104 additions & 3 deletions examples/echoserver/echoserver.c
Original file line number Diff line number Diff line change
Expand Up @@ -1777,6 +1777,46 @@ static int load_key_ed25519(byte* buf, word32 bufSz)
#endif /* WOLFSSH_NO_ED25519 */


#ifndef WOLFSSH_NO_MLDSA44
static int load_key_mldsa44(byte* buf, word32 bufSz)
{
word32 sz = 0;
#ifndef NO_FILESYSTEM
sz = load_file("./keys/server-key-mldsa44.der", buf, &bufSz);
#else
(void)buf; (void)bufSz;
#endif
return sz;
}
#endif /* WOLFSSH_NO_MLDSA44 */

#ifndef WOLFSSH_NO_MLDSA65
static int load_key_mldsa65(byte* buf, word32 bufSz)
{
word32 sz = 0;
#ifndef NO_FILESYSTEM
sz = load_file("./keys/server-key-mldsa65.der", buf, &bufSz);
#else
(void)buf; (void)bufSz;
#endif
return sz;
}
#endif /* WOLFSSH_NO_MLDSA65 */

#ifndef WOLFSSH_NO_MLDSA87
static int load_key_mldsa87(byte* buf, word32 bufSz)
{
word32 sz = 0;
#ifndef NO_FILESYSTEM
sz = load_file("./keys/server-key-mldsa87.der", buf, &bufSz);
#else
(void)buf; (void)bufSz;
#endif
return sz;
}
#endif /* WOLFSSH_NO_MLDSA87 */


typedef struct StrList {
const char* str;
struct StrList* next;
Expand Down Expand Up @@ -2410,6 +2450,7 @@ static int wsUserAuth(byte authType,
PwMapList* list;
PwMap* map;
byte authHash[WC_SHA256_DIGEST_SIZE] = {0};
int userFound = 0;

if (ctx == NULL) {
fprintf(stderr, "wsUserAuth: ctx not set");
Expand Down Expand Up @@ -2530,12 +2571,12 @@ static int wsUserAuth(byte authType,
authData->type == map->type) {

if (authData->type == WOLFSSH_USERAUTH_PUBLICKEY) {
userFound = 1;
if (WMEMCMP(map->p, authHash, WC_SHA256_DIGEST_SIZE) == 0) {
return WOLFSSH_USERAUTH_SUCCESS;
}
else {
return WOLFSSH_USERAUTH_INVALID_PUBLICKEY;
}
/* Hash mismatch: continue checking other registered keys
* for this user (a user may have multiple public keys). */
}
else if (authData->type == WOLFSSH_USERAUTH_PASSWORD) {
if (WMEMCMP(map->p, authHash, WC_SHA256_DIGEST_SIZE) == 0) {
Expand Down Expand Up @@ -2578,6 +2619,8 @@ static int wsUserAuth(byte authType,
map = map->next;
}

if (userFound)
return WOLFSSH_USERAUTH_INVALID_PUBLICKEY;
return WOLFSSH_USERAUTH_INVALID_USER;
}

Expand Down Expand Up @@ -3151,6 +3194,64 @@ THREAD_RETURN WOLFSSH_THREAD echoserver_test(void* args)
#endif /* WOLFSSH_NO_ED25519 */
}

/* ML-DSA keys are loaded only when the key algo list explicitly
* includes an mldsa variant. They are larger than classical keys
* (~3900-4900 bytes) and sit at the top of the default canned list,
* so unconditionally loading them would shift negotiation to mldsa
* for all connections and break non-mldsa tests. */
#ifndef WOLFSSH_NO_MLDSA
if (keyList != NULL && WSTRSTR(keyList, "mldsa") != NULL) {
#define MLDSA_KEY_LOAD_BUF_SZ MLDSA_MAX_BOTH_KEY_DER_SIZE
byte* mldsaBuf = (byte*)WMALLOC(MLDSA_KEY_LOAD_BUF_SZ, NULL, 0);
if (mldsaBuf == NULL) {
ES_ERROR("Couldn't allocate ML-DSA key load buffer.\n");
}
else {
word32 mldsaSz;
const char* mldsaErrMsg = NULL;

#ifndef WOLFSSH_NO_MLDSA44
if (mldsaErrMsg == NULL) {
mldsaSz = load_key_mldsa44(mldsaBuf, MLDSA_KEY_LOAD_BUF_SZ);
if (mldsaSz == 0)
mldsaErrMsg = "Couldn't load ML-DSA-44 key file.\n";
else if (wolfSSH_CTX_UsePrivateKey_buffer(ctx, mldsaBuf,
mldsaSz, WOLFSSH_FORMAT_ASN1) < 0)
mldsaErrMsg = "Couldn't use ML-DSA-44 key buffer.\n";
}
#endif /* WOLFSSH_NO_MLDSA44 */

#ifndef WOLFSSH_NO_MLDSA65
if (mldsaErrMsg == NULL) {
mldsaSz = load_key_mldsa65(mldsaBuf, MLDSA_KEY_LOAD_BUF_SZ);
if (mldsaSz == 0)
mldsaErrMsg = "Couldn't load ML-DSA-65 key file.\n";
else if (wolfSSH_CTX_UsePrivateKey_buffer(ctx, mldsaBuf,
mldsaSz, WOLFSSH_FORMAT_ASN1) < 0)
mldsaErrMsg = "Couldn't use ML-DSA-65 key buffer.\n";
}
#endif /* WOLFSSH_NO_MLDSA65 */

#ifndef WOLFSSH_NO_MLDSA87
if (mldsaErrMsg == NULL) {
mldsaSz = load_key_mldsa87(mldsaBuf, MLDSA_KEY_LOAD_BUF_SZ);
if (mldsaSz == 0)
mldsaErrMsg = "Couldn't load ML-DSA-87 key file.\n";
else if (wolfSSH_CTX_UsePrivateKey_buffer(ctx, mldsaBuf,
mldsaSz, WOLFSSH_FORMAT_ASN1) < 0)
mldsaErrMsg = "Couldn't use ML-DSA-87 key buffer.\n";
}
#endif /* WOLFSSH_NO_MLDSA87 */

WFREE(mldsaBuf, NULL, 0);
if (mldsaErrMsg != NULL) {
ES_ERROR("%s", mldsaErrMsg);
}
}
#undef MLDSA_KEY_LOAD_BUF_SZ
}
#endif /* WOLFSSH_NO_MLDSA */

#ifndef NO_FILESYSTEM
if (userPubKey) {
byte* userBuf = NULL;
Expand Down
Loading
Loading