1/* ==================================================================== 2 * Copyright (c) 1998-2005 The OpenSSL Project. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in 13 * the documentation and/or other materials provided with the 14 * distribution. 15 * 16 * 3. All advertising materials mentioning features or use of this 17 * software must display the following acknowledgment: 18 * "This product includes software developed by the OpenSSL Project 19 * for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)" 20 * 21 * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to 22 * endorse or promote products derived from this software without 23 * prior written permission. For written permission, please contact 24 * openssl-core@OpenSSL.org. 25 * 26 * 5. Products derived from this software may not be called "OpenSSL" 27 * nor may "OpenSSL" appear in their names without prior written 28 * permission of the OpenSSL Project. 29 * 30 * 6. Redistributions of any form whatsoever must retain the following 31 * acknowledgment: 32 * "This product includes software developed by the OpenSSL Project 33 * for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)" 34 * 35 * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY 36 * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 37 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 38 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR 39 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 40 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 41 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 42 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 43 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 44 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 45 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED 46 * OF THE POSSIBILITY OF SUCH DAMAGE. 47 * ==================================================================== 48 * 49 * This product includes cryptographic software written by Eric Young 50 * (eay@cryptsoft.com). This product includes software written by Tim 51 * Hudson (tjh@cryptsoft.com). */ 52 53#include <openssl/ecdsa.h> 54 55#include <limits.h> 56#include <string.h> 57 58#include <openssl/bn.h> 59#include <openssl/bytestring.h> 60#include <openssl/err.h> 61#include <openssl/ec_key.h> 62#include <openssl/mem.h> 63 64#include "../ec/internal.h" 65 66 67size_t ECDSA_size(const EC_KEY *key) { 68 if (key == NULL) { 69 return 0; 70 } 71 72 size_t group_order_size; 73 if (key->ecdsa_meth && key->ecdsa_meth->group_order_size) { 74 group_order_size = key->ecdsa_meth->group_order_size(key); 75 } else { 76 const EC_GROUP *group = EC_KEY_get0_group(key); 77 if (group == NULL) { 78 return 0; 79 } 80 81 group_order_size = BN_num_bytes(EC_GROUP_get0_order(group)); 82 } 83 84 return ECDSA_SIG_max_len(group_order_size); 85} 86 87ECDSA_SIG *ECDSA_SIG_new(void) { 88 ECDSA_SIG *sig = OPENSSL_malloc(sizeof(ECDSA_SIG)); 89 if (sig == NULL) { 90 return NULL; 91 } 92 sig->r = BN_new(); 93 sig->s = BN_new(); 94 if (sig->r == NULL || sig->s == NULL) { 95 ECDSA_SIG_free(sig); 96 return NULL; 97 } 98 return sig; 99} 100 101void ECDSA_SIG_free(ECDSA_SIG *sig) { 102 if (sig == NULL) { 103 return; 104 } 105 106 BN_free(sig->r); 107 BN_free(sig->s); 108 OPENSSL_free(sig); 109} 110 111ECDSA_SIG *ECDSA_SIG_parse(CBS *cbs) { 112 ECDSA_SIG *ret = ECDSA_SIG_new(); 113 if (ret == NULL) { 114 return NULL; 115 } 116 CBS child; 117 if (!CBS_get_asn1(cbs, &child, CBS_ASN1_SEQUENCE) || 118 !BN_cbs2unsigned(&child, ret->r) || 119 !BN_cbs2unsigned(&child, ret->s) || 120 CBS_len(&child) != 0) { 121 OPENSSL_PUT_ERROR(ECDSA, ECDSA_R_BAD_SIGNATURE); 122 ECDSA_SIG_free(ret); 123 return NULL; 124 } 125 return ret; 126} 127 128ECDSA_SIG *ECDSA_SIG_from_bytes(const uint8_t *in, size_t in_len) { 129 CBS cbs; 130 CBS_init(&cbs, in, in_len); 131 ECDSA_SIG *ret = ECDSA_SIG_parse(&cbs); 132 if (ret == NULL || CBS_len(&cbs) != 0) { 133 OPENSSL_PUT_ERROR(ECDSA, ECDSA_R_BAD_SIGNATURE); 134 ECDSA_SIG_free(ret); 135 return NULL; 136 } 137 return ret; 138} 139 140int ECDSA_SIG_marshal(CBB *cbb, const ECDSA_SIG *sig) { 141 CBB child; 142 if (!CBB_add_asn1(cbb, &child, CBS_ASN1_SEQUENCE) || 143 !BN_bn2cbb(&child, sig->r) || 144 !BN_bn2cbb(&child, sig->s) || 145 !CBB_flush(cbb)) { 146 OPENSSL_PUT_ERROR(ECDSA, ECDSA_R_ENCODE_ERROR); 147 return 0; 148 } 149 return 1; 150} 151 152int ECDSA_SIG_to_bytes(uint8_t **out_bytes, size_t *out_len, 153 const ECDSA_SIG *sig) { 154 CBB cbb; 155 CBB_zero(&cbb); 156 if (!CBB_init(&cbb, 0) || 157 !ECDSA_SIG_marshal(&cbb, sig) || 158 !CBB_finish(&cbb, out_bytes, out_len)) { 159 OPENSSL_PUT_ERROR(ECDSA, ECDSA_R_ENCODE_ERROR); 160 CBB_cleanup(&cbb); 161 return 0; 162 } 163 return 1; 164} 165 166/* der_len_len returns the number of bytes needed to represent a length of |len| 167 * in DER. */ 168static size_t der_len_len(size_t len) { 169 if (len < 0x80) { 170 return 1; 171 } 172 size_t ret = 1; 173 while (len > 0) { 174 ret++; 175 len >>= 8; 176 } 177 return ret; 178} 179 180size_t ECDSA_SIG_max_len(size_t order_len) { 181 /* Compute the maximum length of an |order_len| byte integer. Defensively 182 * assume that the leading 0x00 is included. */ 183 size_t integer_len = 1 /* tag */ + der_len_len(order_len + 1) + 1 + order_len; 184 if (integer_len < order_len) { 185 return 0; 186 } 187 /* An ECDSA signature is two INTEGERs. */ 188 size_t value_len = 2 * integer_len; 189 if (value_len < integer_len) { 190 return 0; 191 } 192 /* Add the header. */ 193 size_t ret = 1 /* tag */ + der_len_len(value_len) + value_len; 194 if (ret < value_len) { 195 return 0; 196 } 197 return ret; 198} 199 200ECDSA_SIG *d2i_ECDSA_SIG(ECDSA_SIG **out, const uint8_t **inp, long len) { 201 if (len < 0) { 202 return NULL; 203 } 204 CBS cbs; 205 CBS_init(&cbs, *inp, (size_t)len); 206 ECDSA_SIG *ret = ECDSA_SIG_parse(&cbs); 207 if (ret == NULL) { 208 return NULL; 209 } 210 if (out != NULL) { 211 ECDSA_SIG_free(*out); 212 *out = ret; 213 } 214 *inp += (size_t)len - CBS_len(&cbs); 215 return ret; 216} 217 218int i2d_ECDSA_SIG(const ECDSA_SIG *sig, uint8_t **outp) { 219 uint8_t *der; 220 size_t der_len; 221 if (!ECDSA_SIG_to_bytes(&der, &der_len, sig)) { 222 return -1; 223 } 224 if (der_len > INT_MAX) { 225 OPENSSL_PUT_ERROR(ECDSA, ERR_R_OVERFLOW); 226 OPENSSL_free(der); 227 return -1; 228 } 229 if (outp != NULL) { 230 if (*outp == NULL) { 231 *outp = der; 232 der = NULL; 233 } else { 234 memcpy(*outp, der, der_len); 235 *outp += der_len; 236 } 237 } 238 OPENSSL_free(der); 239 return (int)der_len; 240} 241