Skip to content

Commit b46c359

Browse files
committed
global: move init callbacks into an array
We currently have an explicit callchain of all the initialization callbacks in our `init_common` function. This is perfectly fine, but requires us to manually keep track of how many shutdown callbacks there may be installed: to avoid allocations before libgit2 is fully initialized, we assume that every initializer may register at most one shutdown function. These shutdown functions are stored in a static array of size `MAX_SHUTDOWN_CB`, which then needs to be updated manually whenever a new initializer function is being added. The situation can be easily fixed: convert the callchain of init functions into an array and iterate over it to initialize all subsystems. This allows us to define the `git__shutdown_callbacks` array with the same size as the initializer array and rids us of the need to always update `MAX_SHUTDOWN_CB`.
1 parent 03dc648 commit b46c359

File tree

1 file changed

+22
-14
lines changed

1 file changed

+22
-14
lines changed

src/global.c

Lines changed: 22 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -26,9 +26,23 @@
2626

2727
git_mutex git__mwindow_mutex;
2828

29-
#define MAX_SHUTDOWN_CB 10
29+
typedef int (*git_global_init_fn)(void);
30+
31+
static git_global_init_fn git__init_callbacks[] = {
32+
git_allocator_global_init,
33+
git_hash_global_init,
34+
git_sysdir_global_init,
35+
git_filter_global_init,
36+
git_merge_driver_global_init,
37+
git_transport_ssh_global_init,
38+
git_stream_registry_global_init,
39+
git_openssl_stream_global_init,
40+
git_mbedtls_stream_global_init,
41+
git_mwindow_global_init
42+
};
43+
44+
static git_global_shutdown_fn git__shutdown_callbacks[ARRAY_SIZE(git__init_callbacks)];
3045

31-
static git_global_shutdown_fn git__shutdown_callbacks[MAX_SHUTDOWN_CB];
3246
static git_atomic git__n_shutdown_callbacks;
3347
static git_atomic git__n_inits;
3448
char *git__user_agent;
@@ -37,7 +51,7 @@ char *git__ssl_ciphers;
3751
void git__on_shutdown(git_global_shutdown_fn callback)
3852
{
3953
int count = git_atomic_inc(&git__n_shutdown_callbacks);
40-
assert(count <= MAX_SHUTDOWN_CB && count > 0);
54+
assert(count <= (int) ARRAY_SIZE(git__shutdown_callbacks) && count > 0);
4155
git__shutdown_callbacks[count - 1] = callback;
4256
}
4357

@@ -52,6 +66,7 @@ static void git__global_state_cleanup(git_global_st *st)
5266

5367
static int init_common(void)
5468
{
69+
size_t i;
5570
int ret;
5671

5772
/* Initialize the CRT debug allocator first, before our first malloc */
@@ -60,17 +75,10 @@ static int init_common(void)
6075
git_win32__stack_init();
6176
#endif
6277

63-
/* Initialize any other subsystems that have global state */
64-
if ((ret = git_allocator_global_init()) == 0 &&
65-
(ret = git_hash_global_init()) == 0 &&
66-
(ret = git_sysdir_global_init()) == 0 &&
67-
(ret = git_filter_global_init()) == 0 &&
68-
(ret = git_merge_driver_global_init()) == 0 &&
69-
(ret = git_transport_ssh_global_init()) == 0 &&
70-
(ret = git_stream_registry_global_init()) == 0 &&
71-
(ret = git_openssl_stream_global_init()) == 0 &&
72-
(ret = git_mbedtls_stream_global_init()) == 0)
73-
ret = git_mwindow_global_init();
78+
/* Initialize subsystems that have global state */
79+
for (i = 0; i < ARRAY_SIZE(git__init_callbacks); i++)
80+
if ((ret = git__init_callbacks[i]()) != 0)
81+
break;
7482

7583
GIT_MEMORY_BARRIER;
7684

0 commit comments

Comments
 (0)