[BACK]Return to key.c CVS log [TXT][DIR] Up to [local] / src / usr.bin / ssh

Annotation of src/usr.bin/ssh/key.c, Revision 1.119

1.119   ! djm         1: /* $OpenBSD: key.c,v 1.118 2014/06/24 01:13:21 djm Exp $ */
1.1       markus      2: /*
1.118     djm         3:  * placed in the public domain
1.1       markus      4:  */
1.67      deraadt     5:
1.70      grunk       6: #include <sys/param.h>
1.67      deraadt     7: #include <sys/types.h>
1.118     djm         8: #include <errno.h>
                      9: #include <stdarg.h>
1.66      stevesk    10: #include <stdio.h>
1.15      markus     11:
1.118     djm        12: #define SSH_KEY_NO_DEFINE
1.1       markus     13: #include "key.h"
1.118     djm        14:
                     15: #include "compat.h"
                     16: #include "sshkey.h"
                     17: #include "ssherr.h"
1.15      markus     18: #include "log.h"
1.118     djm        19: #include "authfile.h"
1.45      deraadt    20:
1.83      djm        21: void
                     22: key_add_private(Key *k)
1.12      markus     23: {
1.118     djm        24:        int r;
                     25:
                     26:        if ((r = sshkey_add_private(k)) != 0)
                     27:                fatal("%s: %s", __func__, ssh_err(r));
1.83      djm        28: }
                     29:
                     30: Key *
                     31: key_new_private(int type)
                     32: {
1.118     djm        33:        Key *ret = NULL;
1.83      djm        34:
1.118     djm        35:        if ((ret = sshkey_new_private(type)) == NULL)
                     36:                fatal("%s: failed", __func__);
                     37:        return ret;
1.83      djm        38: }
                     39:
1.52      jakob      40: u_char*
1.100     djm        41: key_fingerprint_raw(const Key *k, enum fp_type dgst_type,
                     42:     u_int *dgst_raw_length)
1.1       markus     43: {
1.118     djm        44:        u_char *ret = NULL;
                     45:        size_t dlen;
                     46:        int r;
                     47:
                     48:        if (dgst_raw_length != NULL)
                     49:                *dgst_raw_length = 0;
                     50:        if ((r = sshkey_fingerprint_raw(k, dgst_type, &ret, &dlen)) != 0)
                     51:                fatal("%s: %s", __func__, ssh_err(r));
                     52:        if (dlen > INT_MAX)
                     53:                fatal("%s: giant len %zu", __func__, dlen);
                     54:        *dgst_raw_length = dlen;
                     55:        return ret;
1.1       markus     56: }
1.45      deraadt    57:
1.12      markus     58: int
1.3       markus     59: key_read(Key *ret, char **cpp)
1.1       markus     60: {
1.118     djm        61:        return sshkey_read(ret, cpp) == 0 ? 1 : -1;
1.1       markus     62: }
1.45      deraadt    63:
1.1       markus     64: int
1.55      jakob      65: key_write(const Key *key, FILE *f)
1.1       markus     66: {
1.118     djm        67:        return sshkey_write(key, f) == 0 ? 1 : 0;
1.1       markus     68: }
1.45      deraadt    69:
1.118     djm        70: Key *
                     71: key_generate(int type, u_int bits)
1.101     djm        72: {
1.118     djm        73:        int r;
                     74:        Key *ret = NULL;
1.101     djm        75:
1.118     djm        76:        if ((r = sshkey_generate(type, bits, &ret)) != 0)
                     77:                fatal("%s: %s", __func__, ssh_err(r));
1.101     djm        78:        return ret;
                     79: }
                     80:
1.83      djm        81: void
1.118     djm        82: key_cert_copy(const Key *from_key, Key *to_key)
1.83      djm        83: {
1.118     djm        84:        int r;
1.83      djm        85:
1.118     djm        86:        if ((r = sshkey_cert_copy(from_key, to_key)) != 0)
                     87:                fatal("%s: %s", __func__, ssh_err(r));
1.83      djm        88: }
                     89:
1.12      markus     90: Key *
1.55      jakob      91: key_from_private(const Key *k)
1.12      markus     92: {
1.118     djm        93:        int r;
                     94:        Key *ret = NULL;
1.25      markus     95:
1.118     djm        96:        if ((r = sshkey_from_private(k, &ret)) != 0)
                     97:                fatal("%s: %s", __func__, ssh_err(r));
1.83      djm        98:        return ret;
                     99: }
                    100:
1.118     djm       101: static void
                    102: fatal_on_fatal_errors(int r, const char *func, int extra_fatal)
1.12      markus    103: {
1.118     djm       104:        if (r == SSH_ERR_INTERNAL_ERROR ||
                    105:            r == SSH_ERR_ALLOC_FAIL ||
                    106:            (extra_fatal != 0 && r == extra_fatal))
                    107:                fatal("%s: %s", func, ssh_err(r));
1.12      markus    108: }
                    109:
1.105     djm       110: Key *
                    111: key_from_blob(const u_char *blob, u_int blen)
                    112: {
1.118     djm       113:        int r;
                    114:        Key *ret = NULL;
                    115:
                    116:        if ((r = sshkey_from_blob(blob, blen, &ret)) != 0) {
                    117:                fatal_on_fatal_errors(r, __func__, 0);
                    118:                error("%s: %s", __func__, ssh_err(r));
                    119:                return NULL;
                    120:        }
                    121:        return ret;
1.105     djm       122: }
                    123:
1.118     djm       124: int
                    125: key_to_blob(const Key *key, u_char **blobp, u_int *lenp)
1.12      markus    126: {
1.118     djm       127:        u_char *blob;
                    128:        size_t blen;
                    129:        int r;
1.12      markus    130:
1.106     djm       131:        if (blobp != NULL)
                    132:                *blobp = NULL;
                    133:        if (lenp != NULL)
                    134:                *lenp = 0;
1.118     djm       135:        if ((r = sshkey_to_blob(key, &blob, &blen)) != 0) {
                    136:                fatal_on_fatal_errors(r, __func__, 0);
                    137:                error("%s: %s", __func__, ssh_err(r));
1.12      markus    138:                return 0;
                    139:        }
1.118     djm       140:        if (blen > INT_MAX)
                    141:                fatal("%s: giant len %zu", __func__, blen);
                    142:        if (blobp != NULL)
                    143:                *blobp = blob;
1.48      markus    144:        if (lenp != NULL)
1.118     djm       145:                *lenp = blen;
                    146:        return blen;
1.12      markus    147: }
                    148:
                    149: int
1.118     djm       150: key_sign(const Key *key, u_char **sigp, u_int *lenp,
                    151:     const u_char *data, u_int datalen)
1.100     djm       152: {
1.118     djm       153:        int r;
                    154:        u_char *sig;
                    155:        size_t siglen;
1.100     djm       156:
1.118     djm       157:        if (sigp != NULL)
                    158:                *sigp = NULL;
                    159:        if (lenp != NULL)
                    160:                *lenp = 0;
                    161:        if ((r = sshkey_sign(key, &sig, &siglen,
                    162:            data, datalen, datafellows)) != 0) {
                    163:                fatal_on_fatal_errors(r, __func__, 0);
                    164:                error("%s: %s", __func__, ssh_err(r));
1.12      markus    165:                return -1;
                    166:        }
1.118     djm       167:        if (siglen > INT_MAX)
                    168:                fatal("%s: giant len %zu", __func__, siglen);
                    169:        if (sigp != NULL)
                    170:                *sigp = sig;
                    171:        if (lenp != NULL)
                    172:                *lenp = siglen;
                    173:        return 0;
1.12      markus    174: }
                    175:
                    176: int
1.118     djm       177: key_verify(const Key *key, const u_char *signature, u_int signaturelen,
1.55      jakob     178:     const u_char *data, u_int datalen)
1.12      markus    179: {
1.118     djm       180:        int r;
1.26      markus    181:
1.118     djm       182:        if ((r = sshkey_verify(key, signature, signaturelen,
                    183:            data, datalen, datafellows)) != 0) {
                    184:                fatal_on_fatal_errors(r, __func__, 0);
                    185:                error("%s: %s", __func__, ssh_err(r));
                    186:                return r == SSH_ERR_SIGNATURE_INVALID ? 0 : -1;
1.12      markus    187:        }
1.118     djm       188:        return 1;
1.42      markus    189: }
                    190:
                    191: Key *
1.55      jakob     192: key_demote(const Key *k)
1.42      markus    193: {
1.118     djm       194:        int r;
                    195:        Key *ret = NULL;
1.43      markus    196:
1.118     djm       197:        if ((r = sshkey_demote(k, &ret)) != 0)
                    198:                fatal("%s: %s", __func__, ssh_err(r));
                    199:        return ret;
1.83      djm       200: }
                    201:
                    202: int
1.118     djm       203: key_to_certified(Key *k, int legacy)
1.83      djm       204: {
1.118     djm       205:        int r;
1.83      djm       206:
1.118     djm       207:        if ((r = sshkey_to_certified(k, legacy)) != 0) {
                    208:                fatal_on_fatal_errors(r, __func__, 0);
                    209:                error("%s: %s", __func__, ssh_err(r));
1.83      djm       210:                return -1;
                    211:        }
1.118     djm       212:        return 0;
1.83      djm       213: }
                    214:
                    215: int
                    216: key_drop_cert(Key *k)
                    217: {
1.118     djm       218:        int r;
                    219:
                    220:        if ((r = sshkey_drop_cert(k)) != 0) {
                    221:                fatal_on_fatal_errors(r, __func__, 0);
                    222:                error("%s: %s", __func__, ssh_err(r));
1.83      djm       223:                return -1;
                    224:        }
1.109     markus    225:        return 0;
1.83      djm       226: }
                    227:
                    228: int
                    229: key_certify(Key *k, Key *ca)
                    230: {
1.118     djm       231:        int r;
1.83      djm       232:
1.118     djm       233:        if ((r = sshkey_certify(k, ca)) != 0) {
                    234:                fatal_on_fatal_errors(r, __func__, 0);
                    235:                error("%s: %s", __func__, ssh_err(r));
1.83      djm       236:                return -1;
                    237:        }
1.118     djm       238:        return 0;
                    239: }
1.83      djm       240:
1.118     djm       241: int
                    242: key_cert_check_authority(const Key *k, int want_host, int require_principal,
                    243:     const char *name, const char **reason)
                    244: {
                    245:        int r;
1.83      djm       246:
1.118     djm       247:        if ((r = sshkey_cert_check_authority(k, want_host, require_principal,
                    248:            name, reason)) != 0) {
                    249:                fatal_on_fatal_errors(r, __func__, 0);
                    250:                error("%s: %s", __func__, ssh_err(r));
1.83      djm       251:                return -1;
                    252:        }
1.118     djm       253:        return 0;
                    254: }
1.83      djm       255:
1.117     markus    256: #ifdef WITH_OPENSSL
1.118     djm       257: int
                    258: key_ec_validate_public(const EC_GROUP *group, const EC_POINT *public)
                    259: {
                    260:        int r;
1.87      djm       261:
1.118     djm       262:        if ((r = sshkey_ec_validate_public(group, public)) != 0) {
                    263:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    264:                error("%s: %s", __func__, ssh_err(r));
1.83      djm       265:                return -1;
                    266:        }
                    267:        return 0;
                    268: }
                    269:
                    270: int
1.118     djm       271: key_ec_validate_private(const EC_KEY *key)
1.83      djm       272: {
1.118     djm       273:        int r;
1.83      djm       274:
1.118     djm       275:        if ((r = sshkey_ec_validate_private(key)) != 0) {
                    276:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    277:                error("%s: %s", __func__, ssh_err(r));
1.83      djm       278:                return -1;
                    279:        }
                    280:        return 0;
1.87      djm       281: }
1.118     djm       282: #endif /* WITH_OPENSSL */
1.87      djm       283:
1.118     djm       284: void
                    285: key_private_serialize(const Key *key, struct sshbuf *b)
                    286: {
                    287:        int r;
                    288:
                    289:        if ((r = sshkey_private_serialize(key, b)) != 0)
                    290:                fatal("%s: %s", __func__, ssh_err(r));
                    291: }
                    292:
                    293: Key *
                    294: key_private_deserialize(struct sshbuf *blob)
1.87      djm       295: {
1.118     djm       296:        int r;
                    297:        Key *ret = NULL;
                    298:
                    299:        if ((r = sshkey_private_deserialize(blob, &ret)) != 0) {
                    300:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    301:                error("%s: %s", __func__, ssh_err(r));
                    302:                return NULL;
1.87      djm       303:        }
1.118     djm       304:        return ret;
1.4       markus    305: }
1.92      djm       306:
1.118     djm       307: /* authfile.c */
                    308:
1.92      djm       309: int
1.118     djm       310: key_save_private(Key *key, const char *filename, const char *passphrase,
                    311:     const char *comment, int force_new_format, const char *new_format_cipher,
                    312:     int new_format_rounds)
1.92      djm       313: {
1.118     djm       314:        int r;
                    315:
                    316:        if ((r = sshkey_save_private(key, filename, passphrase, comment,
                    317:            force_new_format, new_format_cipher, new_format_rounds)) != 0) {
                    318:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    319:                error("%s: %s", __func__, ssh_err(r));
1.93      djm       320:                return 0;
                    321:        }
1.118     djm       322:        return 1;
1.93      djm       323: }
                    324:
1.118     djm       325: int
                    326: key_load_file(int fd, const char *filename, struct sshbuf *blob)
1.92      djm       327: {
1.118     djm       328:        int r;
1.92      djm       329:
1.118     djm       330:        if ((r = sshkey_load_file(fd, filename, blob)) != 0) {
                    331:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    332:                error("%s: %s", __func__, ssh_err(r));
                    333:                return 0;
                    334:        }
                    335:        return 1;
1.93      djm       336: }
                    337:
1.118     djm       338: Key *
                    339: key_load_cert(const char *filename)
1.93      djm       340: {
1.118     djm       341:        int r;
                    342:        Key *ret = NULL;
                    343:
                    344:        if ((r = sshkey_load_cert(filename, &ret)) != 0) {
                    345:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    346:                if (r == SSH_ERR_SYSTEM_ERROR && errno == ENOENT)
                    347:                        debug("%s: %s", __func__, ssh_err(r));
                    348:                else
                    349:                        error("%s: %s", __func__, ssh_err(r));
                    350:                return NULL;
                    351:        }
                    352:        return ret;
1.93      djm       353:
1.92      djm       354: }
                    355:
1.118     djm       356: Key *
                    357: key_load_public(const char *filename, char **commentp)
1.92      djm       358: {
1.118     djm       359:        int r;
                    360:        Key *ret = NULL;
1.92      djm       361:
1.118     djm       362:        if ((r = sshkey_load_public(filename, &ret, commentp)) != 0) {
                    363:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    364:                if (r == SSH_ERR_SYSTEM_ERROR && errno == ENOENT)
                    365:                        debug("%s: %s", __func__, ssh_err(r));
                    366:                else
                    367:                        error("%s: %s", __func__, ssh_err(r));
                    368:                return NULL;
1.92      djm       369:        }
1.118     djm       370:        return ret;
                    371: }
1.92      djm       372:
1.118     djm       373: Key *
                    374: key_load_private(const char *path, const char *passphrase,
                    375:     char **commentp)
                    376: {
                    377:        int r;
                    378:        Key *ret = NULL;
1.92      djm       379:
1.118     djm       380:        if ((r = sshkey_load_private(path, passphrase, &ret, commentp)) != 0) {
                    381:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    382:                if (r == SSH_ERR_SYSTEM_ERROR && errno == ENOENT)
                    383:                        debug("%s: %s", __func__, ssh_err(r));
                    384:                else
                    385:                        error("%s: %s", __func__, ssh_err(r));
                    386:                return NULL;
1.92      djm       387:        }
                    388:        return ret;
                    389: }
                    390:
1.118     djm       391: Key *
                    392: key_load_private_cert(int type, const char *filename, const char *passphrase,
                    393:     int *perm_ok)
1.92      djm       394: {
1.118     djm       395:        int r;
                    396:        Key *ret = NULL;
1.92      djm       397:
1.118     djm       398:        if ((r = sshkey_load_private_cert(type, filename, passphrase,
                    399:            &ret, perm_ok)) != 0) {
                    400:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    401:                if (r == SSH_ERR_SYSTEM_ERROR && errno == ENOENT)
                    402:                        debug("%s: %s", __func__, ssh_err(r));
                    403:                else
                    404:                        error("%s: %s", __func__, ssh_err(r));
                    405:                return NULL;
1.92      djm       406:        }
                    407:        return ret;
                    408: }
                    409:
1.118     djm       410: Key *
                    411: key_load_private_type(int type, const char *filename, const char *passphrase,
                    412:     char **commentp, int *perm_ok)
1.92      djm       413: {
1.118     djm       414:        int r;
                    415:        Key *ret = NULL;
1.92      djm       416:
1.118     djm       417:        if ((r = sshkey_load_private_type(type, filename, passphrase,
                    418:            &ret, commentp, perm_ok)) != 0) {
                    419:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
1.119   ! djm       420:                if ((r == SSH_ERR_SYSTEM_ERROR && errno == ENOENT) ||
        !           421:                    (r == SSH_ERR_KEY_WRONG_PASSPHRASE))
1.118     djm       422:                        debug("%s: %s", __func__, ssh_err(r));
                    423:                else
                    424:                        error("%s: %s", __func__, ssh_err(r));
                    425:                return NULL;
1.92      djm       426:        }
1.118     djm       427:        return ret;
1.92      djm       428: }
                    429:
1.118     djm       430: #ifdef WITH_OPENSSL
                    431: Key *
                    432: key_load_private_pem(int fd, int type, const char *passphrase,
                    433:     char **commentp)
1.92      djm       434: {
1.118     djm       435:        int r;
                    436:        Key *ret = NULL;
1.92      djm       437:
1.118     djm       438:        if ((r = sshkey_load_private_pem(fd, type, passphrase,
                    439:             &ret, commentp)) != 0) {
                    440:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    441:                error("%s: %s", __func__, ssh_err(r));
                    442:                return NULL;
                    443:        }
                    444:        return ret;
1.92      djm       445: }
1.118     djm       446: #endif /* WITH_OPENSSL */
1.92      djm       447:
1.118     djm       448: int
                    449: key_perm_ok(int fd, const char *filename)
1.107     markus    450: {
1.118     djm       451:        return sshkey_perm_ok(fd, filename) == 0 ? 1 : 0;
1.107     markus    452: }
                    453:
1.118     djm       454: int
                    455: key_in_file(Key *key, const char *filename, int strict_type)
1.107     markus    456: {
1.118     djm       457:        int r;
1.107     markus    458:
1.118     djm       459:        if ((r = sshkey_in_file(key, filename, strict_type)) != 0) {
                    460:                fatal_on_fatal_errors(r, __func__, SSH_ERR_LIBCRYPTO_ERROR);
                    461:                if (r == SSH_ERR_SYSTEM_ERROR && errno == ENOENT)
                    462:                        return 0;
                    463:                error("%s: %s", __func__, ssh_err(r));
                    464:                return r == SSH_ERR_KEY_NOT_FOUND ? 0 : -1;
1.107     markus    465:        }
1.118     djm       466:        return 1;
1.107     markus    467: }