diff options
author | jsing <> | 2016-11-06 15:06:52 +0000 |
---|---|---|
committer | jsing <> | 2016-11-06 15:06:52 +0000 |
commit | 70a9b39993a5a2fa10a4898ea064330a4b81d242 (patch) | |
tree | ea687de8cb26f253b37f400fe836fc69fc0bfa7a | |
parent | 8067bfd61e7219c648a6bd4bfe6aa23a66758a00 (diff) | |
download | openbsd-70a9b39993a5a2fa10a4898ea064330a4b81d242.tar.gz openbsd-70a9b39993a5a2fa10a4898ea064330a4b81d242.tar.bz2 openbsd-70a9b39993a5a2fa10a4898ea064330a4b81d242.zip |
Split ssl3_get_client_key_exchange() into separate per algorithm functions.
ok beck@
-rw-r--r-- | src/lib/libssl/s3_srvr.c | 708 |
1 files changed, 388 insertions, 320 deletions
diff --git a/src/lib/libssl/s3_srvr.c b/src/lib/libssl/s3_srvr.c index f364955716..65625cef26 100644 --- a/src/lib/libssl/s3_srvr.c +++ b/src/lib/libssl/s3_srvr.c | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: s3_srvr.c,v 1.131 2016/11/06 14:44:35 jsing Exp $ */ | 1 | /* $OpenBSD: s3_srvr.c,v 1.132 2016/11/06 15:06:52 jsing Exp $ */ |
2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) | 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
3 | * All rights reserved. | 3 | * All rights reserved. |
4 | * | 4 | * |
@@ -1629,369 +1629,443 @@ err: | |||
1629 | return (-1); | 1629 | return (-1); |
1630 | } | 1630 | } |
1631 | 1631 | ||
1632 | int | 1632 | static int |
1633 | ssl3_get_client_key_exchange(SSL *s) | 1633 | ssl3_get_client_kex_rsa(SSL *s, unsigned char *p, long n) |
1634 | { | 1634 | { |
1635 | int i, al, ok; | 1635 | char fakekey[SSL_MAX_MASTER_KEY_LENGTH]; |
1636 | long n; | 1636 | unsigned char *d; |
1637 | unsigned long alg_k; | ||
1638 | unsigned char *d, *p; | ||
1639 | RSA *rsa = NULL; | 1637 | RSA *rsa = NULL; |
1640 | EVP_PKEY *pkey = NULL; | 1638 | EVP_PKEY *pkey = NULL; |
1641 | BIGNUM *pub = NULL; | 1639 | int i, al; |
1642 | DH *dh_srvr; | ||
1643 | 1640 | ||
1644 | EC_KEY *srvr_ecdh = NULL; | 1641 | d = p; |
1645 | EVP_PKEY *clnt_pub_pkey = NULL; | ||
1646 | EC_POINT *clnt_ecpoint = NULL; | ||
1647 | BN_CTX *bn_ctx = NULL; | ||
1648 | 1642 | ||
1649 | /* 2048 maxlen is a guess. How long a key does that permit? */ | 1643 | arc4random_buf(fakekey, sizeof(fakekey)); |
1650 | n = s->method->ssl_get_message(s, SSL3_ST_SR_KEY_EXCH_A, | 1644 | fakekey[0] = s->client_version >> 8; |
1651 | SSL3_ST_SR_KEY_EXCH_B, SSL3_MT_CLIENT_KEY_EXCHANGE, 2048, &ok); | 1645 | fakekey[1] = s->client_version & 0xff; |
1652 | if (!ok) | ||
1653 | return ((int)n); | ||
1654 | d = p = (unsigned char *)s->init_msg; | ||
1655 | |||
1656 | alg_k = s->s3->tmp.new_cipher->algorithm_mkey; | ||
1657 | 1646 | ||
1658 | if (alg_k & SSL_kRSA) { | 1647 | pkey = s->cert->pkeys[SSL_PKEY_RSA_ENC].privatekey; |
1659 | char fakekey[SSL_MAX_MASTER_KEY_LENGTH]; | 1648 | if ((pkey == NULL) || (pkey->type != EVP_PKEY_RSA) || |
1649 | (pkey->pkey.rsa == NULL)) { | ||
1650 | al = SSL_AD_HANDSHAKE_FAILURE; | ||
1651 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1652 | SSL_R_MISSING_RSA_CERTIFICATE); | ||
1653 | goto f_err; | ||
1654 | } | ||
1655 | rsa = pkey->pkey.rsa; | ||
1660 | 1656 | ||
1661 | arc4random_buf(fakekey, sizeof(fakekey)); | 1657 | if (2 > n) |
1662 | fakekey[0] = s->client_version >> 8; | 1658 | goto truncated; |
1663 | fakekey[1] = s->client_version & 0xff; | 1659 | n2s(p, i); |
1660 | if (n != i + 2) { | ||
1661 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1662 | SSL_R_TLS_RSA_ENCRYPTED_VALUE_LENGTH_IS_WRONG); | ||
1663 | goto err; | ||
1664 | } else | ||
1665 | n = i; | ||
1664 | 1666 | ||
1665 | pkey = s->cert->pkeys[SSL_PKEY_RSA_ENC].privatekey; | 1667 | i = RSA_private_decrypt((int)n, p, p, rsa, RSA_PKCS1_PADDING); |
1666 | if ((pkey == NULL) || (pkey->type != EVP_PKEY_RSA) || | ||
1667 | (pkey->pkey.rsa == NULL)) { | ||
1668 | al = SSL_AD_HANDSHAKE_FAILURE; | ||
1669 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1670 | SSL_R_MISSING_RSA_CERTIFICATE); | ||
1671 | goto f_err; | ||
1672 | } | ||
1673 | rsa = pkey->pkey.rsa; | ||
1674 | 1668 | ||
1675 | if (2 > n) | 1669 | ERR_clear_error(); |
1676 | goto truncated; | ||
1677 | n2s(p, i); | ||
1678 | if (n != i + 2) { | ||
1679 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1680 | SSL_R_TLS_RSA_ENCRYPTED_VALUE_LENGTH_IS_WRONG); | ||
1681 | goto err; | ||
1682 | } else | ||
1683 | n = i; | ||
1684 | |||
1685 | i = RSA_private_decrypt((int)n, p, p, rsa, RSA_PKCS1_PADDING); | ||
1686 | 1670 | ||
1687 | ERR_clear_error(); | 1671 | al = -1; |
1688 | 1672 | ||
1689 | al = -1; | 1673 | if (i != SSL_MAX_MASTER_KEY_LENGTH) { |
1674 | al = SSL_AD_DECODE_ERROR; | ||
1675 | /* SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,SSL_R_BAD_RSA_DECRYPT); */ | ||
1676 | } | ||
1690 | 1677 | ||
1691 | if (i != SSL_MAX_MASTER_KEY_LENGTH) { | 1678 | if (p - d + 2 > n) /* needed in the SSL3 case */ |
1679 | goto truncated; | ||
1680 | if ((al == -1) && !((p[0] == (s->client_version >> 8)) && | ||
1681 | (p[1] == (s->client_version & 0xff)))) { | ||
1682 | /* | ||
1683 | * The premaster secret must contain the same version | ||
1684 | * number as the ClientHello to detect version rollback | ||
1685 | * attacks (strangely, the protocol does not offer such | ||
1686 | * protection for DH ciphersuites). | ||
1687 | * However, buggy clients exist that send the negotiated | ||
1688 | * protocol version instead if the server does not | ||
1689 | * support the requested protocol version. | ||
1690 | * If SSL_OP_TLS_ROLLBACK_BUG is set, tolerate such | ||
1691 | * clients. | ||
1692 | */ | ||
1693 | if (!((s->options & SSL_OP_TLS_ROLLBACK_BUG) && | ||
1694 | (p[0] == (s->version >> 8)) && | ||
1695 | (p[1] == (s->version & 0xff)))) { | ||
1692 | al = SSL_AD_DECODE_ERROR; | 1696 | al = SSL_AD_DECODE_ERROR; |
1693 | /* SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,SSL_R_BAD_RSA_DECRYPT); */ | 1697 | /* SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,SSL_R_BAD_PROTOCOL_VERSION_NUMBER); */ |
1694 | } | ||
1695 | 1698 | ||
1696 | if (p - d + 2 > n) /* needed in the SSL3 case */ | ||
1697 | goto truncated; | ||
1698 | if ((al == -1) && !((p[0] == (s->client_version >> 8)) && | ||
1699 | (p[1] == (s->client_version & 0xff)))) { | ||
1700 | /* | 1699 | /* |
1701 | * The premaster secret must contain the same version | 1700 | * The Klima-Pokorny-Rosa extension of |
1702 | * number as the ClientHello to detect version rollback | 1701 | * Bleichenbacher's attack |
1703 | * attacks (strangely, the protocol does not offer such | 1702 | * (http://eprint.iacr.org/2003/052/) exploits |
1704 | * protection for DH ciphersuites). | 1703 | * the version number check as a "bad version |
1705 | * However, buggy clients exist that send the negotiated | 1704 | * oracle" -- an alert would reveal that the |
1706 | * protocol version instead if the server does not | 1705 | * plaintext corresponding to some ciphertext |
1707 | * support the requested protocol version. | 1706 | * made up by the adversary is properly |
1708 | * If SSL_OP_TLS_ROLLBACK_BUG is set, tolerate such | 1707 | * formatted except that the version number is |
1709 | * clients. | 1708 | * wrong. |
1709 | * To avoid such attacks, we should treat this | ||
1710 | * just like any other decryption error. | ||
1710 | */ | 1711 | */ |
1711 | if (!((s->options & SSL_OP_TLS_ROLLBACK_BUG) && | ||
1712 | (p[0] == (s->version >> 8)) && | ||
1713 | (p[1] == (s->version & 0xff)))) { | ||
1714 | al = SSL_AD_DECODE_ERROR; | ||
1715 | /* SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,SSL_R_BAD_PROTOCOL_VERSION_NUMBER); */ | ||
1716 | |||
1717 | /* | ||
1718 | * The Klima-Pokorny-Rosa extension of | ||
1719 | * Bleichenbacher's attack | ||
1720 | * (http://eprint.iacr.org/2003/052/) exploits | ||
1721 | * the version number check as a "bad version | ||
1722 | * oracle" -- an alert would reveal that the | ||
1723 | * plaintext corresponding to some ciphertext | ||
1724 | * made up by the adversary is properly | ||
1725 | * formatted except that the version number is | ||
1726 | * wrong. | ||
1727 | * To avoid such attacks, we should treat this | ||
1728 | * just like any other decryption error. | ||
1729 | */ | ||
1730 | } | ||
1731 | } | 1712 | } |
1713 | } | ||
1732 | 1714 | ||
1733 | if (al != -1) { | 1715 | if (al != -1) { |
1734 | /* | 1716 | /* |
1735 | * Some decryption failure -- use random value instead | 1717 | * Some decryption failure -- use random value instead |
1736 | * as countermeasure against Bleichenbacher's attack | 1718 | * as countermeasure against Bleichenbacher's attack |
1737 | * on PKCS #1 v1.5 RSA padding (see RFC 2246, | 1719 | * on PKCS #1 v1.5 RSA padding (see RFC 2246, |
1738 | * section 7.4.7.1). | 1720 | * section 7.4.7.1). |
1739 | */ | 1721 | */ |
1740 | i = SSL_MAX_MASTER_KEY_LENGTH; | 1722 | i = SSL_MAX_MASTER_KEY_LENGTH; |
1741 | p = fakekey; | 1723 | p = fakekey; |
1742 | } | 1724 | } |
1743 | 1725 | ||
1744 | s->session->master_key_length = | 1726 | s->session->master_key_length = |
1745 | s->method->ssl3_enc->generate_master_secret(s, | 1727 | s->method->ssl3_enc->generate_master_secret(s, |
1746 | s->session->master_key, | 1728 | s->session->master_key, p, i); |
1747 | p, i); | 1729 | |
1748 | explicit_bzero(p, i); | 1730 | explicit_bzero(p, i); |
1749 | } else if (alg_k & SSL_kDHE) { | 1731 | |
1750 | if (2 > n) | 1732 | return (1); |
1751 | goto truncated; | 1733 | truncated: |
1752 | n2s(p, i); | 1734 | al = SSL_AD_DECODE_ERROR; |
1753 | if (n != i + 2) { | 1735 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, SSL_R_BAD_PACKET_LENGTH); |
1754 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1736 | f_err: |
1755 | SSL_R_DH_PUBLIC_VALUE_LENGTH_IS_WRONG); | 1737 | ssl3_send_alert(s, SSL3_AL_FATAL, al); |
1756 | goto err; | 1738 | err: |
1757 | } | 1739 | return (-1); |
1740 | } | ||
1758 | 1741 | ||
1759 | if (n == 0L) { | 1742 | static int |
1760 | /* the parameters are in the cert */ | 1743 | ssl3_get_client_kex_dhe(SSL *s, unsigned char *p, long n) |
1744 | { | ||
1745 | BIGNUM *pub = NULL; | ||
1746 | DH *dh_srvr; | ||
1747 | int i, al; | ||
1748 | |||
1749 | if (2 > n) | ||
1750 | goto truncated; | ||
1751 | n2s(p, i); | ||
1752 | if (n != i + 2) { | ||
1753 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1754 | SSL_R_DH_PUBLIC_VALUE_LENGTH_IS_WRONG); | ||
1755 | goto err; | ||
1756 | } | ||
1757 | |||
1758 | if (n == 0L) { | ||
1759 | /* the parameters are in the cert */ | ||
1760 | al = SSL_AD_HANDSHAKE_FAILURE; | ||
1761 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1762 | SSL_R_UNABLE_TO_DECODE_DH_CERTS); | ||
1763 | goto f_err; | ||
1764 | } else { | ||
1765 | if (s->s3->tmp.dh == NULL) { | ||
1761 | al = SSL_AD_HANDSHAKE_FAILURE; | 1766 | al = SSL_AD_HANDSHAKE_FAILURE; |
1762 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1767 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, |
1763 | SSL_R_UNABLE_TO_DECODE_DH_CERTS); | 1768 | SSL_R_MISSING_TMP_DH_KEY); |
1764 | goto f_err; | 1769 | goto f_err; |
1765 | } else { | 1770 | } else |
1766 | if (s->s3->tmp.dh == NULL) { | 1771 | dh_srvr = s->s3->tmp.dh; |
1767 | al = SSL_AD_HANDSHAKE_FAILURE; | 1772 | } |
1768 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1769 | SSL_R_MISSING_TMP_DH_KEY); | ||
1770 | goto f_err; | ||
1771 | } else | ||
1772 | dh_srvr = s->s3->tmp.dh; | ||
1773 | } | ||
1774 | 1773 | ||
1775 | pub = BN_bin2bn(p, i, NULL); | 1774 | pub = BN_bin2bn(p, i, NULL); |
1776 | if (pub == NULL) { | 1775 | if (pub == NULL) { |
1777 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1776 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, |
1778 | SSL_R_BN_LIB); | 1777 | SSL_R_BN_LIB); |
1779 | goto err; | 1778 | goto err; |
1780 | } | 1779 | } |
1781 | 1780 | ||
1782 | i = DH_compute_key(p, pub, dh_srvr); | 1781 | i = DH_compute_key(p, pub, dh_srvr); |
1783 | 1782 | ||
1784 | if (i <= 0) { | 1783 | if (i <= 0) { |
1784 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1785 | ERR_R_DH_LIB); | ||
1786 | BN_clear_free(pub); | ||
1787 | goto err; | ||
1788 | } | ||
1789 | |||
1790 | DH_free(s->s3->tmp.dh); | ||
1791 | s->s3->tmp.dh = NULL; | ||
1792 | |||
1793 | BN_clear_free(pub); | ||
1794 | pub = NULL; | ||
1795 | |||
1796 | s->session->master_key_length = | ||
1797 | s->method->ssl3_enc->generate_master_secret( | ||
1798 | s, s->session->master_key, p, i); | ||
1799 | |||
1800 | explicit_bzero(p, i); | ||
1801 | |||
1802 | return (1); | ||
1803 | |||
1804 | truncated: | ||
1805 | al = SSL_AD_DECODE_ERROR; | ||
1806 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, SSL_R_BAD_PACKET_LENGTH); | ||
1807 | f_err: | ||
1808 | ssl3_send_alert(s, SSL3_AL_FATAL, al); | ||
1809 | err: | ||
1810 | return (-1); | ||
1811 | } | ||
1812 | |||
1813 | static int | ||
1814 | ssl3_get_client_kex_ecdhe(SSL *s, unsigned char *p, long n) | ||
1815 | { | ||
1816 | EC_KEY *srvr_ecdh = NULL; | ||
1817 | EVP_PKEY *clnt_pub_pkey = NULL; | ||
1818 | EC_POINT *clnt_ecpoint = NULL; | ||
1819 | BN_CTX *bn_ctx = NULL; | ||
1820 | int i, al; | ||
1821 | |||
1822 | int ret = 1; | ||
1823 | int key_size; | ||
1824 | const EC_KEY *tkey; | ||
1825 | const EC_GROUP *group; | ||
1826 | const BIGNUM *priv_key; | ||
1827 | |||
1828 | /* Initialize structures for server's ECDH key pair. */ | ||
1829 | if ((srvr_ecdh = EC_KEY_new()) == NULL) { | ||
1830 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1831 | ERR_R_MALLOC_FAILURE); | ||
1832 | goto err; | ||
1833 | } | ||
1834 | |||
1835 | /* | ||
1836 | * Use the ephemeral values we saved when | ||
1837 | * generating the ServerKeyExchange message. | ||
1838 | */ | ||
1839 | tkey = s->s3->tmp.ecdh; | ||
1840 | |||
1841 | group = EC_KEY_get0_group(tkey); | ||
1842 | priv_key = EC_KEY_get0_private_key(tkey); | ||
1843 | |||
1844 | if (!EC_KEY_set_group(srvr_ecdh, group) || | ||
1845 | !EC_KEY_set_private_key(srvr_ecdh, priv_key)) { | ||
1846 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1847 | ERR_R_EC_LIB); | ||
1848 | goto err; | ||
1849 | } | ||
1850 | |||
1851 | /* Let's get client's public key */ | ||
1852 | if ((clnt_ecpoint = EC_POINT_new(group)) == NULL) { | ||
1853 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1854 | ERR_R_MALLOC_FAILURE); | ||
1855 | goto err; | ||
1856 | } | ||
1857 | |||
1858 | if (n == 0L) { | ||
1859 | /* Client Publickey was in Client Certificate */ | ||
1860 | if (((clnt_pub_pkey = X509_get_pubkey( | ||
1861 | s->session->peer)) == NULL) || | ||
1862 | (clnt_pub_pkey->type != EVP_PKEY_EC)) { | ||
1863 | /* | ||
1864 | * XXX: For now, we do not support client | ||
1865 | * authentication using ECDH certificates | ||
1866 | * so this branch (n == 0L) of the code is | ||
1867 | * never executed. When that support is | ||
1868 | * added, we ought to ensure the key | ||
1869 | * received in the certificate is | ||
1870 | * authorized for key agreement. | ||
1871 | * ECDH_compute_key implicitly checks that | ||
1872 | * the two ECDH shares are for the same | ||
1873 | * group. | ||
1874 | */ | ||
1875 | al = SSL_AD_HANDSHAKE_FAILURE; | ||
1785 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1876 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, |
1786 | ERR_R_DH_LIB); | 1877 | SSL_R_UNABLE_TO_DECODE_ECDH_CERTS); |
1787 | BN_clear_free(pub); | 1878 | goto f_err; |
1788 | goto err; | ||
1789 | } | 1879 | } |
1790 | 1880 | ||
1791 | DH_free(s->s3->tmp.dh); | 1881 | if (EC_POINT_copy(clnt_ecpoint, |
1792 | s->s3->tmp.dh = NULL; | 1882 | EC_KEY_get0_public_key(clnt_pub_pkey->pkey.ec)) |
1793 | 1883 | == 0) { | |
1794 | BN_clear_free(pub); | ||
1795 | pub = NULL; | ||
1796 | s->session->master_key_length = | ||
1797 | s->method->ssl3_enc->generate_master_secret( | ||
1798 | s, s->session->master_key, p, i); | ||
1799 | explicit_bzero(p, i); | ||
1800 | } else if (alg_k & SSL_kECDHE) { | ||
1801 | int ret = 1; | ||
1802 | int key_size; | ||
1803 | const EC_KEY *tkey; | ||
1804 | const EC_GROUP *group; | ||
1805 | const BIGNUM *priv_key; | ||
1806 | |||
1807 | /* Initialize structures for server's ECDH key pair. */ | ||
1808 | if ((srvr_ecdh = EC_KEY_new()) == NULL) { | ||
1809 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1884 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, |
1810 | ERR_R_MALLOC_FAILURE); | 1885 | ERR_R_EC_LIB); |
1811 | goto err; | 1886 | goto err; |
1812 | } | 1887 | } |
1813 | 1888 | ret = 2; /* Skip certificate verify processing */ | |
1889 | } else { | ||
1814 | /* | 1890 | /* |
1815 | * Use the ephemeral values we saved when | 1891 | * Get client's public key from encoded point |
1816 | * generating the ServerKeyExchange message. | 1892 | * in the ClientKeyExchange message. |
1817 | */ | 1893 | */ |
1818 | tkey = s->s3->tmp.ecdh; | 1894 | if ((bn_ctx = BN_CTX_new()) == NULL) { |
1895 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1896 | ERR_R_MALLOC_FAILURE); | ||
1897 | goto err; | ||
1898 | } | ||
1819 | 1899 | ||
1820 | group = EC_KEY_get0_group(tkey); | 1900 | /* Get encoded point length */ |
1821 | priv_key = EC_KEY_get0_private_key(tkey); | 1901 | i = *p; |
1822 | 1902 | ||
1823 | if (!EC_KEY_set_group(srvr_ecdh, group) || | 1903 | p += 1; |
1824 | !EC_KEY_set_private_key(srvr_ecdh, priv_key)) { | 1904 | if (n != 1 + i) { |
1825 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1905 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, |
1826 | ERR_R_EC_LIB); | 1906 | ERR_R_EC_LIB); |
1827 | goto err; | 1907 | goto err; |
1828 | } | 1908 | } |
1829 | 1909 | if (EC_POINT_oct2point(group, | |
1830 | /* Let's get client's public key */ | 1910 | clnt_ecpoint, p, i, bn_ctx) == 0) { |
1831 | if ((clnt_ecpoint = EC_POINT_new(group)) == NULL) { | ||
1832 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1911 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, |
1833 | ERR_R_MALLOC_FAILURE); | 1912 | ERR_R_EC_LIB); |
1834 | goto err; | 1913 | goto err; |
1835 | } | 1914 | } |
1915 | /* | ||
1916 | * p is pointing to somewhere in the buffer | ||
1917 | * currently, so set it to the start. | ||
1918 | */ | ||
1919 | p = (unsigned char *)s->init_buf->data; | ||
1920 | } | ||
1836 | 1921 | ||
1837 | if (n == 0L) { | 1922 | /* Compute the shared pre-master secret */ |
1838 | /* Client Publickey was in Client Certificate */ | 1923 | key_size = ECDH_size(srvr_ecdh); |
1839 | if (((clnt_pub_pkey = X509_get_pubkey( | 1924 | if (key_size <= 0) { |
1840 | s->session->peer)) == NULL) || | 1925 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, |
1841 | (clnt_pub_pkey->type != EVP_PKEY_EC)) { | 1926 | ERR_R_ECDH_LIB); |
1842 | /* | 1927 | goto err; |
1843 | * XXX: For now, we do not support client | 1928 | } |
1844 | * authentication using ECDH certificates | 1929 | i = ECDH_compute_key(p, key_size, clnt_ecpoint, srvr_ecdh, |
1845 | * so this branch (n == 0L) of the code is | 1930 | NULL); |
1846 | * never executed. When that support is | 1931 | if (i <= 0) { |
1847 | * added, we ought to ensure the key | 1932 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, |
1848 | * received in the certificate is | 1933 | ERR_R_ECDH_LIB); |
1849 | * authorized for key agreement. | 1934 | goto err; |
1850 | * ECDH_compute_key implicitly checks that | 1935 | } |
1851 | * the two ECDH shares are for the same | ||
1852 | * group. | ||
1853 | */ | ||
1854 | al = SSL_AD_HANDSHAKE_FAILURE; | ||
1855 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1856 | SSL_R_UNABLE_TO_DECODE_ECDH_CERTS); | ||
1857 | goto f_err; | ||
1858 | } | ||
1859 | 1936 | ||
1860 | if (EC_POINT_copy(clnt_ecpoint, | 1937 | EVP_PKEY_free(clnt_pub_pkey); |
1861 | EC_KEY_get0_public_key(clnt_pub_pkey->pkey.ec)) | 1938 | EC_POINT_free(clnt_ecpoint); |
1862 | == 0) { | 1939 | EC_KEY_free(srvr_ecdh); |
1863 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1940 | BN_CTX_free(bn_ctx); |
1864 | ERR_R_EC_LIB); | 1941 | EC_KEY_free(s->s3->tmp.ecdh); |
1865 | goto err; | 1942 | s->s3->tmp.ecdh = NULL; |
1866 | } | ||
1867 | ret = 2; /* Skip certificate verify processing */ | ||
1868 | } else { | ||
1869 | /* | ||
1870 | * Get client's public key from encoded point | ||
1871 | * in the ClientKeyExchange message. | ||
1872 | */ | ||
1873 | if ((bn_ctx = BN_CTX_new()) == NULL) { | ||
1874 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1875 | ERR_R_MALLOC_FAILURE); | ||
1876 | goto err; | ||
1877 | } | ||
1878 | 1943 | ||
1879 | /* Get encoded point length */ | 1944 | /* Compute the master secret */ |
1880 | i = *p; | 1945 | s->session->master_key_length = |
1946 | s->method->ssl3_enc->generate_master_secret( | ||
1947 | s, s->session->master_key, p, i); | ||
1881 | 1948 | ||
1882 | p += 1; | 1949 | explicit_bzero(p, i); |
1883 | if (n != 1 + i) { | 1950 | return (ret); |
1884 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1885 | ERR_R_EC_LIB); | ||
1886 | goto err; | ||
1887 | } | ||
1888 | if (EC_POINT_oct2point(group, | ||
1889 | clnt_ecpoint, p, i, bn_ctx) == 0) { | ||
1890 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1891 | ERR_R_EC_LIB); | ||
1892 | goto err; | ||
1893 | } | ||
1894 | /* | ||
1895 | * p is pointing to somewhere in the buffer | ||
1896 | * currently, so set it to the start. | ||
1897 | */ | ||
1898 | p = (unsigned char *)s->init_buf->data; | ||
1899 | } | ||
1900 | 1951 | ||
1901 | /* Compute the shared pre-master secret */ | 1952 | f_err: |
1902 | key_size = ECDH_size(srvr_ecdh); | 1953 | ssl3_send_alert(s, SSL3_AL_FATAL, al); |
1903 | if (key_size <= 0) { | 1954 | err: |
1904 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 1955 | EVP_PKEY_free(clnt_pub_pkey); |
1905 | ERR_R_ECDH_LIB); | 1956 | EC_POINT_free(clnt_ecpoint); |
1906 | goto err; | 1957 | EC_KEY_free(srvr_ecdh); |
1907 | } | 1958 | BN_CTX_free(bn_ctx); |
1908 | i = ECDH_compute_key(p, key_size, clnt_ecpoint, srvr_ecdh, | 1959 | return (-1); |
1909 | NULL); | 1960 | } |
1910 | if (i <= 0) { | ||
1911 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1912 | ERR_R_ECDH_LIB); | ||
1913 | goto err; | ||
1914 | } | ||
1915 | 1961 | ||
1916 | EVP_PKEY_free(clnt_pub_pkey); | 1962 | static int |
1917 | EC_POINT_free(clnt_ecpoint); | 1963 | ssl3_get_client_kex_gost(SSL *s, unsigned char *p, long n) |
1918 | EC_KEY_free(srvr_ecdh); | 1964 | { |
1919 | BN_CTX_free(bn_ctx); | ||
1920 | EC_KEY_free(s->s3->tmp.ecdh); | ||
1921 | s->s3->tmp.ecdh = NULL; | ||
1922 | 1965 | ||
1966 | EVP_PKEY_CTX *pkey_ctx; | ||
1967 | EVP_PKEY *client_pub_pkey = NULL, *pk = NULL; | ||
1968 | unsigned char premaster_secret[32], *start; | ||
1969 | size_t outlen = 32, inlen; | ||
1970 | unsigned long alg_a; | ||
1971 | int Ttag, Tclass; | ||
1972 | long Tlen; | ||
1973 | int al; | ||
1974 | int ret = 0; | ||
1923 | 1975 | ||
1924 | /* Compute the master secret */ | 1976 | /* Get our certificate private key*/ |
1925 | s->session->master_key_length = s->method->ssl3_enc-> \ | 1977 | alg_a = s->s3->tmp.new_cipher->algorithm_auth; |
1926 | generate_master_secret(s, s->session->master_key, p, i); | 1978 | if (alg_a & SSL_aGOST01) |
1979 | pk = s->cert->pkeys[SSL_PKEY_GOST01].privatekey; | ||
1927 | 1980 | ||
1928 | explicit_bzero(p, i); | 1981 | pkey_ctx = EVP_PKEY_CTX_new(pk, NULL); |
1982 | EVP_PKEY_decrypt_init(pkey_ctx); | ||
1983 | /* | ||
1984 | * If client certificate is present and is of the same type, | ||
1985 | * maybe use it for key exchange. | ||
1986 | * Don't mind errors from EVP_PKEY_derive_set_peer, because | ||
1987 | * it is completely valid to use a client certificate for | ||
1988 | * authorization only. | ||
1989 | */ | ||
1990 | client_pub_pkey = X509_get_pubkey(s->session->peer); | ||
1991 | if (client_pub_pkey) { | ||
1992 | if (EVP_PKEY_derive_set_peer(pkey_ctx, | ||
1993 | client_pub_pkey) <= 0) | ||
1994 | ERR_clear_error(); | ||
1995 | } | ||
1996 | if (2 > n) | ||
1997 | goto truncated; | ||
1998 | /* Decrypt session key */ | ||
1999 | if (ASN1_get_object((const unsigned char **)&p, &Tlen, &Ttag, | ||
2000 | &Tclass, n) != V_ASN1_CONSTRUCTED || | ||
2001 | Ttag != V_ASN1_SEQUENCE || Tclass != V_ASN1_UNIVERSAL) { | ||
2002 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
2003 | SSL_R_DECRYPTION_FAILED); | ||
2004 | goto gerr; | ||
2005 | } | ||
2006 | start = p; | ||
2007 | inlen = Tlen; | ||
2008 | if (EVP_PKEY_decrypt(pkey_ctx, premaster_secret, &outlen, | ||
2009 | start, inlen) <=0) { | ||
2010 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
2011 | SSL_R_DECRYPTION_FAILED); | ||
2012 | goto gerr; | ||
2013 | } | ||
2014 | /* Generate master secret */ | ||
2015 | s->session->master_key_length = | ||
2016 | s->method->ssl3_enc->generate_master_secret( | ||
2017 | s, s->session->master_key, premaster_secret, 32); | ||
2018 | /* Check if pubkey from client certificate was used */ | ||
2019 | if (EVP_PKEY_CTX_ctrl(pkey_ctx, -1, -1, | ||
2020 | EVP_PKEY_CTRL_PEER_KEY, 2, NULL) > 0) | ||
2021 | ret = 2; | ||
2022 | else | ||
2023 | ret = 1; | ||
2024 | gerr: | ||
2025 | EVP_PKEY_free(client_pub_pkey); | ||
2026 | EVP_PKEY_CTX_free(pkey_ctx); | ||
2027 | if (ret) | ||
1929 | return (ret); | 2028 | return (ret); |
1930 | } else | 2029 | else |
1931 | if (alg_k & SSL_kGOST) { | 2030 | goto err; |
1932 | int ret = 0; | 2031 | |
1933 | EVP_PKEY_CTX *pkey_ctx; | 2032 | truncated: |
1934 | EVP_PKEY *client_pub_pkey = NULL, *pk = NULL; | 2033 | al = SSL_AD_DECODE_ERROR; |
1935 | unsigned char premaster_secret[32], *start; | 2034 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, SSL_R_BAD_PACKET_LENGTH); |
1936 | size_t outlen = 32, inlen; | 2035 | ssl3_send_alert(s, SSL3_AL_FATAL, al); |
1937 | unsigned long alg_a; | 2036 | err: |
1938 | int Ttag, Tclass; | 2037 | return (-1); |
1939 | long Tlen; | 2038 | } |
1940 | 2039 | ||
1941 | /* Get our certificate private key*/ | 2040 | int |
1942 | alg_a = s->s3->tmp.new_cipher->algorithm_auth; | 2041 | ssl3_get_client_key_exchange(SSL *s) |
1943 | if (alg_a & SSL_aGOST01) | 2042 | { |
1944 | pk = s->cert->pkeys[SSL_PKEY_GOST01].privatekey; | 2043 | unsigned long alg_k; |
1945 | 2044 | unsigned char *p; | |
1946 | pkey_ctx = EVP_PKEY_CTX_new(pk, NULL); | 2045 | int al, ok; |
1947 | EVP_PKEY_decrypt_init(pkey_ctx); | 2046 | long n; |
1948 | /* | 2047 | |
1949 | * If client certificate is present and is of the same type, | 2048 | /* 2048 maxlen is a guess. How long a key does that permit? */ |
1950 | * maybe use it for key exchange. | 2049 | n = s->method->ssl_get_message(s, SSL3_ST_SR_KEY_EXCH_A, |
1951 | * Don't mind errors from EVP_PKEY_derive_set_peer, because | 2050 | SSL3_ST_SR_KEY_EXCH_B, SSL3_MT_CLIENT_KEY_EXCHANGE, 2048, &ok); |
1952 | * it is completely valid to use a client certificate for | 2051 | if (!ok) |
1953 | * authorization only. | 2052 | return ((int)n); |
1954 | */ | 2053 | |
1955 | client_pub_pkey = X509_get_pubkey(s->session->peer); | 2054 | p = (unsigned char *)s->init_msg; |
1956 | if (client_pub_pkey) { | 2055 | |
1957 | if (EVP_PKEY_derive_set_peer(pkey_ctx, | 2056 | alg_k = s->s3->tmp.new_cipher->algorithm_mkey; |
1958 | client_pub_pkey) <= 0) | 2057 | |
1959 | ERR_clear_error(); | 2058 | if (alg_k & SSL_kRSA) { |
1960 | } | 2059 | if (ssl3_get_client_kex_rsa(s, p, n) != 1) |
1961 | if (2 > n) | 2060 | goto err; |
1962 | goto truncated; | 2061 | } else if (alg_k & SSL_kDHE) { |
1963 | /* Decrypt session key */ | 2062 | if (ssl3_get_client_kex_dhe(s, p, n) != 1) |
1964 | if (ASN1_get_object((const unsigned char **)&p, &Tlen, &Ttag, | 2063 | goto err; |
1965 | &Tclass, n) != V_ASN1_CONSTRUCTED || | 2064 | } else if (alg_k & SSL_kECDHE) { |
1966 | Ttag != V_ASN1_SEQUENCE || Tclass != V_ASN1_UNIVERSAL) { | 2065 | if (ssl3_get_client_kex_ecdhe(s, p, n) != 1) |
1967 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | 2066 | goto err; |
1968 | SSL_R_DECRYPTION_FAILED); | 2067 | } else if (alg_k & SSL_kGOST) { |
1969 | goto gerr; | 2068 | if (ssl3_get_client_kex_gost(s, p, n) != 1) |
1970 | } | ||
1971 | start = p; | ||
1972 | inlen = Tlen; | ||
1973 | if (EVP_PKEY_decrypt(pkey_ctx, premaster_secret, &outlen, | ||
1974 | start, inlen) <=0) { | ||
1975 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, | ||
1976 | SSL_R_DECRYPTION_FAILED); | ||
1977 | goto gerr; | ||
1978 | } | ||
1979 | /* Generate master secret */ | ||
1980 | s->session->master_key_length = | ||
1981 | s->method->ssl3_enc->generate_master_secret( | ||
1982 | s, s->session->master_key, premaster_secret, 32); | ||
1983 | /* Check if pubkey from client certificate was used */ | ||
1984 | if (EVP_PKEY_CTX_ctrl(pkey_ctx, -1, -1, | ||
1985 | EVP_PKEY_CTRL_PEER_KEY, 2, NULL) > 0) | ||
1986 | ret = 2; | ||
1987 | else | ||
1988 | ret = 1; | ||
1989 | gerr: | ||
1990 | EVP_PKEY_free(client_pub_pkey); | ||
1991 | EVP_PKEY_CTX_free(pkey_ctx); | ||
1992 | if (ret) | ||
1993 | return (ret); | ||
1994 | else | ||
1995 | goto err; | 2069 | goto err; |
1996 | } else { | 2070 | } else { |
1997 | al = SSL_AD_HANDSHAKE_FAILURE; | 2071 | al = SSL_AD_HANDSHAKE_FAILURE; |
@@ -2001,16 +2075,10 @@ gerr: | |||
2001 | } | 2075 | } |
2002 | 2076 | ||
2003 | return (1); | 2077 | return (1); |
2004 | truncated: | 2078 | |
2005 | al = SSL_AD_DECODE_ERROR; | 2079 | f_err: |
2006 | SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, SSL_R_BAD_PACKET_LENGTH); | ||
2007 | f_err: | ||
2008 | ssl3_send_alert(s, SSL3_AL_FATAL, al); | 2080 | ssl3_send_alert(s, SSL3_AL_FATAL, al); |
2009 | err: | 2081 | err: |
2010 | EVP_PKEY_free(clnt_pub_pkey); | ||
2011 | EC_POINT_free(clnt_ecpoint); | ||
2012 | EC_KEY_free(srvr_ecdh); | ||
2013 | BN_CTX_free(bn_ctx); | ||
2014 | return (-1); | 2082 | return (-1); |
2015 | } | 2083 | } |
2016 | 2084 | ||