TPrivateKey * LoadKey(TKeyType KeyType, const UnicodeString & FileName, const UnicodeString & Passphrase) { UTF8String UtfFileName = UTF8String(::ExpandEnvironmentVariables(FileName)); Filename * KeyFile = filename_from_str(UtfFileName.c_str()); AnsiString AnsiPassphrase = AnsiString(Passphrase); struct ssh2_userkey * Ssh2Key = nullptr; const char * ErrorStr = nullptr; switch (KeyType) { case ktSSH2: Ssh2Key = ssh2_load_userkey(KeyFile, (char *)AnsiPassphrase.c_str(), &ErrorStr); break; case ktOpenSSHPEM: case ktOpenSSHNew: case ktSSHCom: Ssh2Key = import_ssh2(KeyFile, KeyType, (char *)AnsiPassphrase.c_str(), &ErrorStr); break; default: DebugFail(); break; } Shred(AnsiPassphrase); if (Ssh2Key == nullptr) { UnicodeString Error = UnicodeString(ErrorStr); // While theoretically we may get "unable to open key file" and // so we should check system error code, // we actully never get here unless we call KeyType previously // and handle ktUnopenable accordingly. throw Exception(Error); } else if (Ssh2Key == SSH2_WRONG_PASSPHRASE) { throw Exception(LoadStr(AUTH_TRANSL_WRONG_PASSPHRASE)); } return reinterpret_cast<TPrivateKey *>(Ssh2Key); }
void load_key_file(HWND hwnd, struct MainDlgState *state, Filename filename, int was_import_cmd) { char passphrase[PASSPHRASE_MAXLEN]; int needs_pass; int type, realtype; int ret; char *comment; struct PassphraseProcStruct pps; struct RSAKey newkey1; struct ssh2_userkey *newkey2 = NULL; type = realtype = key_type(&filename); if (type != SSH_KEYTYPE_SSH1 && type != SSH_KEYTYPE_SSH2 && !import_possible(type)) { char msg[256]; sprintf(msg, "Couldn't load private key (%s)", key_type_to_str(type)); MessageBox(NULL, msg, "PuTTYgen Error", MB_OK | MB_ICONERROR); return; } if (type != SSH_KEYTYPE_SSH1 && type != SSH_KEYTYPE_SSH2) { realtype = type; type = import_target_type(type); } comment = NULL; if (realtype == SSH_KEYTYPE_SSH1) needs_pass = rsakey_encrypted(&filename, &comment); else if (realtype == SSH_KEYTYPE_SSH2) needs_pass = ssh2_userkey_encrypted(&filename, &comment); else needs_pass = import_encrypted(&filename, realtype, &comment); pps.passphrase = passphrase; pps.comment = comment; do { if (needs_pass) { int dlgret; dlgret = DialogBoxParam(hinst, MAKEINTRESOURCE(210), NULL, PassphraseProc, (LPARAM) & pps); if (!dlgret) { ret = -2; break; } } else *passphrase = '\0'; if (type == SSH_KEYTYPE_SSH1) { if (realtype == type) ret = loadrsakey(&filename, &newkey1, passphrase, NULL); else ret = import_ssh1(&filename, realtype, &newkey1, passphrase); } else { if (realtype == type) newkey2 = ssh2_load_userkey(&filename, passphrase, NULL); else newkey2 = import_ssh2(&filename, realtype, passphrase); if (newkey2 == SSH2_WRONG_PASSPHRASE) ret = -1; else if (!newkey2) ret = 0; else ret = 1; } } while (ret == -1); if (comment) sfree(comment); if (ret == 0) { MessageBox(NULL, "Couldn't load private key.", "PuTTYgen Error", MB_OK | MB_ICONERROR); } else if (ret == 1) { /* * Now update the key controls with all the * key data. */ { SetDlgItemText(hwnd, IDC_PASSPHRASE1EDIT, passphrase); SetDlgItemText(hwnd, IDC_PASSPHRASE2EDIT, passphrase); if (type == SSH_KEYTYPE_SSH1) { char buf[128]; char *savecomment; state->ssh2 = FALSE; state->commentptr = &state->key.comment; state->key = newkey1; /* * Set the key fingerprint. */ savecomment = state->key.comment; state->key.comment = NULL; rsa_fingerprint(buf, sizeof(buf), &state->key); state->key.comment = savecomment; SetDlgItemText(hwnd, IDC_FINGERPRINT, buf); /* * Construct a decimal representation * of the key, for pasting into * .ssh/authorized_keys on a Unix box. */ setupbigedit1(hwnd, IDC_KEYDISPLAY, IDC_PKSTATIC, &state->key); } else { char *fp; char *savecomment; state->ssh2 = TRUE; state->commentptr = &state->ssh2key.comment; state->ssh2key = *newkey2; /* structure copy */ sfree(newkey2); savecomment = state->ssh2key.comment; state->ssh2key.comment = NULL; fp = state->ssh2key.alg-> fingerprint(state->ssh2key.data); state->ssh2key.comment = savecomment; SetDlgItemText(hwnd, IDC_FINGERPRINT, fp); sfree(fp); setupbigedit2(hwnd, IDC_KEYDISPLAY, IDC_PKSTATIC, &state->ssh2key); } SetDlgItemText(hwnd, IDC_COMMENTEDIT, *state->commentptr); } /* * Finally, hide the progress bar and show * the key data. */ ui_set_state(hwnd, state, 2); state->key_exists = TRUE; /* * If the user has imported a foreign key * using the Load command, let them know. * If they've used the Import command, be * silent. */ if (realtype != type && !was_import_cmd) { char msg[512]; sprintf(msg, "Successfully imported foreign key\n" "(%s).\n" "To use this key with PuTTY, you need to\n" "use the \"Save private key\" command to\n" "save it in PuTTY's own format.", key_type_to_str(realtype)); MessageBox(NULL, msg, "PuTTYgen Notice", MB_OK | MB_ICONINFORMATION); } } }
int main(int argc, char **argv) { Filename *infilename = NULL; int intype = SSH_KEYTYPE_UNOPENABLE; int encrypted = 0; char* origcomment = 0; char* line = 0; char* passphrase = 0; struct ssh2_userkey *ssh2key = NULL; char* fingerprint = 0; printf("fzputtygen\n"); printf("Copyright (C) 2008-2016 Tim Kosse\n"); printf("Based on PuTTY's puttygen\n"); printf("Copyright (C) 1997-2015 Simon Tatham and the PuTTY team\n"); printf("Converts private SSH keys into PuTTY's format.\n"); printf("This program is used by FileZilla and not intended to be used directly.\n"); printf("Use the puttygen tool from PuTTY for a human-usable tool.\n"); printf("\n"); fflush(stdout); while (1) { sfree(line); line = fgetline(stdin); if (!line || !*line || *line == '\n') break; line[strlen(line) - 1] = 0; char* cmd = line, *args = line; while (*args) { if (*args == ' ') { *(args++) = 0; break; } args++; } if (!*args) args = 0; if (!strcmp(cmd, "file")) { char const* ret = NULL; if (ssh2key) { ssh2key->alg->freekey(ssh2key->data); sfree(ssh2key); ssh2key = 0; } sfree(passphrase); passphrase = 0; sfree(fingerprint); fingerprint = 0; if (!args) { fzprintf(sftpError, "No argument given"); continue; } if (infilename) { filename_free(infilename); } infilename = filename_from_str(args); intype = key_type(infilename); switch (intype) { case SSH_KEYTYPE_SSH1: ret = "incompatible"; intype = SSH_KEYTYPE_UNOPENABLE; break; case SSH_KEYTYPE_SSH2: ret = "ok"; encrypted = ssh2_userkey_encrypted(infilename, &origcomment); break; case SSH_KEYTYPE_UNKNOWN: case SSH_KEYTYPE_UNOPENABLE: default: ret = "error"; intype = SSH_KEYTYPE_UNOPENABLE; break; case SSH_KEYTYPE_OPENSSH_PEM: case SSH_KEYTYPE_OPENSSH_NEW: case SSH_KEYTYPE_SSHCOM: encrypted = import_encrypted(infilename, intype, &origcomment); ret = encrypted ? "convertible" : "ok"; break; } fzprintf(sftpReply, "%s", ret); } else if (!strcmp(cmd, "encrypted")) { if (intype == SSH_KEYTYPE_UNOPENABLE) { fzprintf(sftpError, "No key file opened"); continue; } fzprintf(sftpReply, "%d", encrypted ? 1 : 0); } else if (!strcmp(cmd, "comment")) { if (intype == SSH_KEYTYPE_UNOPENABLE) { fzprintf(sftpError, "No key file opened"); continue; } if (ssh2key && ssh2key->comment) { fzprintf(sftpReply, "%s", ssh2key->comment); } else if (origcomment) fzprintf(sftpReply, "%s", origcomment); else fzprintf(sftpReply, ""); } else if (!strcmp(cmd, "password")) { const char* error = NULL; if (!args) { fzprintf(sftpError, "No argument given"); continue; } if (intype == SSH_KEYTYPE_UNOPENABLE) { fzprintf(sftpError, "No key file opened"); continue; } if (!encrypted) { fzprintf(sftpError, "File is not encrypted"); continue; } if (ssh2key) { fzprintf(sftpError, "Already opened file"); continue; } sfree(passphrase); passphrase = strdup(args); switch (intype) { case SSH_KEYTYPE_SSH2: ssh2key = ssh2_load_userkey(infilename, passphrase, &error); break; case SSH_KEYTYPE_OPENSSH_PEM: case SSH_KEYTYPE_OPENSSH_NEW: case SSH_KEYTYPE_SSHCOM: ssh2key = import_ssh2(infilename, intype, passphrase, &error); break; default: break; } if (ssh2key == SSH2_WRONG_PASSPHRASE) { error = "wrong passphrase"; ssh2key = 0; } if (ssh2key) { error = NULL; } else if (!error) { error = "unknown error"; } if (error) fzprintf(sftpError, "Error loading file: %s", error); else fzprintf(sftpReply, ""); } else if (!strcmp(cmd, "fingerprint")) { const char* error = 0; if (!fingerprint) { if (ssh2key) { fingerprint = ssh2_fingerprint(ssh2key->alg, ssh2key->data); } else { switch (intype) { case SSH_KEYTYPE_SSH2: { void* ssh2blob; int bloblen = 0; char* comment = NULL; ssh2blob = ssh2_userkey_loadpub(infilename, 0, &bloblen, &comment, &error); if (ssh2blob) { fingerprint = ssh2_fingerprint_blob(ssh2blob, bloblen); sfree(ssh2blob); } else if (!error) { error = "unknown error"; } if (comment) { sfree(origcomment); origcomment = comment; } break; } case SSH_KEYTYPE_OPENSSH_PEM: case SSH_KEYTYPE_OPENSSH_NEW: case SSH_KEYTYPE_SSHCOM: ssh2key = import_ssh2(infilename, intype, "", &error); if (ssh2key) { if (ssh2key != SSH2_WRONG_PASSPHRASE) { error = NULL; fingerprint = ssh2_fingerprint(ssh2key->alg, ssh2key->data); } else { ssh2key = NULL; error = "wrong passphrase"; } } else if (!error) error = "unknown error"; break; default: error = "No file loaded"; break; } } } if (!fingerprint && !error) { error = "Could not get fingerprint"; } if (error) fzprintf(sftpError, "Error loading file: %s", error); else fzprintf(sftpReply, "%s", fingerprint); } else if (!strcmp(cmd, "write")) { Filename* outfilename; int ret; if (!args) { fzprintf(sftpError, "No argument given"); continue; } if (!ssh2key) { fzprintf(sftpError, "No key loaded"); continue; } outfilename = filename_from_str(args); ret = ssh2_save_userkey(outfilename, ssh2key, passphrase); if (!ret) { fzprintf(sftpError, "Unable to save SSH-2 private key"); continue; } filename_free(outfilename); fzprintf(sftpReply, ""); } else fzprintf(sftpError, "Unknown command"); } if (infilename) { filename_free(infilename); } sfree(line); sfree(passphrase); if (ssh2key) { ssh2key->alg->freekey(ssh2key->data); sfree(ssh2key); } sfree(fingerprint); sfree(origcomment); return 0; }
int main(int argc, char **argv) { Filename *infilename = NULL, *outfilename = NULL; int intype = SSH_KEYTYPE_UNOPENABLE; int encrypted = 0; char* origcomment = 0; char* line = 0; char* passphrase = 0; struct ssh2_userkey *ssh2key = NULL; struct RSAKey *ssh1key = NULL; printf("fzputtygen\n"); printf("Copyright (C) 2008-2015 Tim Kosse\n"); printf("Based on PuTTY's puttygen\n"); printf("Copyright (C) 1997-2015 Simon Tatham and the PuTTY team\n"); printf("Converts private SSH keys into PuTTY's format.\n"); printf("This program is used by FileZilla and not intended to be used directly.\n"); printf("Use the puttygen tool from PuTTY for a human-usable tool.\n"); printf("\n"); fflush(stdout); while (1) { if (line) sfree(line); line = fgetline(stdin); if (!line || !*line || *line == '\n') break; line[strlen(line) - 1] = 0; char* cmd = line, *args = line; while (*args) { if (*args == ' ') { *(args++) = 0; break; } args++; } if (!*args) args = 0; if (!strcmp(cmd, "file")) { if (ssh1key) { freersakey(ssh1key); ssh1key = 0; } if (ssh2key) { ssh2key->alg->freekey(ssh2key->data); sfree(ssh2key); ssh2key = 0; } if (passphrase) { sfree(passphrase); passphrase = 0; } if (!args) { fzprintf(sftpError, "No argument given"); continue; } infilename = filename_from_str(args); intype = key_type(infilename); switch (intype) { case SSH_KEYTYPE_SSH1: case SSH_KEYTYPE_SSH2: fzprintf(sftpReply, "0"); break; case SSH_KEYTYPE_UNKNOWN: case SSH_KEYTYPE_UNOPENABLE: default: fzprintf(sftpReply, "2"); intype = SSH_KEYTYPE_UNOPENABLE; break; case SSH_KEYTYPE_OPENSSH: case SSH_KEYTYPE_SSHCOM: fzprintf(sftpReply, "1"); break; } } else if (!strcmp(cmd, "encrypted")) { if (intype == SSH_KEYTYPE_UNOPENABLE) { fzprintf(sftpError, "No keyfile opened"); continue; } if (intype == SSH_KEYTYPE_SSH1) encrypted = rsakey_encrypted(infilename, &origcomment); else if (intype == SSH_KEYTYPE_SSH2) encrypted = ssh2_userkey_encrypted(infilename, &origcomment); else encrypted = import_encrypted(infilename, intype, &origcomment); fzprintf(sftpReply, "%d", encrypted ? 1 : 0); } else if (!strcmp(cmd, "comment")) { if (intype == SSH_KEYTYPE_UNOPENABLE) { fzprintf(sftpError, "No keyfile opened"); continue; } if (origcomment) fzprintf(sftpReply, "%s", origcomment); else fzprintf(sftpReply, ""); } else if (!strcmp(cmd, "password")) { if (!args) { fzprintf(sftpError, "No argument given"); continue; } if (intype == SSH_KEYTYPE_UNOPENABLE) { fzprintf(sftpError, "No keyfile opened"); continue; } if (passphrase) sfree(passphrase); passphrase = strdup(args); fzprintf(sftpReply, ""); } else if (!strcmp(cmd, "load")) { const char* error = 0; if (ssh1key) { freersakey(ssh1key); ssh1key = 0; } if (ssh2key) { ssh2key->alg->freekey(ssh2key->data); sfree(ssh2key); ssh2key = 0; } if (intype == SSH_KEYTYPE_UNOPENABLE) { fzprintf(sftpError, "No keyfile opened"); continue; } if (encrypted && !passphrase) { fzprintf(sftpError, "No password given"); continue; } switch (intype) { int ret; case SSH_KEYTYPE_SSH1: ssh1key = snew(struct RSAKey); ret = loadrsakey(infilename, ssh1key, passphrase, &error); if (ret > 0) error = NULL; else if (!error) error = "unknown error"; break; case SSH_KEYTYPE_SSH2: ssh2key = ssh2_load_userkey(infilename, passphrase, &error); if (ssh2key == SSH2_WRONG_PASSPHRASE) { error = "wrong passphrase"; ssh2key = 0; } else if (ssh2key) error = NULL; else if (!error) error = "unknown error"; break; case SSH_KEYTYPE_OPENSSH: case SSH_KEYTYPE_SSHCOM: ssh2key = import_ssh2(infilename, intype, passphrase, &error); if (ssh2key) { if (ssh2key != SSH2_WRONG_PASSPHRASE) error = NULL; else { ssh2key = NULL; error = "wrong passphrase"; } } else if (!error) error = "unknown error"; break; default: assert(0); } if (error) fzprintf(sftpError, "Error loading file: %s", error); else fzprintf(sftpReply, ""); } else if (!strcmp(cmd, "data")) { if (!ssh1key && !ssh2key) { fzprintf(sftpError, "No key loaded"); continue; } if (ssh1key) { char data[512]; char* p; strcpy(data, "ssh1 "); p = data + strlen(data); rsa_fingerprint(p, sizeof(data) - (p - data), ssh1key); fzprintf(sftpReply, "%s", data); continue; } if (ssh2key) { char* fingerprint = ssh2key->alg->fingerprint(ssh2key->data); if (fingerprint) { fzprintf(sftpReply, "%s", fingerprint); continue; } } fzprintf(sftpReply, ""); } else if (!strcmp(cmd, "write")) { int ret; if (!args) { fzprintf(sftpError, "No argument given"); continue; } if (!ssh1key && !ssh2key) { fzprintf(sftpError, "No key loaded"); continue; } outfilename = filename_from_str(args); if (ssh1key) { ret = saversakey(outfilename, ssh1key, 0); if (!ret) { fzprintf(sftpError, "Unable to save SSH-1 private key"); continue; } } else if (ssh2key) { ret = ssh2_save_userkey(outfilename, ssh2key, 0); if (!ret) { fzprintf(sftpError, "Unable to save SSH-2 private key"); continue; } } fzprintf(sftpReply, ""); } else fzprintf(sftpError, "Unknown command"); }