VirtualBox

source: vbox/trunk/src/libs/openssl-3.0.1/crypto/mem.c@ 94096

最後變更 在這個檔案從94096是 94082,由 vboxsync 提交於 3 年 前

libs/openssl-3.0.1: started applying and adjusting our OpenSSL changes to 3.0.1. bugref:10128

檔案大小: 7.8 KB
 
1/*
2 * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the Apache License 2.0 (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 "e_os.h"
11#include "internal/cryptlib.h"
12#include <stdio.h>
13#include <stdlib.h>
14#include <limits.h>
15#include <openssl/crypto.h>
16
17/*
18 * the following pointers may be changed as long as 'allow_customize' is set
19 */
20static int allow_customize = 1;
21static CRYPTO_malloc_fn malloc_impl = CRYPTO_malloc;
22static CRYPTO_realloc_fn realloc_impl = CRYPTO_realloc;
23static CRYPTO_free_fn free_impl = CRYPTO_free;
24
25#if !defined(OPENSSL_NO_CRYPTO_MDEBUG) && !defined(FIPS_MODULE)
26# include "internal/tsan_assist.h"
27
28static TSAN_QUALIFIER int malloc_count;
29static TSAN_QUALIFIER int realloc_count;
30static TSAN_QUALIFIER int free_count;
31
32# define INCREMENT(x) tsan_counter(&(x))
33
34static char *md_failstring;
35static long md_count;
36static int md_fail_percent = 0;
37static int md_tracefd = -1;
38
39static void parseit(void);
40static int shouldfail(void);
41
42# define FAILTEST() if (shouldfail()) return NULL
43
44#else
45
46# define INCREMENT(x) /* empty */
47# define FAILTEST() /* empty */
48#endif
49
50int CRYPTO_set_mem_functions(CRYPTO_malloc_fn malloc_fn,
51 CRYPTO_realloc_fn realloc_fn,
52 CRYPTO_free_fn free_fn)
53{
54 if (!allow_customize)
55 return 0;
56 if (malloc_fn != NULL)
57 malloc_impl = malloc_fn;
58 if (realloc_fn != NULL)
59 realloc_impl = realloc_fn;
60 if (free_fn != NULL)
61 free_impl = free_fn;
62 return 1;
63}
64
65void CRYPTO_get_mem_functions(CRYPTO_malloc_fn *malloc_fn,
66 CRYPTO_realloc_fn *realloc_fn,
67 CRYPTO_free_fn *free_fn)
68{
69 if (malloc_fn != NULL)
70 *malloc_fn = malloc_impl;
71 if (realloc_fn != NULL)
72 *realloc_fn = realloc_impl;
73 if (free_fn != NULL)
74 *free_fn = free_impl;
75}
76
77#if !defined(OPENSSL_NO_CRYPTO_MDEBUG) && !defined(FIPS_MODULE)
78void CRYPTO_get_alloc_counts(int *mcount, int *rcount, int *fcount)
79{
80 if (mcount != NULL)
81 *mcount = tsan_load(&malloc_count);
82 if (rcount != NULL)
83 *rcount = tsan_load(&realloc_count);
84 if (fcount != NULL)
85 *fcount = tsan_load(&free_count);
86}
87
88/*
89 * Parse a "malloc failure spec" string. This likes like a set of fields
90 * separated by semicolons. Each field has a count and an optional failure
91 * percentage. For example:
92 * 100@0;100@25;0@0
93 * or 100;100@25;0
94 * This means 100 mallocs succeed, then next 100 fail 25% of the time, and
95 * all remaining (count is zero) succeed.
96 */
97static void parseit(void)
98{
99 char *semi = strchr(md_failstring, ';');
100 char *atsign;
101
102 if (semi != NULL)
103 *semi++ = '\0';
104
105 /* Get the count (atol will stop at the @ if there), and percentage */
106 md_count = atol(md_failstring);
107 atsign = strchr(md_failstring, '@');
108 md_fail_percent = atsign == NULL ? 0 : atoi(atsign + 1);
109
110 if (semi != NULL)
111 md_failstring = semi;
112}
113
114/*
115 * Windows doesn't have random(), but it has rand()
116 * Some rand() implementations aren't good, but we're not
117 * dealing with secure randomness here.
118 */
119# ifdef _WIN32
120# define random() rand()
121# endif
122/*
123 * See if the current malloc should fail.
124 */
125static int shouldfail(void)
126{
127 int roll = (int)(random() % 100);
128 int shoulditfail = roll < md_fail_percent;
129# ifndef _WIN32
130/* suppressed on Windows as POSIX-like file descriptors are non-inheritable */
131 int len;
132 char buff[80];
133
134 if (md_tracefd > 0) {
135 BIO_snprintf(buff, sizeof(buff),
136 "%c C%ld %%%d R%d\n",
137 shoulditfail ? '-' : '+', md_count, md_fail_percent, roll);
138 len = strlen(buff);
139 if (write(md_tracefd, buff, len) != len)
140 perror("shouldfail write failed");
141 }
142# endif
143
144 if (md_count) {
145 /* If we used up this one, go to the next. */
146 if (--md_count == 0)
147 parseit();
148 }
149
150 return shoulditfail;
151}
152
153void ossl_malloc_setup_failures(void)
154{
155 const char *cp = getenv("OPENSSL_MALLOC_FAILURES");
156
157 if (cp != NULL && (md_failstring = strdup(cp)) != NULL)
158 parseit();
159 if ((cp = getenv("OPENSSL_MALLOC_FD")) != NULL)
160 md_tracefd = atoi(cp);
161}
162#endif
163
164void *CRYPTO_malloc(size_t num, const char *file, int line)
165{
166 INCREMENT(malloc_count);
167 if (malloc_impl != CRYPTO_malloc)
168 return malloc_impl(num, file, line);
169
170 if (num == 0)
171 return NULL;
172
173 FAILTEST();
174 if (allow_customize) {
175 /*
176 * Disallow customization after the first allocation. We only set this
177 * if necessary to avoid a store to the same cache line on every
178 * allocation.
179 */
180 allow_customize = 0;
181 }
182
183 return malloc(num);
184}
185
186void *CRYPTO_zalloc(size_t num, const char *file, int line)
187{
188 void *ret;
189
190 ret = CRYPTO_malloc(num, file, line);
191 FAILTEST();
192 if (ret != NULL)
193 memset(ret, 0, num);
194
195 return ret;
196}
197
198void *CRYPTO_realloc(void *str, size_t num, const char *file, int line)
199{
200 INCREMENT(realloc_count);
201 if (realloc_impl != CRYPTO_realloc)
202 return realloc_impl(str, num, file, line);
203
204 FAILTEST();
205 if (str == NULL)
206 return CRYPTO_malloc(num, file, line);
207
208 if (num == 0) {
209 CRYPTO_free(str, file, line);
210 return NULL;
211 }
212
213 return realloc(str, num);
214}
215
216void *CRYPTO_clear_realloc(void *str, size_t old_len, size_t num,
217 const char *file, int line)
218{
219 void *ret = NULL;
220
221 if (str == NULL)
222 return CRYPTO_malloc(num, file, line);
223
224 if (num == 0) {
225 CRYPTO_clear_free(str, old_len, file, line);
226 return NULL;
227 }
228
229 /* Can't shrink the buffer since memcpy below copies |old_len| bytes. */
230 if (num < old_len) {
231 OPENSSL_cleanse((char*)str + num, old_len - num);
232 return str;
233 }
234
235 ret = CRYPTO_malloc(num, file, line);
236 if (ret != NULL) {
237 memcpy(ret, str, old_len);
238 CRYPTO_clear_free(str, old_len, file, line);
239 }
240 return ret;
241}
242
243void CRYPTO_free(void *str, const char *file, int line)
244{
245 INCREMENT(free_count);
246 if (free_impl != CRYPTO_free) {
247 free_impl(str, file, line);
248 return;
249 }
250
251 free(str);
252}
253
254void CRYPTO_clear_free(void *str, size_t num, const char *file, int line)
255{
256 if (str == NULL)
257 return;
258 if (num)
259 OPENSSL_cleanse(str, num);
260 CRYPTO_free(str, file, line);
261}
262
263#if !defined(OPENSSL_NO_CRYPTO_MDEBUG)
264
265# ifndef OPENSSL_NO_DEPRECATED_3_0
266int CRYPTO_mem_ctrl(int mode)
267{
268 (void)mode;
269 return -1;
270}
271
272int CRYPTO_set_mem_debug(int flag)
273{
274 (void)flag;
275 return -1;
276}
277
278int CRYPTO_mem_debug_push(const char *info, const char *file, int line)
279{
280 (void)info; (void)file; (void)line;
281 return -1;
282}
283
284int CRYPTO_mem_debug_pop(void)
285{
286 return -1;
287}
288
289void CRYPTO_mem_debug_malloc(void *addr, size_t num, int flag,
290 const char *file, int line)
291{
292 (void)addr; (void)num; (void)flag; (void)file; (void)line;
293}
294
295void CRYPTO_mem_debug_realloc(void *addr1, void *addr2, size_t num, int flag,
296 const char *file, int line)
297{
298 (void)addr1; (void)addr2; (void)num; (void)flag; (void)file; (void)line;
299}
300
301void CRYPTO_mem_debug_free(void *addr, int flag,
302 const char *file, int line)
303{
304 (void)addr; (void)flag; (void)file; (void)line;
305}
306
307int CRYPTO_mem_leaks(BIO *b)
308{
309 (void)b;
310 return -1;
311}
312
313# ifndef OPENSSL_NO_STDIO
314int CRYPTO_mem_leaks_fp(FILE *fp)
315{
316 (void)fp;
317 return -1;
318}
319# endif
320
321int CRYPTO_mem_leaks_cb(int (*cb)(const char *str, size_t len, void *u),
322 void *u)
323{
324 (void)cb; (void)u;
325 return -1;
326}
327
328# endif
329
330#endif
注意: 瀏覽 TracBrowser 來幫助您使用儲存庫瀏覽器

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette