source src/streams/registry.c
Line | Flow | Count | Block(s) | Source |
---|---|---|---|---|
1 | - | /* | ||
2 | - | * Copyright (C) the libgit2 contributors. All rights reserved. | ||
3 | - | * | ||
4 | - | * This file is part of libgit2, distributed under the GNU GPL v2 with | ||
5 | - | * a Linking Exception. For full terms see the included COPYING file. | ||
6 | - | */ | ||
7 | - | |||
8 | - | #include "common.h" | ||
9 | - | |||
10 | - | #include "streams/registry.h" | ||
11 | - | |||
12 | - | #include "global.h" | ||
13 | - | #include "streams/tls.h" | ||
14 | - | #include "streams/mbedtls.h" | ||
15 | - | #include "streams/openssl.h" | ||
16 | - | #include "streams/stransport.h" | ||
17 | - | |||
18 | - | struct stream_registry { | ||
19 | - | git_rwlock lock; | ||
20 | - | git_stream_registration callbacks; | ||
21 | - | git_stream_registration tls_callbacks; | ||
22 | - | }; | ||
23 | - | |||
24 | - | static struct stream_registry stream_registry; | ||
25 | - | |||
26 | 9 | 2 | static void shutdown_stream_registry(void) | |
27 | - | { | ||
28 | 9 | 2 | git_rwlock_free(&stream_registry.lock); | |
29 | 9 | 3 | } | |
30 | - | |||
31 | 9 | 2 | int git_stream_registry_global_init(void) | |
32 | - | { | ||
33 | 9 | 2,3 | if (git_rwlock_init(&stream_registry.lock) < 0) | |
34 | ##### | 4 | return -1; | |
35 | - | |||
36 | 9 | 5 | git__on_shutdown(shutdown_stream_registry); | |
37 | 9 | 6 | return 0; | |
38 | - | } | ||
39 | - | |||
40 | 18 | 2 | GIT_INLINE(void) stream_registration_cpy( | |
41 | - | git_stream_registration *target, | ||
42 | - | git_stream_registration *src) | ||
43 | - | { | ||
44 | 18 | 2 | if (src) | |
45 | 8 | 3 | memcpy(target, src, sizeof(git_stream_registration)); | |
46 | - | else | ||
47 | 10 | 4 | memset(target, 0, sizeof(git_stream_registration)); | |
48 | 18 | 5 | } | |
49 | - | |||
50 | 147 | 2 | int git_stream_registry_lookup(git_stream_registration *out, git_stream_t type) | |
51 | - | { | ||
52 | - | git_stream_registration *target; | ||
53 | 147 | 2 | int error = GIT_ENOTFOUND; | |
54 | - | |||
55 | 147 | 2,3 | assert(out); | |
56 | - | |||
57 | 147 | 4 | switch(type) { | |
58 | - | case GIT_STREAM_STANDARD: | ||
59 | 96 | 5 | target = &stream_registry.callbacks; | |
60 | 96 | 5 | break; | |
61 | - | case GIT_STREAM_TLS: | ||
62 | 51 | 6 | target = &stream_registry.tls_callbacks; | |
63 | 51 | 6 | break; | |
64 | - | default: | ||
65 | - | 7 | assert(0); | |
66 | - | return -1; | ||
67 | - | } | ||
68 | - | |||
69 | 147 | 8,9 | if (git_rwlock_rdlock(&stream_registry.lock) < 0) { | |
70 | ##### | 10 | git_error_set(GIT_ERROR_OS, "failed to lock stream registry"); | |
71 | ##### | 11 | return -1; | |
72 | - | } | ||
73 | - | |||
74 | 147 | 12 | if (target->init) { | |
75 | 4 | 13 | stream_registration_cpy(out, target); | |
76 | 4 | 14 | error = 0; | |
77 | - | } | ||
78 | - | |||
79 | 147 | 15 | git_rwlock_rdunlock(&stream_registry.lock); | |
80 | 147 | 16 | return error; | |
81 | - | } | ||
82 | - | |||
83 | 9 | 2 | int git_stream_register(git_stream_t type, git_stream_registration *registration) | |
84 | - | { | ||
85 | 9 | 2-4 | assert(!registration || registration->init); | |
86 | - | |||
87 | 9 | 5-7 | GIT_ERROR_CHECK_VERSION(registration, GIT_STREAM_VERSION, "stream_registration"); | |
88 | - | |||
89 | 9 | 8,9 | if (git_rwlock_wrlock(&stream_registry.lock) < 0) { | |
90 | ##### | 10 | git_error_set(GIT_ERROR_OS, "failed to lock stream registry"); | |
91 | ##### | 11 | return -1; | |
92 | - | } | ||
93 | - | |||
94 | 9 | 12 | if ((type & GIT_STREAM_STANDARD) == GIT_STREAM_STANDARD) | |
95 | 7 | 13 | stream_registration_cpy(&stream_registry.callbacks, registration); | |
96 | - | |||
97 | 9 | 14 | if ((type & GIT_STREAM_TLS) == GIT_STREAM_TLS) | |
98 | 7 | 15 | stream_registration_cpy(&stream_registry.tls_callbacks, registration); | |
99 | - | |||
100 | 9 | 16 | git_rwlock_wrunlock(&stream_registry.lock); | |
101 | 9 | 17 | return 0; | |
102 | - | } | ||
103 | - | |||
104 | - | #ifndef GIT_DEPRECATE_HARD | ||
105 | ##### | 2 | int git_stream_register_tls( | |
106 | - | int GIT_CALLBACK(ctor)(git_stream **out, const char *host, const char *port)) | ||
107 | - | { | ||
108 | ##### | 2 | git_stream_registration registration = {0}; | |
109 | - | |||
110 | ##### | 2 | if (ctor) { | |
111 | ##### | 3 | registration.version = GIT_STREAM_VERSION; | |
112 | ##### | 3 | registration.init = ctor; | |
113 | ##### | 3 | registration.wrap = NULL; | |
114 | - | |||
115 | ##### | 3 | return git_stream_register(GIT_STREAM_TLS, ®istration); | |
116 | - | } else { | ||
117 | ##### | 4 | return git_stream_register(GIT_STREAM_TLS, NULL); | |
118 | - | } | ||
119 | - | } | ||
120 | - | #endif |