Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/freebsd-src
Path: blob/main/crypto/openssl/ms/uplink.c
105420 views
1
/*
2
* Copyright 2004-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
#if (defined(_WIN64) || defined(_WIN32_WCE)) && !defined(UNICODE)
11
#define UNICODE
12
#endif
13
#if defined(UNICODE) && !defined(_UNICODE)
14
#define _UNICODE
15
#endif
16
#if defined(_UNICODE) && !defined(UNICODE)
17
#define UNICODE
18
#endif
19
20
#include <windows.h>
21
#include <tchar.h>
22
#include <stdio.h>
23
#include "uplink.h"
24
void OPENSSL_showfatal(const char *, ...);
25
26
static TCHAR msg[128];
27
28
static void unimplemented(void)
29
{
30
OPENSSL_showfatal(sizeof(TCHAR) == sizeof(char) ? "%s\n" : "%S\n", msg);
31
TerminateProcess(GetCurrentProcess(), 1);
32
}
33
34
void OPENSSL_Uplink(volatile void **table, int index)
35
{
36
static HMODULE volatile apphandle = NULL;
37
static void **volatile applinktable = NULL;
38
int len;
39
void (*func)(void) = unimplemented;
40
HANDLE h;
41
void **p;
42
43
/*
44
* Note that the below code is not MT-safe in respect to msg buffer, but
45
* what's the worst thing that can happen? Error message might be
46
* misleading or corrupted. As error condition is fatal and should never
47
* be risen, I accept the risk...
48
*/
49
/*
50
* One can argue that I should have used InterlockedExchangePointer or
51
* something to update static variables and table[]. Well, store
52
* instructions are as atomic as they can get and assigned values are
53
* effectively constant... So that volatile qualifier should be
54
* sufficient [it prohibits compiler to reorder memory access
55
* instructions].
56
*/
57
do {
58
len = _sntprintf(msg, sizeof(msg) / sizeof(TCHAR),
59
_T("OPENSSL_Uplink(%p,%02X): "), table, index);
60
_tcscpy(msg + len, _T("unimplemented function"));
61
62
if ((h = apphandle) == NULL) {
63
if ((h = GetModuleHandle(NULL)) == NULL) {
64
apphandle = (HMODULE)-1;
65
_tcscpy(msg + len, _T("no host application"));
66
break;
67
}
68
apphandle = h;
69
}
70
if ((h = apphandle) == (HMODULE)-1) /* revalidate */
71
break;
72
73
if (applinktable == NULL) {
74
void **(*applink)();
75
76
applink = (void **(*)())GetProcAddress(h, "OPENSSL_Applink");
77
if (applink == NULL) {
78
apphandle = (HMODULE)-1;
79
_tcscpy(msg + len, _T("no OPENSSL_Applink"));
80
break;
81
}
82
p = (*applink)();
83
if (p == NULL) {
84
apphandle = (HMODULE)-1;
85
_tcscpy(msg + len, _T("no ApplinkTable"));
86
break;
87
}
88
applinktable = p;
89
} else
90
p = applinktable;
91
92
if (index > (int)p[0])
93
break;
94
95
if (p[index])
96
func = p[index];
97
} while (0);
98
99
table[index] = func;
100
}
101
102
#if (defined(_MSC_VER) || defined(__BORLANDC__)) && defined(_M_IX86)
103
#if defined(_MSC_VER)
104
#define LAZY(i) \
105
__declspec(naked) static void lazy##i(void) \
106
{ \
107
_asm push i _asm push OFFSET OPENSSL_UplinkTable _asm call OPENSSL_Uplink _asm add esp, 8 _asm jmp OPENSSL_UplinkTable + 4 * i \
108
}
109
#elif defined(__BORLANDC__) && defined(__clang__)
110
void *OPENSSL_UplinkTable[26]; /* C++Builder requires declaration before use */
111
#define LAZY(i) \
112
__declspec(naked) static void lazy##i(void) \
113
{ \
114
__asm__("pushl $" #i "; " \
115
"pushl %0; " \
116
"call %P1; " \
117
"addl $8, %%esp; " \
118
"jmp *%2 " \
119
: /* no outputs */ \
120
: "i"(OPENSSL_UplinkTable), \
121
"i"(OPENSSL_Uplink), \
122
"m"(OPENSSL_UplinkTable[i])); \
123
}
124
#endif
125
126
#if APPLINK_MAX > 25
127
#error "Add more stubs..."
128
#endif
129
/* make some in advance... */
130
LAZY(1)
131
LAZY(2)
132
LAZY(3)
133
LAZY(4)
134
LAZY(5)
135
LAZY(6)
136
LAZY(7)
137
LAZY(8)
138
LAZY(9)
139
LAZY(10)
140
LAZY(11)
141
LAZY(12)
142
LAZY(13)
143
LAZY(14)
144
LAZY(15)
145
LAZY(16)
146
LAZY(17)
147
LAZY(18)
148
LAZY(19)
149
LAZY(20)
150
LAZY(21)
151
LAZY(22)
152
LAZY(23)
153
LAZY(24)
154
LAZY(25)
155
void *OPENSSL_UplinkTable[] = {
156
(void *)APPLINK_MAX,
157
lazy1,
158
lazy2,
159
lazy3,
160
lazy4,
161
lazy5,
162
lazy6,
163
lazy7,
164
lazy8,
165
lazy9,
166
lazy10,
167
lazy11,
168
lazy12,
169
lazy13,
170
lazy14,
171
lazy15,
172
lazy16,
173
lazy17,
174
lazy18,
175
lazy19,
176
lazy20,
177
lazy21,
178
lazy22,
179
lazy23,
180
lazy24,
181
lazy25,
182
};
183
#endif
184
185
#ifdef SELFTEST
186
main()
187
{
188
UP_fprintf(UP_stdout, "hello, world!\n");
189
}
190
#endif
191
192