Adding SSL Constructs header file. (First version)
[people/xl0/gpxe.git] / src / crypto / ssl_constructs.h
1 // Note: This file still needs some work.
2
3 // Typedefs
4 // (As defined by the SSL v3.0 RFC Draft)
5 // URL: http://wp.netscape.com/eng/ssl3/draft302.txt
6 typedef unsigned char uint8;
7 typedef uint8 uint16[2];
8 typedef uint8 uint24[3];
9 typedef uint8 uint32[4];
10 typedef uint8 uint64[8];
11
12 // Record layers
13 typedef struct _ProtocolVersion{
14   uint8 major, minor;
15 } ProtocolVersion;
16
17 ProtocolVersion version = { 3, 0 };
18
19 typedef enum _ContentType{
20   content_type_change_cipher_spec_type=20,
21   content_type_alert=21,
22   content_type_handshake=22,
23   content_type_application_data=23,
24   content_type_size=255 // to force size
25 } ContentType;
26
27 typedef struct _SSLPlaintext{
28   ContentType type;
29   ProtocolVersion version;
30   uint16 length; // can not exceed 2^14 bytes
31   uint8 fragment[16384]; // 2^14 = 16,384 bytes
32 } SSLPlaintext;
33
34 typedef struct _SSLCompressed{
35   ContentType type;
36   ProtocolVersion version;
37   uint16 length; // can not exceed 2^14 + 1024
38   uint8 fragment[17408]; // SSLCompressed.length
39 } SSLCompressed;
40
41 typedef struct _GenericStreamCipher{
42   uint8 content[17408]; // SSLCompressed.length
43   uint8 MAC[]; // CipherSpec.hash_size
44 } GenericStreamCipher;
45
46 typedef struct _SSLStreamCiphertext{
47   ContentType type;
48   ProtocolVersion version;
49   uint16 length; // can not exceed 2^14 + 2048 = 18,456
50   GenericStreamCipher fragment;
51 } SSLStreamCiphertext;
52
53 typedef struct _GenericBlockCipher{
54   uint8 content[17408]; // SSLConpressed.length
55   uint8 MAC[0]; // CipherSpec.hash_size
56   // padding is used to bring the plaintext to
57   // a multiple of the block cipher's block length.
58   uint8 padding[0]; // GenericBlockCipher.padding_length
59   uint8 padding_length;
60 } GenericBlockCipher;
61
62 typedef struct _SSLBlockCiphertext{
63   ContentType type;
64   ProtocolVersion version;
65   uint16 length; // can not exceed 2^14 + 2048 = 18,456
66   GenericBlockCipher fragment;
67 } SSLBlockCiphertext;
68
69 // Change cipher specs message
70 typedef struct _ChangeCipherSpec{
71   enum { type_change_cipher_spec=1, type_size=255 } type;
72 } ChangeCipherSpec;
73
74 // Alert messages
75 typedef enum _AlertLevel{
76   alert_level_warning=1,
77   alert_level_fatal=2,
78   alert_level_size=255 
79 } AlertLevel;
80
81 typedef enum _AlertDescription{
82   alert_description_close_notify=0,
83   alert_description_unexpected_message=10,
84   alert_description_bad_record_mac=20,
85   alert_description_decompression_failure=30,
86   alert_description_handshake_failure=40,
87   alert_description_no_certificate=41,
88   alert_description_bad_certificate=42,
89   alert_description_unsupported_certificate=43,
90   alert_description_certificate_revoked=44,
91   alert_description_certificate_expired=45,
92   alert_description_certificate_unknown=46,
93   alert_description_illegal_parameter=47,
94   alert_description_size=255
95 } AlertDescription;
96
97 typedef struct _Alert{
98   AlertLevel level;
99   AlertDescription description;
100 } Alert;
101
102 // Handshake protocol
103 // What is the best way to have a generic pointer to the body struct??
104 typedef enum _HandshakeType{
105   handshake_type_hello_request=0,
106   handshake_type_client_hello=1,
107   handshake_type_server_hello=2,
108   handshake_type_certificate=11,
109   handshake_type_server_key_exchange=12,
110   handshake_type_certificate_request=13,
111   handshake_type_server_done=14,
112   handshake_type_certificate_verify=15,
113   handshake_type_client_key_exchange=16,
114   handshake_type_finished=20,
115   handshake_type_size=255
116 } HandshakeType;
117
118 typedef struct _Handshake{
119   HandshakeType msg_type;
120   uint24 length;
121 } Handshake; // generic Handshake, need to recast to get body
122
123 // Hello messages
124 typedef struct _HelloRequest{} HelloRequest;
125
126 typedef struct _HelloRequestHandshake{
127   HandshakeType msg_type;
128   uint24 length;
129   HelloRequest body;
130 } HelloRequestHandshake;
131
132 typedef struct _Random{
133   uint32 gmt_unix_time;
134   uint8 random_bytes[28];
135 } Random;
136
137 typedef uint8 SessionID[32]; // <0..32>
138 typedef uint8 CipherSuite[2];
139
140 typedef enum _CompressionMethod{ compression_method_null=0, compression_method_size=255 } CompressionMethod;
141
142 typedef struct _ClientHello{
143   ProtocolVersion client_version;
144   Random random;
145   SessionID session_id;
146   CipherSuite cipher_suites[32768]; // <2..2^16-1> = 65,536 bytes and CipherSuite is 2 bytes
147   CompressionMethod compression_methods[256]; // <0..2^8-1> = 256 bytes and CompressionMethod is 1 byte
148 } ClientHello;
149
150 typedef struct _ClientHelloHandshake{
151   HandshakeType msg_type;
152   uint24 length;
153   ClientHello body;
154 } ClientHelloHandshake;
155
156 typedef struct _ServerHello{
157   ProtocolVersion server_version;
158   Random random;
159   SessionID session_id;
160   CipherSuite cipher_suite;
161   CompressionMethod compression_method;
162 } ServerHello;
163
164 typedef struct _ServerHelloHandshake{
165   HandshakeType msg_type;
166   uint24 length;
167   ServerHello body;
168 } ServerHelloHandshake;
169
170 // Server authentication and key exchange messages
171 typedef uint8 ASN1Cert[16777216]; // <1..2^24-1> = 16,777,216 bytes
172
173 typedef struct _Certificate{
174   ASN1Cert certificate_list[1]; // <1..2^24-1> / ANS1Cert = 1
175   // for some reason the size of certificate_list and ASN1Cert is the same, so only one certificate in the list
176 } Certificate;
177
178 typedef enum _KeyExchangeAlgorithm{
179   key_exchange_algorithm_rsa,
180   key_exchange_algorithm_diffie_hellman,
181   key_exchange_algorithm_fortezza_kea 
182 } KeyExchangeAlgorithm;
183
184 typedef struct _AnonSignature{
185   struct {};
186 } AnonSignature;
187
188 typedef struct _RSASignature{
189   uint8 md5_hash[16];
190   uint8 sha_hash[20];
191 } RSASignature;
192
193 typedef struct _DSASignature{
194   uint8 sha_hash[20];
195 } DSASignature;
196
197 // use union??,  make a mess to reference, but easy to make Signature type.
198 typedef union _Signature{ AnonSignature anon; RSASignature rsa; DSASignature dsa; } Signature;
199
200 typedef struct _ServerRSAParams{
201   uint8 RSA_modulus[65536]; // <1..2^16-1> = 65,536
202   uint8 RSA_exponent[65536]; // <1..2^16-1> = 65,536
203 } ServerRSAParams;
204
205 typedef struct _ServerDHParams{
206   uint8 DH_p[65536]; // <1..2^16-1>
207   uint8 DH_g[65536]; // <1..2^16-1>
208   uint8 DH_Ys[65536]; // <1..2^16-1>
209 } ServerDHParams;
210
211 typedef struct _ServerDHKeyExchange{
212   ServerDHParams params;
213   Signature signed_params;
214 } ServerDHKeyExchange;
215
216 typedef struct _ServerRSAKeyExchange{
217   ServerRSAParams params;
218   Signature signed_params;
219 } ServerRSAKeyExchange;
220
221 typedef enum _SignatureAlgorithm{
222   signature_algorithm_anonymous,
223   signature_algorithm_rsa,
224   signature_algorithm_dsa 
225 } SignatureAlgorithm;
226
227 typedef enum _CertificateType{
228   certificate_type_RSA_sign=1,
229   certificate_type_DSS_sign=2,
230   certificate_type_RSA_fixed_DH=3,
231   certificate_type_DSS_fixed_DH=4,
232   certificate_type_RSA_ephemeral_DH=5,
233   certificate_type_DSS_ephemeral_DH=6,
234   certificate_type_FORTEZZA_MISSI=20,
235   certificate_type_size=255
236 } CertificateType;
237
238 typedef uint8 DistinguishedName[65536]; // <1..2^16-1> = 65,536
239
240 typedef struct _CertificateRequest{
241   CertificateType certificate_types[256]; // <1..2^8-1>
242   DistinguishedName certificate_authorities[1]; // <3...2^16-1> / DistinguishedName
243   // this is another one that is odd with a list size of 1
244 } CertificateRequest;
245
246 typedef struct _ServerHelloDone{} ServerHelloDone;
247
248 // Client authentication and key exchange messages
249 typedef struct _PreMasterSecret{
250   ProtocolVersion client_version;
251   uint8 random[46];
252 } PreMasterSecret;
253
254 typedef struct _EncryptedPreMasterSecret{
255   PreMasterSecret pre_master_secret;
256 } EncryptedPreMasterSecret;
257
258 typedef struct _RSAClientKeyExchange{
259   EncryptedPreMasterSecret exchange_keys;
260 } RSAClientKeyExchange;
261
262 typedef enum _PublicValueEncoding{ public_value_encoding_implicit, public_value_encoding_explicit } PublicValueEncoding;
263
264 typedef struct _ClientDiffieHellmanPublic{
265   // This is a select on PublicValueEncoding,  and I chose the larger size
266   uint8 dh_public[65536]; // DH_Yc<1..2^16-1>, the dh public value
267 } ClientDiffieHellmanPublic;
268
269 typedef struct _DHClientKeyExhange{
270   ClientDiffieHellmanPublic exchange_keys;
271 } DHClientKeyExchange;
272
273 typedef struct _CertificateVerify{
274   Signature signature;
275 } CertificateVerify;
276
277 // Handshake finalization message
278 typedef struct _Finished{
279   uint8 md5_hash[16];
280   uint8 sha_hash[20];
281 } Finished;
282
283 // The CipherSuite
284 CipherSuite SSL_NULL_WITH_NULL_NULL                     = { 0x00, 0x00 };
285 CipherSuite SSL_DH_DSS_EXPORT_WITH_DES40_CBC_SHA        = { 0x00, 0x0B };
286 CipherSuite SSL_DH_DSS_WITH_DES_CBC_SHA                 = { 0x00, 0x0C };
287 CipherSuite SSL_DH_anon_EXPORT_WITH_RC4_40_MD5          = { 0x00, 0x17 };
288 CipherSuite SSL_DH_anon_WITH_RC4_128_MD5                = { 0x00, 0x18 };
289
290 // The CipherSpec
291 typedef enum _CipherType{ cipher_type_stream, cipher_type_block } CipherType;
292 typedef enum _IsExportable{ is_exportable_true, is_exportable_false } IsExportable;
293 typedef enum _BulkCipherAlgorithm{
294   bulk_cipher_algorithm_null,
295   bulk_cipher_algorithm_rc4,
296   bulk_cipher_algorithm_rc2,
297   bulk_cipher_algorithm_des,
298   bulk_cipher_algorithm_3des,
299   bulk_cipher_algorithm_des40,
300   bulk_cipher_algorithm_fortezza 
301 } BulkCipherAlgorithm;
302 typedef enum _MACAlgorithm{ mac_algorithm_null, mac_algorithm_md5, mac_algorithm_sha } MACAlgorithm;
303
304 typedef struct _CipherSpec{
305   BulkCipherAlgorithm bulk_cipher_algorithm;
306   MACAlgorithm mac_algorithm;
307   CipherType cipher_type;
308   IsExportable is_exportable;
309   uint8 hash_size;
310   uint8 key_material;
311   uint8 IV_size;
312 } CipherSpec;
313
314