monotone

monotone Mtn Source Tree

Root/botan/rsa.cpp

1/*************************************************
2* RSA Source File *
3* (C) 1999-2006 The Botan Project *
4*************************************************/
5
6#include <botan/rsa.h>
7#include <botan/numthry.h>
8#include <botan/keypair.h>
9#include <botan/parsing.h>
10
11namespace Botan {
12
13/*************************************************
14* RSA_PublicKey Constructor *
15*************************************************/
16RSA_PublicKey::RSA_PublicKey(const BigInt& mod, const BigInt& exp)
17 {
18 n = mod;
19 e = exp;
20 X509_load_hook();
21 }
22
23/*************************************************
24* RSA Public Operation *
25*************************************************/
26BigInt RSA_PublicKey::public_op(const BigInt& i) const
27 {
28 if(i >= n)
29 throw Invalid_Argument(algo_name() + "::public_op: input is too large");
30 return core.public_op(i);
31 }
32
33/*************************************************
34* RSA Encryption Function *
35*************************************************/
36SecureVector<byte> RSA_PublicKey::encrypt(const byte in[], u32bit len) const
37 {
38 BigInt i(in, len);
39 return BigInt::encode_1363(public_op(i), n.bytes());
40 }
41
42/*************************************************
43* RSA Verification Function *
44*************************************************/
45SecureVector<byte> RSA_PublicKey::verify(const byte in[], u32bit len) const
46 {
47 BigInt i(in, len);
48 return BigInt::encode(public_op(i));
49 }
50
51/*************************************************
52* Create a RSA private key *
53*************************************************/
54RSA_PrivateKey::RSA_PrivateKey(u32bit bits, u32bit exp)
55 {
56 if(bits < 128)
57 throw Invalid_Argument(algo_name() + ": Can't make a key that is only " +
58 to_string(bits) + " bits long");
59 if(exp < 3 || exp % 2 == 0)
60 throw Invalid_Argument(algo_name() + ": Invalid encryption exponent");
61
62 e = exp;
63 p = random_prime((bits + 1) / 2, e);
64 q = random_prime(bits - p.bits(), e);
65 d = inverse_mod(e, lcm(p - 1, q - 1));
66
67 PKCS8_load_hook(true);
68
69 if(n.bits() != bits)
70 throw Self_Test_Failure(algo_name() + " private key generation failed");
71 }
72
73/*************************************************
74* RSA_PrivateKey Constructor *
75*************************************************/
76RSA_PrivateKey::RSA_PrivateKey(const BigInt& prime1, const BigInt& prime2,
77 const BigInt& exp, const BigInt& d_exp,
78 const BigInt& mod)
79 {
80 p = prime1;
81 q = prime2;
82 e = exp;
83 d = d_exp;
84 n = mod;
85
86 if(d == 0)
87 d = inverse_mod(e, lcm(p - 1, q - 1));
88
89 PKCS8_load_hook();
90 }
91
92/*************************************************
93* RSA Private Operation *
94*************************************************/
95BigInt RSA_PrivateKey::private_op(const byte in[], u32bit length) const
96 {
97 BigInt i(in, length);
98 if(i >= n)
99 throw Invalid_Argument(algo_name() + "::private_op: input is too large");
100
101 BigInt r = core.private_op(i);
102 if(i != public_op(r))
103 throw Self_Test_Failure(algo_name() + " private operation check failed");
104 return r;
105 }
106
107/*************************************************
108* RSA Decryption Operation *
109*************************************************/
110SecureVector<byte> RSA_PrivateKey::decrypt(const byte in[], u32bit len) const
111 {
112 return BigInt::encode(private_op(in, len));
113 }
114
115/*************************************************
116* RSA Signature Operation *
117*************************************************/
118SecureVector<byte> RSA_PrivateKey::sign(const byte in[], u32bit len) const
119 {
120 return BigInt::encode_1363(private_op(in, len), n.bytes());
121 }
122
123/*************************************************
124* Check Private RSA Parameters *
125*************************************************/
126bool RSA_PrivateKey::check_key(bool strong) const
127 {
128 if(!IF_Scheme_PrivateKey::check_key(strong))
129 return false;
130
131 if(!strong)
132 return true;
133
134 if((e * d) % lcm(p - 1, q - 1) != 1)
135 return false;
136
137 try {
138 KeyPair::check_key(get_pk_encryptor(*this, "EME1(SHA-1)"),
139 get_pk_decryptor(*this, "EME1(SHA-1)")
140 );
141
142 KeyPair::check_key(get_pk_signer(*this, "EMSA4(SHA-1)"),
143 get_pk_verifier(*this, "EMSA4(SHA-1)")
144 );
145 }
146 catch(Self_Test_Failure)
147 {
148 return false;
149 }
150
151 return true;
152 }
153
154}

Archive Download this file

Branches

Tags

Quick Links:     www.monotone.ca    -     Downloads    -     Documentation    -     Wiki    -     Code Forge    -     Build Status