Coverage Report

Created: 2025-06-13 06:55

/src/glib/gio/gtlsbackend.c
Line
Count
Source (jump to first uncovered line)
1
/* GIO - GLib Input, Output and Streaming Library
2
 *
3
 * Copyright © 2010 Red Hat, Inc
4
 * Copyright © 2015 Collabora, Ltd.
5
 *
6
 * SPDX-License-Identifier: LGPL-2.1-or-later
7
 *
8
 * This library is free software; you can redistribute it and/or
9
 * modify it under the terms of the GNU Lesser General Public
10
 * License as published by the Free Software Foundation; either
11
 * version 2.1 of the License, or (at your option) any later version.
12
 *
13
 * This library is distributed in the hope that it will be useful,
14
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16
 * Lesser General Public License for more details.
17
 *
18
 * You should have received a copy of the GNU Lesser General
19
 * Public License along with this library; if not, see <http://www.gnu.org/licenses/>.
20
 */
21
22
#include "config.h"
23
#include "glib.h"
24
25
#include "gtlsbackend.h"
26
#include "gtlsdatabase.h"
27
#include "gdummytlsbackend.h"
28
#include "gioenumtypes.h"
29
#include "giomodule-priv.h"
30
31
/**
32
 * SECTION:gtls
33
 * @title: TLS Overview
34
 * @short_description: TLS (aka SSL) support for GSocketConnection
35
 * @include: gio/gio.h
36
 *
37
 * #GTlsConnection and related classes provide TLS (Transport Layer
38
 * Security, previously known as SSL, Secure Sockets Layer) support for
39
 * gio-based network streams.
40
 *
41
 * #GDtlsConnection and related classes provide DTLS (Datagram TLS) support for
42
 * GIO-based network sockets, using the #GDatagramBased interface. The TLS and
43
 * DTLS APIs are almost identical, except TLS is stream-based and DTLS is
44
 * datagram-based. They share certificate and backend infrastructure.
45
 *
46
 * In the simplest case, for a client TLS connection, you can just set the
47
 * #GSocketClient:tls flag on a #GSocketClient, and then any
48
 * connections created by that client will have TLS negotiated
49
 * automatically, using appropriate default settings, and rejecting
50
 * any invalid or self-signed certificates (unless you change that
51
 * default by setting the #GSocketClient:tls-validation-flags
52
 * property). The returned object will be a #GTcpWrapperConnection,
53
 * which wraps the underlying #GTlsClientConnection.
54
 *
55
 * For greater control, you can create your own #GTlsClientConnection,
56
 * wrapping a #GSocketConnection (or an arbitrary #GIOStream with
57
 * pollable input and output streams) and then connect to its signals,
58
 * such as #GTlsConnection::accept-certificate, before starting the
59
 * handshake.
60
 *
61
 * Server-side TLS is similar, using #GTlsServerConnection. At the
62
 * moment, there is no support for automatically wrapping server-side
63
 * connections in the way #GSocketClient does for client-side
64
 * connections.
65
 */
66
67
/**
68
 * SECTION:gtlsbackend
69
 * @title: GTlsBackend
70
 * @short_description: TLS backend implementation
71
 * @include: gio/gio.h
72
 *
73
 * TLS (Transport Layer Security, aka SSL) and DTLS backend.
74
 *
75
 * Since: 2.28
76
 */
77
78
/**
79
 * GTlsBackend:
80
 *
81
 * TLS (Transport Layer Security, aka SSL) and DTLS backend. This is an
82
 * internal type used to coordinate the different classes implemented
83
 * by a TLS backend.
84
 *
85
 * Since: 2.28
86
 */
87
88
G_DEFINE_INTERFACE (GTlsBackend, g_tls_backend, G_TYPE_OBJECT)
89
90
static GTlsDatabase *default_database;
91
G_LOCK_DEFINE_STATIC (default_database_lock);
92
93
static void
94
g_tls_backend_default_init (GTlsBackendInterface *iface)
95
0
{
96
0
}
97
98
static GTlsBackend *tls_backend_default_singleton = NULL;  /* (owned) (atomic) */
99
100
/**
101
 * g_tls_backend_get_default:
102
 *
103
 * Gets the default #GTlsBackend for the system.
104
 *
105
 * Returns: (not nullable) (transfer none): a #GTlsBackend, which will be a
106
 *     dummy object if no TLS backend is available
107
 *
108
 * Since: 2.28
109
 */
110
GTlsBackend *
111
g_tls_backend_get_default (void)
112
0
{
113
0
  if (g_once_init_enter (&tls_backend_default_singleton))
114
0
    {
115
0
      GTlsBackend *singleton;
116
117
0
      singleton = _g_io_module_get_default (G_TLS_BACKEND_EXTENSION_POINT_NAME,
118
0
                                            "GIO_USE_TLS",
119
0
                                            NULL);
120
121
0
      g_once_init_leave (&tls_backend_default_singleton, singleton);
122
0
    }
123
124
0
  return tls_backend_default_singleton;
125
0
}
126
127
/**
128
 * g_tls_backend_supports_tls:
129
 * @backend: the #GTlsBackend
130
 *
131
 * Checks if TLS is supported; if this returns %FALSE for the default
132
 * #GTlsBackend, it means no "real" TLS backend is available.
133
 *
134
 * Returns: whether or not TLS is supported
135
 *
136
 * Since: 2.28
137
 */
138
gboolean
139
g_tls_backend_supports_tls (GTlsBackend *backend)
140
0
{
141
0
  if (G_TLS_BACKEND_GET_INTERFACE (backend)->supports_tls)
142
0
    return G_TLS_BACKEND_GET_INTERFACE (backend)->supports_tls (backend);
143
0
  else if (G_IS_DUMMY_TLS_BACKEND (backend))
144
0
    return FALSE;
145
0
  else
146
0
    return TRUE;
147
0
}
148
149
/**
150
 * g_tls_backend_supports_dtls:
151
 * @backend: the #GTlsBackend
152
 *
153
 * Checks if DTLS is supported. DTLS support may not be available even if TLS
154
 * support is available, and vice-versa.
155
 *
156
 * Returns: whether DTLS is supported
157
 *
158
 * Since: 2.48
159
 */
160
gboolean
161
g_tls_backend_supports_dtls (GTlsBackend *backend)
162
0
{
163
0
  if (G_TLS_BACKEND_GET_INTERFACE (backend)->supports_dtls)
164
0
    return G_TLS_BACKEND_GET_INTERFACE (backend)->supports_dtls (backend);
165
166
0
  return FALSE;
167
0
}
168
169
/**
170
 * g_tls_backend_get_default_database:
171
 * @backend: the #GTlsBackend
172
 *
173
 * Gets the default #GTlsDatabase used to verify TLS connections.
174
 *
175
 * Returns: (transfer full): the default database, which should be
176
 *               unreffed when done.
177
 *
178
 * Since: 2.30
179
 */
180
GTlsDatabase *
181
g_tls_backend_get_default_database (GTlsBackend *backend)
182
0
{
183
0
  GTlsDatabase *db;
184
185
0
  g_return_val_if_fail (G_IS_TLS_BACKEND (backend), NULL);
186
187
  /* This method was added later, so accept the (remote) possibility it can be NULL */
188
0
  if (!G_TLS_BACKEND_GET_INTERFACE (backend)->get_default_database)
189
0
    return NULL;
190
191
0
  G_LOCK (default_database_lock);
192
193
0
  if (!default_database)
194
0
    default_database = G_TLS_BACKEND_GET_INTERFACE (backend)->get_default_database (backend);
195
0
  db = default_database ? g_object_ref (default_database) : NULL;
196
0
  G_UNLOCK (default_database_lock);
197
198
0
  return db;
199
0
}
200
201
/**
202
 * g_tls_backend_set_default_database:
203
 * @backend: the #GTlsBackend
204
 * @database: (nullable): the #GTlsDatabase
205
 *
206
 * Set the default #GTlsDatabase used to verify TLS connections
207
 *
208
 * Any subsequent call to g_tls_backend_get_default_database() will return
209
 * the database set in this call.  Existing databases and connections are not
210
 * modified.
211
 *
212
 * Setting a %NULL default database will reset to using the system default
213
 * database as if g_tls_backend_set_default_database() had never been called.
214
 *
215
 * Since: 2.60
216
 */
217
void
218
g_tls_backend_set_default_database (GTlsBackend  *backend,
219
                                    GTlsDatabase *database)
220
0
{
221
0
  g_return_if_fail (G_IS_TLS_BACKEND (backend));
222
0
  g_return_if_fail (database == NULL || G_IS_TLS_DATABASE (database));
223
224
0
  G_LOCK (default_database_lock);
225
0
  g_set_object (&default_database, database);
226
0
  G_UNLOCK (default_database_lock);
227
0
}
228
229
/**
230
 * g_tls_backend_get_certificate_type:
231
 * @backend: the #GTlsBackend
232
 *
233
 * Gets the #GType of @backend's #GTlsCertificate implementation.
234
 *
235
 * Returns: the #GType of @backend's #GTlsCertificate
236
 *   implementation.
237
 *
238
 * Since: 2.28
239
 */
240
GType
241
g_tls_backend_get_certificate_type (GTlsBackend *backend)
242
0
{
243
0
  return G_TLS_BACKEND_GET_INTERFACE (backend)->get_certificate_type ();
244
0
}
245
246
/**
247
 * g_tls_backend_get_client_connection_type:
248
 * @backend: the #GTlsBackend
249
 *
250
 * Gets the #GType of @backend's #GTlsClientConnection implementation.
251
 *
252
 * Returns: the #GType of @backend's #GTlsClientConnection
253
 *   implementation.
254
 *
255
 * Since: 2.28
256
 */
257
GType
258
g_tls_backend_get_client_connection_type (GTlsBackend *backend)
259
0
{
260
0
  return G_TLS_BACKEND_GET_INTERFACE (backend)->get_client_connection_type ();
261
0
}
262
263
/**
264
 * g_tls_backend_get_server_connection_type:
265
 * @backend: the #GTlsBackend
266
 *
267
 * Gets the #GType of @backend's #GTlsServerConnection implementation.
268
 *
269
 * Returns: the #GType of @backend's #GTlsServerConnection
270
 *   implementation.
271
 *
272
 * Since: 2.28
273
 */
274
GType
275
g_tls_backend_get_server_connection_type (GTlsBackend *backend)
276
0
{
277
0
  return G_TLS_BACKEND_GET_INTERFACE (backend)->get_server_connection_type ();
278
0
}
279
280
/**
281
 * g_tls_backend_get_dtls_client_connection_type:
282
 * @backend: the #GTlsBackend
283
 *
284
 * Gets the #GType of @backend’s #GDtlsClientConnection implementation.
285
 *
286
 * Returns: the #GType of @backend’s #GDtlsClientConnection
287
 *   implementation, or %G_TYPE_INVALID if this backend doesn’t support DTLS.
288
 *
289
 * Since: 2.48
290
 */
291
GType
292
g_tls_backend_get_dtls_client_connection_type (GTlsBackend *backend)
293
0
{
294
0
  GTlsBackendInterface *iface;
295
296
0
  g_return_val_if_fail (G_IS_TLS_BACKEND (backend), G_TYPE_INVALID);
297
298
0
  iface = G_TLS_BACKEND_GET_INTERFACE (backend);
299
0
  if (iface->get_dtls_client_connection_type == NULL)
300
0
    return G_TYPE_INVALID;
301
302
0
  return iface->get_dtls_client_connection_type ();
303
0
}
304
305
/**
306
 * g_tls_backend_get_dtls_server_connection_type:
307
 * @backend: the #GTlsBackend
308
 *
309
 * Gets the #GType of @backend’s #GDtlsServerConnection implementation.
310
 *
311
 * Returns: the #GType of @backend’s #GDtlsServerConnection
312
 *   implementation, or %G_TYPE_INVALID if this backend doesn’t support DTLS.
313
 *
314
 * Since: 2.48
315
 */
316
GType
317
g_tls_backend_get_dtls_server_connection_type (GTlsBackend *backend)
318
0
{
319
0
  GTlsBackendInterface *iface;
320
321
0
  g_return_val_if_fail (G_IS_TLS_BACKEND (backend), G_TYPE_INVALID);
322
323
0
  iface = G_TLS_BACKEND_GET_INTERFACE (backend);
324
0
  if (iface->get_dtls_server_connection_type == NULL)
325
0
    return G_TYPE_INVALID;
326
327
0
  return iface->get_dtls_server_connection_type ();
328
0
}
329
330
/**
331
 * g_tls_backend_get_file_database_type:
332
 * @backend: the #GTlsBackend
333
 *
334
 * Gets the #GType of @backend's #GTlsFileDatabase implementation.
335
 *
336
 * Returns: the #GType of backend's #GTlsFileDatabase implementation.
337
 *
338
 * Since: 2.30
339
 */
340
GType
341
g_tls_backend_get_file_database_type (GTlsBackend *backend)
342
0
{
343
0
  g_return_val_if_fail (G_IS_TLS_BACKEND (backend), 0);
344
345
  /* This method was added later, so accept the (remote) possibility it can be NULL */
346
0
  if (!G_TLS_BACKEND_GET_INTERFACE (backend)->get_file_database_type)
347
0
    return 0;
348
349
0
  return G_TLS_BACKEND_GET_INTERFACE (backend)->get_file_database_type ();
350
0
}