Loading lib/ssh.c +39 −32 Original line number Diff line number Diff line Loading @@ -639,6 +639,43 @@ static CURLcode ssh_knownhost(struct connectdata *conn) return result; } static bool ssh_check_fingerprint(struct connectdata *conn) { struct ssh_conn *sshc = &conn->proto.sshc; struct SessionHandle *data = conn->data; const char *pubkey_md5 = data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5]; char md5buffer[33]; int i; const char *fingerprint = libssh2_hostkey_hash(sshc->ssh_session, LIBSSH2_HOSTKEY_HASH_MD5); /* The fingerprint points to static storage (!), don't free() it. */ for(i = 0; i < 16; i++) snprintf(&md5buffer[i*2], 3, "%02x", (unsigned char) fingerprint[i]); infof(data, "SSH MD5 fingerprint: %s\n", md5buffer); /* Before we authenticate we check the hostkey's MD5 fingerprint * against a known fingerprint, if available. */ if(pubkey_md5 && strlen(pubkey_md5) == 32) { if(!strequal(md5buffer, pubkey_md5)) { failf(data, "Denied establishing ssh session: mismatch md5 fingerprint. " "Remote %s is not equal to %s", md5buffer, pubkey_md5); state(conn, SSH_SESSION_FREE); sshc->actualcode = CURLE_PEER_FAILED_VERIFICATION; return sshc->actualcode; } else { infof(data, "MD5 checksum match!\n"); /* as we already matched, we skip the check for known hosts */ return CURLE_OK; } } else return ssh_knownhost(conn); } /* * ssh_statemach_act() runs the SSH state machine as far as it can without Loading @@ -654,10 +691,8 @@ static CURLcode ssh_statemach_act(struct connectdata *conn, bool *block) struct SSHPROTO *sftp_scp = data->state.proto.ssh; struct ssh_conn *sshc = &conn->proto.sshc; curl_socket_t sock = conn->sock[FIRSTSOCKET]; const char *fingerprint; char md5buffer[33]; char *new_readdir_line; int rc = LIBSSH2_ERROR_NONE, i; int rc = LIBSSH2_ERROR_NONE; int err; int seekerr = CURL_SEEKFUNC_OK; *block = 0; /* we're not blocking by default */ Loading Loading @@ -698,35 +733,7 @@ static CURLcode ssh_statemach_act(struct connectdata *conn, bool *block) * against our known hosts. How that is handled (reading from file, * whatever) is up to us. */ fingerprint = libssh2_hostkey_hash(sshc->ssh_session, LIBSSH2_HOSTKEY_HASH_MD5); /* The fingerprint points to static storage (!), don't free() it. */ for(i = 0; i < 16; i++) snprintf(&md5buffer[i*2], 3, "%02x", (unsigned char) fingerprint[i]); infof(data, "SSH MD5 fingerprint: %s\n", md5buffer); /* Before we authenticate we check the hostkey's MD5 fingerprint * against a known fingerprint, if available. */ if(data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5] && strlen(data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5]) == 32) { if(!strequal(md5buffer, data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5])) { failf(data, "Denied establishing ssh session: mismatch md5 fingerprint. " "Remote %s is not equal to %s", md5buffer, data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5]); state(conn, SSH_SESSION_FREE); result = sshc->actualcode = CURLE_PEER_FAILED_VERIFICATION; } else infof(data, "MD5 checksum match!\n"); /* as we already matched, we skip the check for known hosts */ } else result = ssh_knownhost(conn); result = ssh_check_fingerprint(conn); if(!result) state(conn, SSH_AUTHLIST); break; Loading Loading
lib/ssh.c +39 −32 Original line number Diff line number Diff line Loading @@ -639,6 +639,43 @@ static CURLcode ssh_knownhost(struct connectdata *conn) return result; } static bool ssh_check_fingerprint(struct connectdata *conn) { struct ssh_conn *sshc = &conn->proto.sshc; struct SessionHandle *data = conn->data; const char *pubkey_md5 = data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5]; char md5buffer[33]; int i; const char *fingerprint = libssh2_hostkey_hash(sshc->ssh_session, LIBSSH2_HOSTKEY_HASH_MD5); /* The fingerprint points to static storage (!), don't free() it. */ for(i = 0; i < 16; i++) snprintf(&md5buffer[i*2], 3, "%02x", (unsigned char) fingerprint[i]); infof(data, "SSH MD5 fingerprint: %s\n", md5buffer); /* Before we authenticate we check the hostkey's MD5 fingerprint * against a known fingerprint, if available. */ if(pubkey_md5 && strlen(pubkey_md5) == 32) { if(!strequal(md5buffer, pubkey_md5)) { failf(data, "Denied establishing ssh session: mismatch md5 fingerprint. " "Remote %s is not equal to %s", md5buffer, pubkey_md5); state(conn, SSH_SESSION_FREE); sshc->actualcode = CURLE_PEER_FAILED_VERIFICATION; return sshc->actualcode; } else { infof(data, "MD5 checksum match!\n"); /* as we already matched, we skip the check for known hosts */ return CURLE_OK; } } else return ssh_knownhost(conn); } /* * ssh_statemach_act() runs the SSH state machine as far as it can without Loading @@ -654,10 +691,8 @@ static CURLcode ssh_statemach_act(struct connectdata *conn, bool *block) struct SSHPROTO *sftp_scp = data->state.proto.ssh; struct ssh_conn *sshc = &conn->proto.sshc; curl_socket_t sock = conn->sock[FIRSTSOCKET]; const char *fingerprint; char md5buffer[33]; char *new_readdir_line; int rc = LIBSSH2_ERROR_NONE, i; int rc = LIBSSH2_ERROR_NONE; int err; int seekerr = CURL_SEEKFUNC_OK; *block = 0; /* we're not blocking by default */ Loading Loading @@ -698,35 +733,7 @@ static CURLcode ssh_statemach_act(struct connectdata *conn, bool *block) * against our known hosts. How that is handled (reading from file, * whatever) is up to us. */ fingerprint = libssh2_hostkey_hash(sshc->ssh_session, LIBSSH2_HOSTKEY_HASH_MD5); /* The fingerprint points to static storage (!), don't free() it. */ for(i = 0; i < 16; i++) snprintf(&md5buffer[i*2], 3, "%02x", (unsigned char) fingerprint[i]); infof(data, "SSH MD5 fingerprint: %s\n", md5buffer); /* Before we authenticate we check the hostkey's MD5 fingerprint * against a known fingerprint, if available. */ if(data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5] && strlen(data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5]) == 32) { if(!strequal(md5buffer, data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5])) { failf(data, "Denied establishing ssh session: mismatch md5 fingerprint. " "Remote %s is not equal to %s", md5buffer, data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5]); state(conn, SSH_SESSION_FREE); result = sshc->actualcode = CURLE_PEER_FAILED_VERIFICATION; } else infof(data, "MD5 checksum match!\n"); /* as we already matched, we skip the check for known hosts */ } else result = ssh_knownhost(conn); result = ssh_check_fingerprint(conn); if(!result) state(conn, SSH_AUTHLIST); break; Loading