1 | /*
|
---|
2 | * Copyright 2019-2021 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 | #define OSSL_FORCE_ERR_STATE
|
---|
11 |
|
---|
12 | #include <string.h>
|
---|
13 | #include <openssl/err.h>
|
---|
14 | #include "err_local.h"
|
---|
15 |
|
---|
16 | void ERR_new(void)
|
---|
17 | {
|
---|
18 | ERR_STATE *es;
|
---|
19 |
|
---|
20 | es = ossl_err_get_state_int();
|
---|
21 | if (es == NULL)
|
---|
22 | return;
|
---|
23 |
|
---|
24 | /* Allocate a slot */
|
---|
25 | err_get_slot(es);
|
---|
26 | err_clear(es, es->top, 0);
|
---|
27 | }
|
---|
28 |
|
---|
29 | void ERR_set_debug(const char *file, int line, const char *func)
|
---|
30 | {
|
---|
31 | ERR_STATE *es;
|
---|
32 |
|
---|
33 | es = ossl_err_get_state_int();
|
---|
34 | if (es == NULL)
|
---|
35 | return;
|
---|
36 |
|
---|
37 | err_set_debug(es, es->top, file, line, func);
|
---|
38 | }
|
---|
39 |
|
---|
40 | void ERR_set_error(int lib, int reason, const char *fmt, ...)
|
---|
41 | {
|
---|
42 | va_list args;
|
---|
43 |
|
---|
44 | va_start(args, fmt);
|
---|
45 | ERR_vset_error(lib, reason, fmt, args);
|
---|
46 | va_end(args);
|
---|
47 | }
|
---|
48 |
|
---|
49 | void ERR_vset_error(int lib, int reason, const char *fmt, va_list args)
|
---|
50 | {
|
---|
51 | ERR_STATE *es;
|
---|
52 | char *buf = NULL;
|
---|
53 | size_t buf_size = 0;
|
---|
54 | unsigned long flags = 0;
|
---|
55 | size_t i;
|
---|
56 |
|
---|
57 | es = ossl_err_get_state_int();
|
---|
58 | if (es == NULL)
|
---|
59 | return;
|
---|
60 | i = es->top;
|
---|
61 |
|
---|
62 | if (fmt != NULL) {
|
---|
63 | int printed_len = 0;
|
---|
64 | char *rbuf = NULL;
|
---|
65 |
|
---|
66 | buf = es->err_data[i];
|
---|
67 | buf_size = es->err_data_size[i];
|
---|
68 |
|
---|
69 | /*
|
---|
70 | * To protect the string we just grabbed from tampering by other
|
---|
71 | * functions we may call, or to protect them from freeing a pointer
|
---|
72 | * that may no longer be valid at that point, we clear away the
|
---|
73 | * data pointer and the flags. We will set them again at the end
|
---|
74 | * of this function.
|
---|
75 | */
|
---|
76 | es->err_data[i] = NULL;
|
---|
77 | es->err_data_flags[i] = 0;
|
---|
78 |
|
---|
79 | /*
|
---|
80 | * Try to maximize the space available. If that fails, we use what
|
---|
81 | * we have.
|
---|
82 | */
|
---|
83 | if (buf_size < ERR_MAX_DATA_SIZE
|
---|
84 | && (rbuf = OPENSSL_realloc(buf, ERR_MAX_DATA_SIZE)) != NULL) {
|
---|
85 | buf = rbuf;
|
---|
86 | buf_size = ERR_MAX_DATA_SIZE;
|
---|
87 | }
|
---|
88 |
|
---|
89 | if (buf != NULL) {
|
---|
90 | printed_len = BIO_vsnprintf(buf, buf_size, fmt, args);
|
---|
91 | }
|
---|
92 | if (printed_len < 0)
|
---|
93 | printed_len = 0;
|
---|
94 | if (buf != NULL)
|
---|
95 | buf[printed_len] = '\0';
|
---|
96 |
|
---|
97 | /*
|
---|
98 | * Try to reduce the size, but only if we maximized above. If that
|
---|
99 | * fails, we keep what we have.
|
---|
100 | * (According to documentation, realloc leaves the old buffer untouched
|
---|
101 | * if it fails)
|
---|
102 | */
|
---|
103 | if ((rbuf = OPENSSL_realloc(buf, printed_len + 1)) != NULL) {
|
---|
104 | buf = rbuf;
|
---|
105 | buf_size = printed_len + 1;
|
---|
106 | buf[printed_len] = '\0';
|
---|
107 | }
|
---|
108 |
|
---|
109 | if (buf != NULL)
|
---|
110 | flags = ERR_TXT_MALLOCED | ERR_TXT_STRING;
|
---|
111 | }
|
---|
112 |
|
---|
113 | err_clear_data(es, es->top, 0);
|
---|
114 | err_set_error(es, es->top, lib, reason);
|
---|
115 | if (fmt != NULL)
|
---|
116 | err_set_data(es, es->top, buf, buf_size, flags);
|
---|
117 | }
|
---|