1
2
3
4 """Abstract class for RSA."""
5
6 from .cryptomath import *
7
8
10 """This is an abstract base class for RSA keys.
11
12 Particular implementations of RSA keys, such as
13 L{openssl_rsakey.OpenSSL_RSAKey},
14 L{python_rsakey.Python_RSAKey}, and
15 L{pycrypto_rsakey.PyCrypto_RSAKey},
16 inherit from this.
17
18 To create or parse an RSA key, don't use one of these classes
19 directly. Instead, use the factory functions in
20 L{tlslite.utils.keyfactory}.
21 """
22
24 """Create a new RSA key.
25
26 If n and e are passed in, the new key will be initialized.
27
28 @type n: int
29 @param n: RSA modulus.
30
31 @type e: int
32 @param e: RSA public exponent.
33 """
34 raise NotImplementedError()
35
37 """Return the length of this key in bits.
38
39 @rtype: int
40 """
41 return numBits(self.n)
42
44 """Return whether or not this key has a private component.
45
46 @rtype: bool
47 """
48 raise NotImplementedError()
49
51 """Hash and sign the passed-in bytes.
52
53 This requires the key to have a private component. It performs
54 a PKCS1-SHA1 signature on the passed-in data.
55
56 @type bytes: str or L{bytearray} of unsigned bytes
57 @param bytes: The value which will be hashed and signed.
58
59 @rtype: L{bytearray} of unsigned bytes.
60 @return: A PKCS1-SHA1 signature on the passed-in data.
61 """
62 if not isinstance(bytes, type("")):
63 bytes = bytesToString(bytes)
64 hashBytes = stringToBytes(sha1(bytes).digest())
65 prefixedHashBytes = self._addPKCS1SHA1Prefix(hashBytes)
66 sigBytes = self.sign(prefixedHashBytes)
67 return sigBytes
68
70 """Hash and verify the passed-in bytes with the signature.
71
72 This verifies a PKCS1-SHA1 signature on the passed-in data.
73
74 @type sigBytes: L{bytearray} of unsigned bytes
75 @param sigBytes: A PKCS1-SHA1 signature.
76
77 @type bytes: str or L{bytearray} of unsigned bytes
78 @param bytes: The value which will be hashed and verified.
79
80 @rtype: bool
81 @return: Whether the signature matches the passed-in data.
82 """
83 if not isinstance(bytes, type("")):
84 bytes = bytesToString(bytes)
85 hashBytes = stringToBytes(sha1(bytes).digest())
86 prefixedHashBytes = self._addPKCS1SHA1Prefix(hashBytes)
87 return self.verify(sigBytes, prefixedHashBytes)
88
89 - def sign(self, bytes):
90 """Sign the passed-in bytes.
91
92 This requires the key to have a private component. It performs
93 a PKCS1 signature on the passed-in data.
94
95 @type bytes: L{bytearray} of unsigned bytes
96 @param bytes: The value which will be signed.
97
98 @rtype: L{bytearray} of unsigned bytes.
99 @return: A PKCS1 signature on the passed-in data.
100 """
101 if not self.hasPrivateKey():
102 raise AssertionError()
103 paddedBytes = self._addPKCS1Padding(bytes, 1)
104 m = bytesToNumber(paddedBytes)
105 if m >= self.n:
106 raise ValueError()
107 c = self._rawPrivateKeyOp(m)
108 sigBytes = numberToBytes(c, numBytes(self.n))
109 return sigBytes
110
111 - def verify(self, sigBytes, bytes):
112 """Verify the passed-in bytes with the signature.
113
114 This verifies a PKCS1 signature on the passed-in data.
115
116 @type sigBytes: L{bytearray} of unsigned bytes
117 @param sigBytes: A PKCS1 signature.
118
119 @type bytes: L{bytearray} of unsigned bytes
120 @param bytes: The value which will be verified.
121
122 @rtype: bool
123 @return: Whether the signature matches the passed-in data.
124 """
125 if len(sigBytes) != numBytes(self.n):
126 return False
127 paddedBytes = self._addPKCS1Padding(bytes, 1)
128 c = bytesToNumber(sigBytes)
129 if c >= self.n:
130 return False
131 m = self._rawPublicKeyOp(c)
132 checkBytes = numberToBytes(m, numBytes(self.n))
133 return checkBytes == paddedBytes
134
136 """Encrypt the passed-in bytes.
137
138 This performs PKCS1 encryption of the passed-in data.
139
140 @type bytes: L{bytearray} of unsigned bytes
141 @param bytes: The value which will be encrypted.
142
143 @rtype: L{bytearray} of unsigned bytes.
144 @return: A PKCS1 encryption of the passed-in data.
145 """
146 paddedBytes = self._addPKCS1Padding(bytes, 2)
147 m = bytesToNumber(paddedBytes)
148 if m >= self.n:
149 raise ValueError()
150 c = self._rawPublicKeyOp(m)
151 encBytes = numberToBytes(c, numBytes(self.n))
152 return encBytes
153
155 """Decrypt the passed-in bytes.
156
157 This requires the key to have a private component. It performs
158 PKCS1 decryption of the passed-in data.
159
160 @type encBytes: L{bytearray} of unsigned bytes
161 @param encBytes: The value which will be decrypted.
162
163 @rtype: L{bytearray} of unsigned bytes or None.
164 @return: A PKCS1 decryption of the passed-in data or None if
165 the data is not properly formatted.
166 """
167 if not self.hasPrivateKey():
168 raise AssertionError()
169 if len(encBytes) != numBytes(self.n):
170 return None
171 c = bytesToNumber(encBytes)
172 if c >= self.n:
173 return None
174 m = self._rawPrivateKeyOp(c)
175 decBytes = numberToBytes(m, numBytes(self.n))
176 if decBytes[0] != 0 or decBytes[1] != 2:
177 return None
178 for x in range(1, len(decBytes)-1):
179 if decBytes[x]== 0:
180 break
181 else:
182 return None
183 return decBytes[x+1:]
184
186 raise NotImplementedError()
187
189 raise NotImplementedError()
190
192 """Return True if the write() method accepts a password for use
193 in encrypting the private key.
194
195 @rtype: bool
196 """
197 raise NotImplementedError()
198
199 - def write(self, password=None):
200 """Return a string containing the key.
201
202 @rtype: str
203 @return: A string describing the key, in whichever format (PEM)
204 is native to the implementation.
205 """
206 raise NotImplementedError()
207
209 """Generate a new key with the specified bit length.
210
211 @rtype: L{tlslite.utils.RSAKey.RSAKey}
212 """
213 raise NotImplementedError()
214 generate = staticmethod(generate)
215
216
217
218
219
220
222
223
224
225
226
227
228
229
230
231 if not withNULL:
232 prefixBytes = createByteArraySequence(\
233 [0x30,0x1f,0x30,0x07,0x06,0x05,0x2b,0x0e,0x03,0x02,0x1a,0x04,0x14])
234 else:
235 prefixBytes = createByteArraySequence(\
236 [0x30,0x21,0x30,0x09,0x06,0x05,0x2b,0x0e,0x03,0x02,0x1a,0x05,0x00,0x04,0x14])
237 prefixedBytes = prefixBytes + bytes
238 return prefixedBytes
239
241 padLength = (numBytes(self.n) - (len(bytes)+3))
242 if blockType == 1:
243 pad = [0xFF] * padLength
244 elif blockType == 2:
245 pad = createByteArraySequence([])
246 while len(pad) < padLength:
247 padBytes = getRandomBytes(padLength * 2)
248 pad = [b for b in padBytes if b != 0]
249 pad = pad[:padLength]
250 else:
251 raise AssertionError()
252
253 padding = createByteArraySequence([0,blockType] + pad + [0])
254 paddedBytes = padding + bytes
255 return paddedBytes
256