]>
Commit | Line | Data |
---|---|---|
c1074ce0 MC |
1 | /* |
2 | * Copyright 2017 The OpenSSL Project Authors. All Rights Reserved. | |
3 | * | |
4 | * Licensed under the OpenSSL license (the "License"). You may not use | |
5 | * this file except in compliance with the License. You can obtain a copy | |
6 | * in the file LICENSE in the source distribution or at | |
7 | * https://www.openssl.org/source/license.html | |
8 | */ | |
9 | ||
10 | #include <string.h> | |
11 | ||
12 | #include "ssltestlib.h" | |
13 | #include "testutil.h" | |
14 | #include "test_main_custom.h" | |
15 | ||
16 | static char *cert = NULL; | |
17 | static char *privkey = NULL; | |
18 | ||
19 | #define TEST_PLAINTEXT_OVERFLOW_OK 0 | |
20 | #define TEST_PLAINTEXT_OVERFLOW_NOT_OK 1 | |
21 | #define TEST_ENCRYPTED_OVERFLOW_TLS1_3_OK 2 | |
22 | #define TEST_ENCRYPTED_OVERFLOW_TLS1_3_NOT_OK 3 | |
23 | #define TEST_ENCRYPTED_OVERFLOW_TLS1_2_OK 4 | |
24 | #define TEST_ENCRYPTED_OVERFLOW_TLS1_2_NOT_OK 5 | |
25 | ||
26 | #define TOTAL_RECORD_OVERFLOW_TESTS 6 | |
27 | ||
28 | static int write_record(BIO *b, size_t len, int rectype, int recversion) | |
29 | { | |
30 | unsigned char header[SSL3_RT_HEADER_LENGTH]; | |
31 | size_t written; | |
32 | unsigned char buf[256]; | |
33 | ||
34 | memset(buf, 0, sizeof(buf)); | |
35 | ||
36 | header[0] = rectype; | |
37 | header[1] = (recversion >> 8) & 0xff; | |
38 | header[2] = recversion & 0xff; | |
39 | header[3] = (len >> 8) & 0xff; | |
40 | header[4] = len & 0xff; | |
41 | ||
42 | if (!BIO_write_ex(b, header, SSL3_RT_HEADER_LENGTH, &written) | |
43 | || written != SSL3_RT_HEADER_LENGTH) | |
44 | return 0; | |
45 | ||
46 | while (len > 0) { | |
47 | size_t outlen; | |
48 | ||
49 | if (len > sizeof(buf)) | |
50 | outlen = sizeof(buf); | |
51 | else | |
52 | outlen = len; | |
53 | ||
54 | if (!BIO_write_ex(b, buf, outlen, &written) | |
55 | || written != outlen) | |
56 | return 0; | |
57 | ||
58 | len -= outlen; | |
59 | } | |
60 | ||
61 | return 1; | |
62 | } | |
63 | ||
64 | static int fail_due_to_record_overflow(int enc) | |
65 | { | |
66 | long err = ERR_peek_error(); | |
67 | int reason; | |
68 | ||
69 | if (enc) | |
70 | reason = SSL_R_ENCRYPTED_LENGTH_TOO_LONG; | |
71 | else | |
72 | reason = SSL_R_DATA_LENGTH_TOO_LONG; | |
73 | ||
74 | if (ERR_GET_LIB(err) == ERR_LIB_SSL | |
75 | && ERR_GET_REASON(err) == reason) | |
76 | return 1; | |
77 | ||
78 | return 0; | |
79 | } | |
80 | ||
4f7b76bf | 81 | static int test_record_overflow(int idx) |
c1074ce0 MC |
82 | { |
83 | SSL_CTX *cctx = NULL, *sctx = NULL; | |
84 | SSL *clientssl = NULL, *serverssl = NULL; | |
85 | int testresult = 0; | |
86 | size_t len = 0; | |
87 | size_t written; | |
88 | int overf_expected; | |
89 | unsigned char buf; | |
90 | BIO *serverbio; | |
91 | int recversion; | |
92 | ||
93 | #ifdef OPENSSL_NO_TLS1_2 | |
94 | if (idx == TEST_ENCRYPTED_OVERFLOW_TLS1_2_OK | |
95 | || idx == TEST_ENCRYPTED_OVERFLOW_TLS1_2_NOT_OK) | |
96 | return 1; | |
97 | #endif | |
98 | #ifdef OPENSSL_NO_TLS1_3 | |
99 | if (idx == TEST_ENCRYPTED_OVERFLOW_TLS1_3_OK | |
100 | || idx == TEST_ENCRYPTED_OVERFLOW_TLS1_3_NOT_OK) | |
101 | return 1; | |
102 | #endif | |
103 | ||
104 | ERR_clear_error(); | |
105 | ||
106 | if (!create_ssl_ctx_pair(TLS_server_method(), TLS_client_method(), &sctx, | |
107 | &cctx, cert, privkey)) { | |
108 | printf("Unable to create SSL_CTX pair\n"); | |
109 | goto end; | |
110 | } | |
111 | ||
112 | if (idx == TEST_ENCRYPTED_OVERFLOW_TLS1_2_OK | |
113 | || idx == TEST_ENCRYPTED_OVERFLOW_TLS1_2_NOT_OK) { | |
4f7b76bf MC |
114 | len = SSL3_RT_MAX_ENCRYPTED_LENGTH; |
115 | #ifndef OPENSSL_NO_COMP | |
116 | len -= SSL3_RT_MAX_COMPRESSED_OVERHEAD; | |
117 | #endif | |
c1074ce0 MC |
118 | SSL_CTX_set_max_proto_version(sctx, TLS1_2_VERSION); |
119 | } else if (idx == TEST_ENCRYPTED_OVERFLOW_TLS1_3_OK | |
120 | || idx == TEST_ENCRYPTED_OVERFLOW_TLS1_3_NOT_OK) { | |
121 | len = SSL3_RT_MAX_TLS13_ENCRYPTED_LENGTH; | |
122 | } | |
123 | ||
124 | if (!create_ssl_objects(sctx, cctx, &serverssl, &clientssl, NULL, NULL)) { | |
125 | printf("Unable to create SSL objects\n"); | |
126 | goto end; | |
127 | } | |
128 | ||
129 | serverbio = SSL_get_rbio(serverssl); | |
130 | ||
131 | if (idx == TEST_PLAINTEXT_OVERFLOW_OK | |
132 | || idx == TEST_PLAINTEXT_OVERFLOW_NOT_OK) { | |
133 | len = SSL3_RT_MAX_PLAIN_LENGTH; | |
134 | ||
135 | if (idx == TEST_PLAINTEXT_OVERFLOW_NOT_OK) | |
136 | len++; | |
137 | ||
138 | if (!write_record(serverbio, len, SSL3_RT_HANDSHAKE, TLS1_VERSION)) { | |
139 | printf("Unable to write plaintext record\n"); | |
140 | goto end; | |
141 | } | |
142 | ||
143 | if (SSL_accept(serverssl) > 0) { | |
144 | printf("Unexpected success reading plaintext record\n"); | |
145 | goto end; | |
146 | } | |
147 | ||
148 | overf_expected = (idx == TEST_PLAINTEXT_OVERFLOW_OK) ? 0 : 1; | |
149 | if (fail_due_to_record_overflow(0) != overf_expected) { | |
150 | printf("Unexpected error value received\n"); | |
151 | goto end; | |
152 | } | |
153 | ||
154 | goto success; | |
155 | } | |
156 | ||
157 | if (!create_ssl_connection(serverssl, clientssl, SSL_ERROR_NONE)) { | |
158 | printf("Unable to create SSL connection\n"); | |
159 | goto end; | |
160 | } | |
161 | ||
162 | if (idx == TEST_ENCRYPTED_OVERFLOW_TLS1_2_NOT_OK | |
163 | || idx == TEST_ENCRYPTED_OVERFLOW_TLS1_3_NOT_OK) { | |
164 | overf_expected = 1; | |
165 | len++; | |
166 | } else { | |
167 | overf_expected = 0; | |
168 | } | |
169 | ||
170 | if (idx == TEST_ENCRYPTED_OVERFLOW_TLS1_3_OK | |
171 | || idx == TEST_ENCRYPTED_OVERFLOW_TLS1_3_NOT_OK) | |
172 | recversion = TLS1_VERSION; | |
173 | else | |
174 | recversion = TLS1_2_VERSION; | |
175 | ||
176 | if (!write_record(serverbio, len, SSL3_RT_APPLICATION_DATA, recversion)) { | |
177 | printf("Unable to write encryprted record\n"); | |
178 | goto end; | |
179 | } | |
180 | ||
181 | if (SSL_read_ex(serverssl, &buf, sizeof(buf), &written)) { | |
182 | printf("Unexpected success reading encrypted record\n"); | |
183 | goto end; | |
184 | } | |
185 | ||
186 | if (fail_due_to_record_overflow(1) != overf_expected) { | |
187 | printf("Unexpected error value received\n"); | |
188 | goto end; | |
189 | } | |
190 | ||
191 | success: | |
192 | testresult = 1; | |
193 | ||
194 | end: | |
195 | if(!testresult) | |
196 | ERR_print_errors_fp(stdout); | |
197 | SSL_free(serverssl); | |
198 | SSL_free(clientssl); | |
199 | SSL_CTX_free(sctx); | |
200 | SSL_CTX_free(cctx); | |
201 | ||
202 | return testresult; | |
203 | } | |
204 | ||
205 | int test_main(int argc, char *argv[]) | |
206 | { | |
207 | int testresult = 1; | |
208 | ||
209 | if (argc != 3) { | |
210 | printf("Invalid argument count\n"); | |
211 | return 1; | |
212 | } | |
213 | ||
214 | cert = argv[1]; | |
215 | privkey = argv[2]; | |
216 | ||
4f7b76bf | 217 | ADD_ALL_TESTS(test_record_overflow, TOTAL_RECORD_OVERFLOW_TESTS); |
c1074ce0 MC |
218 | |
219 | testresult = run_tests(argv[0]); | |
220 | ||
221 | bio_s_mempacket_test_free(); | |
222 | ||
223 | return testresult; | |
224 | } |