Botan  1.10.9
ec_group.cpp
Go to the documentation of this file.
1 /*
2 * ECC Domain Parameters
3 *
4 * (C) 2007 Falko Strenzke, FlexSecure GmbH
5 * 2008 Jack Lloyd
6 *
7 * Distributed under the terms of the Botan license
8 */
9 
10 #include <botan/ec_group.h>
11 #include <botan/ber_dec.h>
12 #include <botan/der_enc.h>
13 #include <botan/libstate.h>
14 #include <botan/oids.h>
15 #include <botan/pem.h>
16 
17 namespace Botan {
18 
19 EC_Group::EC_Group(const OID& domain_oid)
20  {
21  std::string pem =
22  global_state().get("ec", OIDS::lookup(domain_oid));
23 
24  if(pem == "")
25  throw Lookup_Error("No ECC domain data for " + domain_oid.as_string());
26 
27  *this = EC_Group(pem);
28  oid = domain_oid.as_string();
29  }
30 
31 EC_Group::EC_Group(const std::string& str)
32  {
33  if(str == "")
34  return; // no initialization / uninitialized
35 
36  try
37  {
38  DataSource_Memory input(str);
39 
40  SecureVector<byte> ber =
41  PEM_Code::decode_check_label(input, "EC PARAMETERS");
42 
43  *this = EC_Group(ber);
44  }
45  catch(Decoding_Error) // hmm, not PEM?
46  {
47  *this = EC_Group(OIDS::lookup(str));
48  }
49  }
50 
52  {
53  BER_Decoder ber(ber_data);
54  BER_Object obj = ber.get_next_object();
55 
56  if(obj.type_tag == NULL_TAG)
57  throw Decoding_Error("Cannot handle ImplicitCA ECDSA parameters");
58  else if(obj.type_tag == OBJECT_ID)
59  {
60  OID dom_par_oid;
61  BER_Decoder(ber_data).decode(dom_par_oid);
62  *this = EC_Group(dom_par_oid);
63  }
64  else if(obj.type_tag == SEQUENCE)
65  {
66  BigInt p, a, b;
67  SecureVector<byte> sv_base_point;
68 
69  BER_Decoder(ber_data)
71  .decode_and_check<size_t>(1, "Unknown ECC param version code")
72  .start_cons(SEQUENCE)
73  .decode_and_check(OID("1.2.840.10045.1.1"),
74  "Only prime ECC fields supported")
75  .decode(p)
76  .end_cons()
80  .end_cons()
81  .decode(sv_base_point, OCTET_STRING)
82  .decode(order)
83  .decode(cofactor)
84  .end_cons()
85  .verify_end();
86 
87  curve = CurveGFp(p, a, b);
88  base_point = OS2ECP(sv_base_point, curve);
89  }
90  else
91  throw Decoding_Error("Unexpected tag while decoding ECC domain params");
92  }
93 
96  {
97  if(form == EC_DOMPAR_ENC_EXPLICIT)
98  {
99  const size_t ecpVers1 = 1;
100  OID curve_type("1.2.840.10045.1.1");
101 
102  const size_t p_bytes = curve.get_p().bytes();
103 
104  return DER_Encoder()
106  .encode(ecpVers1)
108  .encode(curve_type)
109  .encode(curve.get_p())
110  .end_cons()
112  .encode(BigInt::encode_1363(curve.get_a(), p_bytes),
113  OCTET_STRING)
114  .encode(BigInt::encode_1363(curve.get_b(), p_bytes),
115  OCTET_STRING)
116  .end_cons()
118  .encode(order)
119  .encode(cofactor)
120  .end_cons()
121  .get_contents();
122  }
123  else if(form == EC_DOMPAR_ENC_OID)
124  return DER_Encoder().encode(OID(get_oid())).get_contents();
125  else if(form == EC_DOMPAR_ENC_IMPLICITCA)
126  return DER_Encoder().encode_null().get_contents();
127  else
128  throw Internal_Error("EC_Group::DER_encode: Unknown encoding");
129  }
130 
131 std::string EC_Group::PEM_encode() const
132  {
134  return PEM_Code::encode(der, "EC PARAMETERS");
135  }
136 
137 }
const BigInt & get_a() const
Definition: curve_gfp.h:53
SecureVector< byte > get_contents()
Definition: der_enc.cpp:122
std::string get_oid() const
Definition: ec_group.h:115
const BigInt & get_b() const
Definition: curve_gfp.h:58
BER_Decoder & decode(bool &)
Definition: ber_dec.cpp:338
BER_Decoder & decode_and_check(const T &expected, const std::string &error_msg)
Definition: ber_dec.h:62
PointGFp OS2ECP(const byte data[], size_t data_len, const CurveGFp &curve)
Definition: point_gfp.cpp:554
DER_Encoder & end_cons()
Definition: der_enc.cpp:145
BER_Decoder start_cons(ASN1_Tag, ASN1_Tag=UNIVERSAL)
Definition: ber_dec.cpp:232
SecureVector< byte > EC2OSP(const PointGFp &point, byte format)
Definition: point_gfp.cpp:482
DER_Encoder & encode(bool b)
Definition: der_enc.cpp:209
BER_Decoder & decode_octet_string_bigint(class BigInt &)
Definition: ber_dec.cpp:359
BER_Decoder & end_cons()
Definition: ber_dec.cpp:246
Library_State & global_state()
std::string lookup(const OID &oid)
Definition: oids.cpp:31
std::string PEM_encode() const
Definition: ec_group.cpp:131
DER_Encoder & encode_null()
Definition: der_enc.cpp:201
SecureVector< byte > DER_encode(EC_Group_Encoding form) const
Definition: ec_group.cpp:95
EC_Group(const CurveGFp &curve, const PointGFp &base_point, const BigInt &order, const BigInt &cofactor)
Definition: ec_group.h:42
BER_Object get_next_object()
Definition: ber_dec.cpp:193
EC_Group_Encoding
Definition: ec_group.h:22
std::string encode(const byte der[], size_t length, const std::string &label, size_t width)
Definition: pem.cpp:19
const BigInt & get_p() const
Definition: curve_gfp.h:64
ASN1_Tag type_tag
Definition: asn1_int.h:82
BER_Decoder & verify_end()
Definition: ber_dec.cpp:160
std::string as_string() const
Definition: asn1_oid.cpp:50
DER_Encoder & start_cons(ASN1_Tag type_tag, ASN1_Tag class_tag=UNIVERSAL)
Definition: der_enc.cpp:135
static SecureVector< byte > encode_1363(const BigInt &n, size_t bytes)
Definition: big_code.cpp:78
SecureVector< byte > decode_check_label(DataSource &source, const std::string &label_want)
Definition: pem.cpp:42
std::string get(const std::string &section, const std::string &key) const
Definition: libstate.cpp:114
size_t bytes() const
Definition: bigint.cpp:245