From e7643ba14ffde5432e1f20da675230a93dc6e073 Mon Sep 17 00:00:00 2001 From: Damien Miller Date: Fri, 21 Sep 2012 04:14:14 +1000 Subject: [PATCH] convert auth2-hostbased.c schnorr.c ssh-pkcs11-client.c to new buffer API --- ssh/auth2-hostbased.c | 40 ++++++++------- ssh/schnorr.c | 85 +++++++++++++++++-------------- ssh/ssh-pkcs11-client.c | 110 +++++++++++++++++++++++----------------- 3 files changed, 130 insertions(+), 105 deletions(-) diff --git a/ssh/auth2-hostbased.c b/ssh/auth2-hostbased.c index 82bfca1..f7b647f 100644 --- a/ssh/auth2-hostbased.c +++ b/ssh/auth2-hostbased.c @@ -35,7 +35,7 @@ #define PACKET_SKIP_COMPAT #define PACKET_SKIP_COMPAT2 #include "packet.h" -#include "buffer.h" +#include "sshbuf.h" #include "log.h" #include "servconf.h" #include "compat.h" @@ -59,7 +59,7 @@ static int userauth_hostbased(struct ssh *ssh) { Authctxt *authctxt = ssh->authctxt; - Buffer b; + struct sshbuf *b; struct sshkey *key = NULL; char *pkalg, *cuser, *chost, *service; u_char *pkblob, *sig; @@ -81,10 +81,10 @@ userauth_hostbased(struct ssh *ssh) cuser, chost, pkalg, slen); #ifdef DEBUG_PK debug("signature:"); - buffer_init(&b); - buffer_append(&b, sig, slen); - buffer_dump(&b); - buffer_free(&b); + b = sshbuf_new(); + sshbuf_put(b, sig, siglen); + sshbuf_dump(b, stderr); + sshbuf_free(b); #endif pktype = sshkey_type_from_name(pkalg); if (pktype == KEY_UNSPEC) { @@ -108,28 +108,30 @@ userauth_hostbased(struct ssh *ssh) } service = ssh->compat & SSH_BUG_HBSERVICE ? "ssh-userauth" : authctxt->service; - buffer_init(&b); - buffer_put_string(&b, session_id2, session_id2_len); + if ((b = sshbuf_new()) == NULL) + fatal("%s: sshbuf_new failed", __func__); /* reconstruct packet */ - buffer_put_char(&b, SSH2_MSG_USERAUTH_REQUEST); - buffer_put_cstring(&b, authctxt->user); - buffer_put_cstring(&b, service); - buffer_put_cstring(&b, "hostbased"); - buffer_put_string(&b, pkalg, alen); - buffer_put_string(&b, pkblob, blen); - buffer_put_cstring(&b, chost); - buffer_put_cstring(&b, cuser); + if ((r = sshbuf_put_string(b, session_id2, session_id2_len)) != 0 || + (r = sshbuf_put_u8(b, SSH2_MSG_USERAUTH_REQUEST)) != 0 || + (r = sshbuf_put_cstring(b, authctxt->user)) != 0 || + (r = sshbuf_put_cstring(b, service)) != 0 || + (r = sshbuf_put_cstring(b, "hostbased")) != 0 || + (r = sshbuf_put_string(b, pkalg, alen)) != 0 || + (r = sshbuf_put_string(b, pkblob, blen)) != 0 || + (r = sshbuf_put_cstring(b, chost)) != 0 || + (r = sshbuf_put_cstring(b, cuser)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); #ifdef DEBUG_PK - buffer_dump(&b); + sshbuf_dump(b, stderr); #endif /* test for allowed key and correct signature */ authenticated = 0; if (PRIVSEP(hostbased_key_allowed(authctxt->pw, cuser, chost, key)) && PRIVSEP(sshkey_verify(key, sig, slen, - buffer_ptr(&b), buffer_len(&b), ssh->compat)) == 0) + sshbuf_ptr(b), sshbuf_len(b), ssh->compat)) == 0) authenticated = 1; - buffer_free(&b); + sshbuf_free(b); done: debug2("%s: authenticated %d", __func__, authenticated); if (key != NULL) diff --git a/ssh/schnorr.c b/ssh/schnorr.c index e741d3d..46b0855 100644 --- a/ssh/schnorr.c +++ b/ssh/schnorr.c @@ -35,7 +35,8 @@ #include #include "xmalloc.h" -#include "buffer.h" +#include "sshbuf.h" +#include "err.h" #include "log.h" #include "schnorr.h" @@ -64,27 +65,29 @@ schnorr_hash(const BIGNUM *p, const BIGNUM *q, const BIGNUM *g, u_char *digest; u_int digest_len; BIGNUM *h; - Buffer b; - int success = -1; + struct sshbuf *b; + int r, success = -1; if ((h = BN_new()) == NULL) { error("%s: BN_new", __func__); return NULL; } - buffer_init(&b); + if ((b = sshbuf_new()) == NULL) + fatal("%s: sshbuf_new failed", __func__); /* h = H(g || p || q || g^v || g^x || id) */ - buffer_put_bignum2(&b, g); - buffer_put_bignum2(&b, p); - buffer_put_bignum2(&b, q); - buffer_put_bignum2(&b, g_v); - buffer_put_bignum2(&b, g_x); - buffer_put_string(&b, id, idlen); + if ((r = sshbuf_put_bignum2(b, g)) != 0 || + (r = sshbuf_put_bignum2(b, p)) != 0 || + (r = sshbuf_put_bignum2(b, q)) != 0 || + (r = sshbuf_put_bignum2(b, g_v)) != 0 || + (r = sshbuf_put_bignum2(b, g_x)) != 0 || + (r = sshbuf_put_string(b, id, idlen)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); - SCHNORR_DEBUG_BUF((buffer_ptr(&b), buffer_len(&b), + SCHNORR_DEBUG_BUF((sshbuf_ptr(b), sshbuf_len(b), "%s: hashblob", __func__)); - if (hash_buffer(buffer_ptr(&b), buffer_len(&b), evp_md, + if (hash_buffer(sshbuf_ptr(b), sshbuf_len(b), evp_md, &digest, &digest_len) != 0) { error("%s: hash_buffer", __func__); goto out; @@ -96,7 +99,7 @@ schnorr_hash(const BIGNUM *p, const BIGNUM *q, const BIGNUM *g, success = 0; SCHNORR_DEBUG_BN((h, "%s: h = ", __func__)); out: - buffer_free(&b); + sshbuf_free(b); bzero(digest, digest_len); xfree(digest); digest_len = 0; @@ -216,26 +219,29 @@ schnorr_sign_buf(const BIGNUM *grp_p, const BIGNUM *grp_q, const BIGNUM *grp_g, const BIGNUM *x, const BIGNUM *g_x, const u_char *id, u_int idlen, u_char **sig, u_int *siglen) { - Buffer b; - BIGNUM *r, *e; + struct sshbuf *b; + BIGNUM *rv, *e; + int r; if (schnorr_sign(grp_p, grp_q, grp_g, EVP_sha256(), - x, g_x, id, idlen, &r, &e) != 0) + x, g_x, id, idlen, &rv, &e) != 0) return -1; /* Signature is (e, r) */ - buffer_init(&b); + if ((b = sshbuf_new()) == NULL) + fatal("%s: sshbuf_new failed", __func__); /* XXX sigtype-hash as string? */ - buffer_put_bignum2(&b, e); - buffer_put_bignum2(&b, r); - *siglen = buffer_len(&b); + if ((r = sshbuf_put_bignum2(b, e)) != 0 || + (r = sshbuf_put_bignum2(b, rv)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); + *siglen = sshbuf_len(b); *sig = xmalloc(*siglen); - memcpy(*sig, buffer_ptr(&b), *siglen); - SCHNORR_DEBUG_BUF((buffer_ptr(&b), buffer_len(&b), + memcpy(*sig, sshbuf_ptr(b), *siglen); + SCHNORR_DEBUG_BUF((sshbuf_ptr(b), sshbuf_len(b), "%s: sigblob", __func__)); - buffer_free(&b); + sshbuf_free(b); - BN_clear_free(r); + BN_clear_free(rv); BN_clear_free(e); return 0; @@ -355,37 +361,38 @@ schnorr_verify_buf(const BIGNUM *grp_p, const BIGNUM *grp_q, const BIGNUM *g_x, const u_char *id, u_int idlen, const u_char *sig, u_int siglen) { - Buffer b; - int ret = -1; + struct sshbuf *b; + int r, ret = -1; u_int rlen; - BIGNUM *r, *e; + BIGNUM *rv, *e; - e = r = NULL; + e = rv = NULL; if ((e = BN_new()) == NULL || - (r = BN_new()) == NULL) { + (rv = BN_new()) == NULL) { error("%s: BN_new", __func__); goto out; } /* Extract g^v and r from signature blob */ - buffer_init(&b); - buffer_append(&b, sig, siglen); - SCHNORR_DEBUG_BUF((buffer_ptr(&b), buffer_len(&b), - "%s: sigblob", __func__)); - buffer_get_bignum2(&b, e); - buffer_get_bignum2(&b, r); - rlen = buffer_len(&b); - buffer_free(&b); + if ((b = sshbuf_new()) == NULL) + fatal("%s: sshbuf_new failed", __func__); + SCHNORR_DEBUG_BUF((b, b, "%s: sigblob", __func__)); + if ((r = sshbuf_put(b, sig, siglen)) != 0 || + (r = sshbuf_get_bignum2(b, e)) != 0 || + (r = sshbuf_get_bignum2(b, rv)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); + rlen = sshbuf_len(b); + sshbuf_free(b); if (rlen != 0) { error("%s: remaining bytes in signature %d", __func__, rlen); goto out; } ret = schnorr_verify(grp_p, grp_q, grp_g, EVP_sha256(), - g_x, id, idlen, r, e); + g_x, id, idlen, rv, e); out: BN_clear_free(e); - BN_clear_free(r); + BN_clear_free(rv); return ret; } diff --git a/ssh/ssh-pkcs11-client.c b/ssh/ssh-pkcs11-client.c index 8c0e57b..7bebe28 100644 --- a/ssh/ssh-pkcs11-client.c +++ b/ssh/ssh-pkcs11-client.c @@ -42,34 +42,37 @@ int fd = -1; pid_t pid = -1; static void -send_msg(Buffer *m) +send_msg(struct sshbuf *m) { u_char buf[4]; - int mlen = buffer_len(m); + size_t mlen = sshbuf_len(m); + int r; - put_u32(buf, mlen); + POKE_U32(buf, mlen); if (atomicio(vwrite, fd, buf, 4) != 4 || - atomicio(vwrite, fd, buffer_ptr(m), - buffer_len(m)) != buffer_len(m)) + atomicio(vwrite, fd, sshbuf_ptr(m), + sshbuf_len(m)) != sshbuf_len(m)) error("write to helper failed"); - buffer_consume(m, mlen); + if ((r = sshbuf_consume(m, mlen)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); } static int -recv_msg(Buffer *m) +recv_msg(struct sshbuf *m) { u_int l, len; - u_char buf[1024]; + u_char c, buf[1024]; + int r; if ((len = atomicio(read, fd, buf, 4)) != 4) { error("read from helper failed: %u", len); return (0); /* XXX */ } - len = get_u32(buf); + len = PEEK_U32(buf); if (len > 256 * 1024) fatal("response too long: %u", len); /* read len bytes into m */ - buffer_clear(m); + sshbuf_reset(m); while (len > 0) { l = len; if (l > sizeof(buf)) @@ -78,10 +81,13 @@ recv_msg(Buffer *m) error("response from helper failed."); return (0); /* XXX */ } - buffer_append(m, buf, l); + if ((r = sshbuf_put(m, buf, l)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); len -= l; } - return (buffer_get_char(m)); + if ((r = sshbuf_get_u8(m, &c)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); + return c; } int @@ -104,7 +110,7 @@ pkcs11_rsa_private_encrypt(int flen, const u_char *from, u_char *to, RSA *rsa, u_char *blob, *signature = NULL; size_t blen, slen = 0; int r, ret = -1; - Buffer msg; + struct sshbuf *msg; if (padding != RSA_PKCS1_PADDING) return (-1); @@ -114,17 +120,19 @@ pkcs11_rsa_private_encrypt(int flen, const u_char *from, u_char *to, RSA *rsa, error("%s: sshkey_to_blob: %s", __func__, ssh_err(r)); return -1; } - buffer_init(&msg); - buffer_put_char(&msg, SSH2_AGENTC_SIGN_REQUEST); - buffer_put_string(&msg, blob, blen); - buffer_put_string(&msg, from, flen); - buffer_put_int(&msg, 0); + if ((msg = sshbuf_new()) == NULL) + fatal("%s: sshbuf_new failed", __func__); + if ((r = sshbuf_put_u8(msg, SSH2_AGENTC_SIGN_REQUEST)) != 0 || + (r = sshbuf_put_string(msg, blob, blen)) != 0 || + (r = sshbuf_put_string(msg, from, flen)) != 0 || + (r = sshbuf_put_u32(msg, 0)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); xfree(blob); - send_msg(&msg); - buffer_clear(&msg); + send_msg(msg); + sshbuf_reset(msg); - if (recv_msg(&msg) == SSH2_AGENT_SIGN_RESPONSE) { - if ((r = sshbuf_get_string(&msg, &signature, &slen)) != 0) + if (recv_msg(msg) == SSH2_AGENT_SIGN_RESPONSE) { + if ((r = sshbuf_get_string(msg, &signature, &slen)) != 0) fatal("%s: buffer error: %s", __func__, ssh_err(r)); if (slen <= (size_t)RSA_size(rsa)) { memcpy(to, signature, slen); @@ -132,7 +140,7 @@ pkcs11_rsa_private_encrypt(int flen, const u_char *from, u_char *to, RSA *rsa, } xfree(signature); } - buffer_free(&msg); + sshbuf_free(msg); return (ret); } @@ -184,28 +192,34 @@ int pkcs11_add_provider(char *name, char *pin, struct sshkey ***keysp) { struct sshkey *k; - int i, nkeys, r; + int r; u_char *blob; - u_int blen; - Buffer msg; + size_t blen; + u_int nkeys, i; + struct sshbuf *msg; if (fd < 0 && pkcs11_start_helper() < 0) return (-1); - buffer_init(&msg); - buffer_put_char(&msg, SSH_AGENTC_ADD_SMARTCARD_KEY); - buffer_put_cstring(&msg, name); - buffer_put_cstring(&msg, pin); - send_msg(&msg); - buffer_clear(&msg); + if ((msg = sshbuf_new()) == NULL) + fatal("%s: sshbuf_new failed", __func__); + if ((r = sshbuf_put_u8(msg, SSH_AGENTC_ADD_SMARTCARD_KEY)) != 0 || + (r = sshbuf_put_cstring(msg, name)) != 0 || + (r = sshbuf_put_cstring(msg, pin)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); + send_msg(msg); + sshbuf_reset(msg); - if (recv_msg(&msg) == SSH2_AGENT_IDENTITIES_ANSWER) { - nkeys = buffer_get_int(&msg); + if (recv_msg(msg) == SSH2_AGENT_IDENTITIES_ANSWER) { + if ((r = sshbuf_get_u32(msg, &nkeys)) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); *keysp = xcalloc(nkeys, sizeof(struct sshkey *)); for (i = 0; i < nkeys; i++) { - blob = buffer_get_string(&msg, &blen); - xfree(buffer_get_string(&msg, NULL)); /* XXX clean up properly instead of fatal() */ + if ((r = sshbuf_get_string(msg, &blob, &blen)) != 0 || + (r = sshbuf_skip_string(msg)) != 0) + fatal("%s: buffer error: %s", + __func__, ssh_err(r)); if ((r = sshkey_from_blob(blob, blen, &k)) != 0) fatal("%s: bad key: %s", __func__, ssh_err(r)); wrap_key(k->rsa); @@ -215,25 +229,27 @@ pkcs11_add_provider(char *name, char *pin, struct sshkey ***keysp) } else { nkeys = -1; } - buffer_free(&msg); + sshbuf_free(msg); return (nkeys); } int pkcs11_del_provider(char *name) { - int ret = -1; - Buffer msg; + int r, ret = -1; + struct sshbuf *msg; - buffer_init(&msg); - buffer_put_char(&msg, SSH_AGENTC_REMOVE_SMARTCARD_KEY); - buffer_put_cstring(&msg, name); - buffer_put_cstring(&msg, ""); - send_msg(&msg); - buffer_clear(&msg); + if ((msg = sshbuf_new()) == NULL) + fatal("%s: sshbuf_new failed", __func__); + if ((r = sshbuf_put_u8(msg, SSH_AGENTC_REMOVE_SMARTCARD_KEY)) != 0 || + (r = sshbuf_put_cstring(msg, name)) != 0 || + (r = sshbuf_put_cstring(msg, "")) != 0) + fatal("%s: buffer error: %s", __func__, ssh_err(r)); + send_msg(msg); + sshbuf_reset(msg); - if (recv_msg(&msg) == SSH_AGENT_SUCCESS) + if (recv_msg(msg) == SSH_AGENT_SUCCESS) ret = 0; - buffer_free(&msg); + sshbuf_free(msg); return (ret); }