Skip to content

Commit cd8fde8

Browse files
authored
Merge pull request libgit2#6258 from libgit2/ethomson/sha256_openssl_dynamic
sha256: support dynamically loaded openssl
2 parents d8015d2 + 3bd9bb8 commit cd8fde8

File tree

5 files changed

+107
-3
lines changed

5 files changed

+107
-3
lines changed

cmake/SelectHashes.cmake

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,10 @@ if(USE_SHA1 STREQUAL "CollisionDetection")
2626
set(GIT_SHA1_COLLISIONDETECT 1)
2727
elseif(USE_SHA1 STREQUAL "OpenSSL")
2828
set(GIT_SHA1_OPENSSL 1)
29+
elseif(USE_SHA1 STREQUAL "OpenSSL-Dynamic")
30+
set(GIT_SHA1_OPENSSL 1)
31+
set(GIT_SHA1_OPENSSL_DYNAMIC 1)
32+
list(APPEND LIBGIT2_SYSTEM_LIBS dl)
2933
elseif(USE_SHA1 STREQUAL "CommonCrypto")
3034
set(GIT_SHA1_COMMON_CRYPTO 1)
3135
elseif(USE_SHA1 STREQUAL "mbedTLS")
@@ -58,6 +62,10 @@ if(USE_SHA256 STREQUAL "Builtin")
5862
set(GIT_SHA256_BUILTIN 1)
5963
elseif(USE_SHA256 STREQUAL "OpenSSL")
6064
set(GIT_SHA256_OPENSSL 1)
65+
elseif(USE_SHA256 STREQUAL "OpenSSL-Dynamic")
66+
set(GIT_SHA256_OPENSSL 1)
67+
set(GIT_SHA256_OPENSSL_DYNAMIC 1)
68+
list(APPEND LIBGIT2_SYSTEM_LIBS dl)
6169
elseif(USE_SHA256 STREQUAL "CommonCrypto")
6270
set(GIT_SHA256_COMMON_CRYPTO 1)
6371
elseif(USE_SHA256 STREQUAL "mbedTLS")

src/features.h.in

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,12 +46,14 @@
4646
#cmakedefine GIT_SHA1_WIN32 1
4747
#cmakedefine GIT_SHA1_COMMON_CRYPTO 1
4848
#cmakedefine GIT_SHA1_OPENSSL 1
49+
#cmakedefine GIT_SHA1_OPENSSL_DYNAMIC 1
4950
#cmakedefine GIT_SHA1_MBEDTLS 1
5051

5152
#cmakedefine GIT_SHA256_BUILTIN 1
5253
#cmakedefine GIT_SHA256_WIN32 1
5354
#cmakedefine GIT_SHA256_COMMON_CRYPTO 1
5455
#cmakedefine GIT_SHA256_OPENSSL 1
56+
#cmakedefine GIT_SHA256_OPENSSL_DYNAMIC 1
5557
#cmakedefine GIT_SHA256_MBEDTLS 1
5658

5759
#cmakedefine GIT_RAND_GETENTROPY 1

src/util/CMakeLists.txt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ if(USE_SHA1 STREQUAL "CollisionDetection")
3333
target_compile_definitions(util PRIVATE SHA1DC_NO_STANDARD_INCLUDES=1)
3434
target_compile_definitions(util PRIVATE SHA1DC_CUSTOM_INCLUDE_SHA1_C=\"git2_util.h\")
3535
target_compile_definitions(util PRIVATE SHA1DC_CUSTOM_INCLUDE_UBC_CHECK_C=\"git2_util.h\")
36-
elseif(USE_SHA1 STREQUAL "OpenSSL")
36+
elseif(USE_SHA1 STREQUAL "OpenSSL" OR USE_SHA1 STREQUAL "OpenSSL-Dynamic")
3737
file(GLOB UTIL_SRC_SHA1 hash/openssl.*)
3838
elseif(USE_SHA1 STREQUAL "CommonCrypto")
3939
file(GLOB UTIL_SRC_SHA1 hash/common_crypto.*)
@@ -49,7 +49,7 @@ list(SORT UTIL_SRC_SHA1)
4949

5050
if(USE_SHA256 STREQUAL "Builtin")
5151
file(GLOB UTIL_SRC_SHA256 hash/builtin.* hash/rfc6234/*)
52-
elseif(USE_SHA256 STREQUAL "OpenSSL")
52+
elseif(USE_SHA256 STREQUAL "OpenSSL" OR USE_SHA256 STREQUAL "OpenSSL-Dynamic")
5353
file(GLOB UTIL_SRC_SHA256 hash/openssl.*)
5454
elseif(USE_SHA256 STREQUAL "CommonCrypto")
5555
file(GLOB UTIL_SRC_SHA256 hash/common_crypto.*)

src/util/hash/openssl.c

Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,67 @@
77

88
#include "openssl.h"
99

10+
#ifdef GIT_OPENSSL_DYNAMIC
11+
# include <dlfcn.h>
12+
13+
int handle_count;
14+
void *openssl_handle;
15+
16+
static int git_hash_openssl_global_shutdown(void)
17+
{
18+
if (--handle_count == 0) {
19+
dlclose(openssl_handle);
20+
openssl_handle = NULL;
21+
}
22+
23+
return 0;
24+
}
25+
26+
static int git_hash_openssl_global_init(void)
27+
{
28+
if (!handle_count) {
29+
if ((openssl_handle = dlopen("libssl.so.1.1", RTLD_NOW)) == NULL &&
30+
(openssl_handle = dlopen("libssl.1.1.dylib", RTLD_NOW)) == NULL &&
31+
(openssl_handle = dlopen("libssl.so.1.0.0", RTLD_NOW)) == NULL &&
32+
(openssl_handle = dlopen("libssl.1.0.0.dylib", RTLD_NOW)) == NULL &&
33+
(openssl_handle = dlopen("libssl.so.10", RTLD_NOW)) == NULL) {
34+
git_error_set(GIT_ERROR_SSL, "could not load ssl libraries");
35+
return -1;
36+
}
37+
}
38+
39+
if (git_hash_openssl_global_shutdown() < 0)
40+
return -1;
41+
42+
handle_count++;
43+
return 0;
44+
}
45+
46+
#endif
47+
1048
#ifdef GIT_SHA1_OPENSSL
1149

50+
# ifdef GIT_OPENSSL_DYNAMIC
51+
static int (*SHA1_Init)(SHA_CTX *c);
52+
static int (*SHA1_Update)(SHA_CTX *c, const void *data, size_t len);
53+
static int (*SHA1_Final)(unsigned char *md, SHA_CTX *c);
54+
# endif
55+
1256
int git_hash_sha1_global_init(void)
1357
{
58+
#ifdef GIT_OPENSSL_DYNAMIC
59+
if (git_hash_openssl_global_init() < 0)
60+
return -1;
61+
62+
if ((SHA1_Init = dlsym(openssl_handle, "SHA1_Init")) == NULL ||
63+
(SHA1_Update = dlsym(openssl_handle, "SHA1_Update")) == NULL ||
64+
(SHA1_Final = dlsym(openssl_handle, "SHA1_Final")) == NULL) {
65+
const char *msg = dlerror();
66+
git_error_set(GIT_ERROR_SSL, "could not load hash function: %s", msg ? msg : "unknown error");
67+
return -1;
68+
}
69+
#endif
70+
1471
return 0;
1572
}
1673

@@ -64,8 +121,27 @@ int git_hash_sha1_final(unsigned char *out, git_hash_sha1_ctx *ctx)
64121

65122
#ifdef GIT_SHA256_OPENSSL
66123

124+
# ifdef GIT_OPENSSL_DYNAMIC
125+
static int (*SHA256_Init)(SHA256_CTX *c);
126+
static int (*SHA256_Update)(SHA256_CTX *c, const void *data, size_t len);
127+
static int (*SHA256_Final)(unsigned char *md, SHA256_CTX *c);
128+
#endif
129+
67130
int git_hash_sha256_global_init(void)
68131
{
132+
#ifdef GIT_OPENSSL_DYNAMIC
133+
if (git_hash_openssl_global_init() < 0)
134+
return -1;
135+
136+
if ((SHA256_Init = dlsym(openssl_handle, "SHA256_Init")) == NULL ||
137+
(SHA256_Update = dlsym(openssl_handle, "SHA256_Update")) == NULL ||
138+
(SHA256_Final = dlsym(openssl_handle, "SHA256_Final")) == NULL) {
139+
const char *msg = dlerror();
140+
git_error_set(GIT_ERROR_SSL, "could not load hash function: %s", msg ? msg : "unknown error");
141+
return -1;
142+
}
143+
#endif
144+
69145
return 0;
70146
}
71147

src/util/hash/openssl.h

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,25 @@
1010

1111
#include "hash/sha.h"
1212

13-
#include <openssl/sha.h>
13+
#ifndef GIT_OPENSSL_DYNAMIC
14+
# include <openssl/sha.h>
15+
#else
16+
17+
typedef struct {
18+
unsigned int h0, h1, h2, h3, h4;
19+
unsigned int Nl, Nh;
20+
unsigned int data[16];
21+
unsigned int num;
22+
} SHA_CTX;
23+
24+
typedef struct {
25+
unsigned int h[8];
26+
unsigned int Nl, Nh;
27+
unsigned int data[16];
28+
unsigned int num, md_len;
29+
} SHA256_CTX;
30+
31+
#endif
1432

1533
#ifdef GIT_SHA1_OPENSSL
1634
struct git_hash_sha1_ctx {

0 commit comments

Comments
 (0)