• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* GIO - GLib Input, Output and Streaming Library
2  *
3  * Copyright (C) 2010 Collabora, Ltd.
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2.1 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General
16  * Public License along with this library; if not, see <http://www.gnu.org/licenses/>.
17  *
18  * Author: Stef Walter <stefw@collabora.co.uk>
19  */
20 
21 #include "config.h"
22 
23 #include "gtlsdatabase.h"
24 
25 #include "gasyncresult.h"
26 #include "gcancellable.h"
27 #include "glibintl.h"
28 #include "gsocketconnectable.h"
29 #include "gtask.h"
30 #include "gtlscertificate.h"
31 #include "gtlsinteraction.h"
32 
33 /**
34  * SECTION:gtlsdatabase
35  * @short_description: TLS database type
36  * @include: gio/gio.h
37  *
38  * #GTlsDatabase is used to look up certificates and other information
39  * from a certificate or key store. It is an abstract base class which
40  * TLS library specific subtypes override.
41  *
42  * A #GTlsDatabase may be accessed from multiple threads by the TLS backend.
43  * All implementations are required to be fully thread-safe.
44  *
45  * Most common client applications will not directly interact with
46  * #GTlsDatabase. It is used internally by #GTlsConnection.
47  *
48  * Since: 2.30
49  */
50 
51 /**
52  * GTlsDatabase:
53  *
54  * Abstract base class for the backend-specific database types.
55  *
56  * Since: 2.30
57  */
58 
59 /**
60  * GTlsDatabaseClass:
61  * @verify_chain: Virtual method implementing
62  *  g_tls_database_verify_chain().
63  * @verify_chain_async: Virtual method implementing
64  *  g_tls_database_verify_chain_async().
65  * @verify_chain_finish: Virtual method implementing
66  *  g_tls_database_verify_chain_finish().
67  * @create_certificate_handle: Virtual method implementing
68  *  g_tls_database_create_certificate_handle().
69  * @lookup_certificate_for_handle: Virtual method implementing
70  *  g_tls_database_lookup_certificate_for_handle().
71  * @lookup_certificate_for_handle_async: Virtual method implementing
72  *  g_tls_database_lookup_certificate_for_handle_async().
73  * @lookup_certificate_for_handle_finish: Virtual method implementing
74  *  g_tls_database_lookup_certificate_for_handle_finish().
75  * @lookup_certificate_issuer: Virtual method implementing
76  *  g_tls_database_lookup_certificate_issuer().
77  * @lookup_certificate_issuer_async: Virtual method implementing
78  *  g_tls_database_lookup_certificate_issuer_async().
79  * @lookup_certificate_issuer_finish: Virtual method implementing
80  *  g_tls_database_lookup_certificate_issuer_finish().
81  * @lookup_certificates_issued_by: Virtual method implementing
82  *  g_tls_database_lookup_certificates_issued_by().
83  * @lookup_certificates_issued_by_async: Virtual method implementing
84  *  g_tls_database_lookup_certificates_issued_by_async().
85  * @lookup_certificates_issued_by_finish: Virtual method implementing
86  *  g_tls_database_lookup_certificates_issued_by_finish().
87  *
88  * The class for #GTlsDatabase. Derived classes should implement the various
89  * virtual methods. _async and _finish methods have a default
90  * implementation that runs the corresponding sync method in a thread.
91  *
92  * Since: 2.30
93  */
94 
95 G_DEFINE_ABSTRACT_TYPE (GTlsDatabase, g_tls_database, G_TYPE_OBJECT)
96 
97 enum {
98   UNLOCK_REQUIRED,
99 
100   LAST_SIGNAL
101 };
102 
103 /**
104  * G_TLS_DATABASE_PURPOSE_AUTHENTICATE_SERVER:
105  *
106  * The purpose used to verify the server certificate in a TLS connection. This
107  * is the most common purpose in use. Used by TLS clients.
108  */
109 
110 /**
111  * G_TLS_DATABASE_PURPOSE_AUTHENTICATE_CLIENT:
112  *
113  * The purpose used to verify the client certificate in a TLS connection.
114  * Used by TLS servers.
115  */
116 
117 static void
g_tls_database_init(GTlsDatabase * cert)118 g_tls_database_init (GTlsDatabase *cert)
119 {
120 
121 }
122 
123 typedef struct _AsyncVerifyChain {
124   GTlsCertificate *chain;
125   gchar *purpose;
126   GSocketConnectable *identity;
127   GTlsInteraction *interaction;
128   GTlsDatabaseVerifyFlags flags;
129 } AsyncVerifyChain;
130 
131 static void
async_verify_chain_free(gpointer data)132 async_verify_chain_free (gpointer data)
133 {
134   AsyncVerifyChain *args = data;
135   g_clear_object (&args->chain);
136   g_free (args->purpose);
137   g_clear_object (&args->identity);
138   g_clear_object (&args->interaction);
139   g_slice_free (AsyncVerifyChain, args);
140 }
141 
142 static void
async_verify_chain_thread(GTask * task,gpointer object,gpointer task_data,GCancellable * cancellable)143 async_verify_chain_thread (GTask         *task,
144 			   gpointer       object,
145 			   gpointer       task_data,
146 			   GCancellable  *cancellable)
147 {
148   AsyncVerifyChain *args = task_data;
149   GTlsCertificateFlags verify_result;
150   GError *error = NULL;
151 
152   verify_result = g_tls_database_verify_chain (G_TLS_DATABASE (object),
153 					       args->chain,
154 					       args->purpose,
155 					       args->identity,
156 					       args->interaction,
157 					       args->flags,
158 					       cancellable,
159 					       &error);
160   if (error)
161     g_task_return_error (task, error);
162   else
163     g_task_return_int (task, (gssize)verify_result);
164 }
165 
166 static void
g_tls_database_real_verify_chain_async(GTlsDatabase * self,GTlsCertificate * chain,const gchar * purpose,GSocketConnectable * identity,GTlsInteraction * interaction,GTlsDatabaseVerifyFlags flags,GCancellable * cancellable,GAsyncReadyCallback callback,gpointer user_data)167 g_tls_database_real_verify_chain_async (GTlsDatabase           *self,
168                                         GTlsCertificate        *chain,
169                                         const gchar            *purpose,
170                                         GSocketConnectable     *identity,
171                                         GTlsInteraction        *interaction,
172                                         GTlsDatabaseVerifyFlags flags,
173                                         GCancellable           *cancellable,
174                                         GAsyncReadyCallback     callback,
175                                         gpointer                user_data)
176 {
177   GTask *task;
178   AsyncVerifyChain *args;
179 
180   args = g_slice_new0 (AsyncVerifyChain);
181   args->chain = g_object_ref (chain);
182   args->purpose = g_strdup (purpose);
183   args->identity = identity ? g_object_ref (identity) : NULL;
184   args->interaction = interaction ? g_object_ref (interaction) : NULL;
185   args->flags = flags;
186 
187   task = g_task_new (self, cancellable, callback, user_data);
188   g_task_set_source_tag (task, g_tls_database_real_verify_chain_async);
189   g_task_set_task_data (task, args, async_verify_chain_free);
190   g_task_run_in_thread (task, async_verify_chain_thread);
191   g_object_unref (task);
192 }
193 
194 static GTlsCertificateFlags
g_tls_database_real_verify_chain_finish(GTlsDatabase * self,GAsyncResult * result,GError ** error)195 g_tls_database_real_verify_chain_finish (GTlsDatabase          *self,
196                                          GAsyncResult          *result,
197                                          GError               **error)
198 {
199   GTlsCertificateFlags ret;
200 
201   g_return_val_if_fail (g_task_is_valid (result, self), G_TLS_CERTIFICATE_GENERIC_ERROR);
202 
203   ret = (GTlsCertificateFlags)g_task_propagate_int (G_TASK (result), error);
204   if (ret == (GTlsCertificateFlags)-1)
205     return G_TLS_CERTIFICATE_GENERIC_ERROR;
206   else
207     return ret;
208 }
209 
210 typedef struct {
211   gchar *handle;
212   GTlsInteraction *interaction;
213   GTlsDatabaseLookupFlags flags;
214 } AsyncLookupCertificateForHandle;
215 
216 static void
async_lookup_certificate_for_handle_free(gpointer data)217 async_lookup_certificate_for_handle_free (gpointer data)
218 {
219   AsyncLookupCertificateForHandle *args = data;
220 
221   g_free (args->handle);
222   g_clear_object (&args->interaction);
223   g_slice_free (AsyncLookupCertificateForHandle, args);
224 }
225 
226 static void
async_lookup_certificate_for_handle_thread(GTask * task,gpointer object,gpointer task_data,GCancellable * cancellable)227 async_lookup_certificate_for_handle_thread (GTask         *task,
228 					    gpointer       object,
229 					    gpointer       task_data,
230 					    GCancellable  *cancellable)
231 {
232   AsyncLookupCertificateForHandle *args = task_data;
233   GTlsCertificate *result;
234   GError *error = NULL;
235 
236   result = g_tls_database_lookup_certificate_for_handle (G_TLS_DATABASE (object),
237 							 args->handle,
238 							 args->interaction,
239 							 args->flags,
240 							 cancellable,
241 							 &error);
242   if (result)
243     g_task_return_pointer (task, result, g_object_unref);
244   else
245     g_task_return_error (task, error);
246 }
247 
248 static void
g_tls_database_real_lookup_certificate_for_handle_async(GTlsDatabase * self,const gchar * handle,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GAsyncReadyCallback callback,gpointer user_data)249 g_tls_database_real_lookup_certificate_for_handle_async (GTlsDatabase           *self,
250                                                          const gchar            *handle,
251                                                          GTlsInteraction        *interaction,
252                                                          GTlsDatabaseLookupFlags flags,
253                                                          GCancellable           *cancellable,
254                                                          GAsyncReadyCallback     callback,
255                                                          gpointer                user_data)
256 {
257   GTask *task;
258   AsyncLookupCertificateForHandle *args;
259 
260   args = g_slice_new0 (AsyncLookupCertificateForHandle);
261   args->handle = g_strdup (handle);
262   args->interaction = interaction ? g_object_ref (interaction) : NULL;
263 
264   task = g_task_new (self, cancellable, callback, user_data);
265   g_task_set_source_tag (task,
266                          g_tls_database_real_lookup_certificate_for_handle_async);
267   g_task_set_task_data (task, args, async_lookup_certificate_for_handle_free);
268   g_task_run_in_thread (task, async_lookup_certificate_for_handle_thread);
269   g_object_unref (task);
270 }
271 
272 static GTlsCertificate*
g_tls_database_real_lookup_certificate_for_handle_finish(GTlsDatabase * self,GAsyncResult * result,GError ** error)273 g_tls_database_real_lookup_certificate_for_handle_finish (GTlsDatabase          *self,
274                                                           GAsyncResult          *result,
275                                                           GError               **error)
276 {
277   g_return_val_if_fail (g_task_is_valid (result, self), NULL);
278 
279   return g_task_propagate_pointer (G_TASK (result), error);
280 }
281 
282 
283 typedef struct {
284   GTlsCertificate *certificate;
285   GTlsInteraction *interaction;
286   GTlsDatabaseLookupFlags flags;
287 } AsyncLookupCertificateIssuer;
288 
289 static void
async_lookup_certificate_issuer_free(gpointer data)290 async_lookup_certificate_issuer_free (gpointer data)
291 {
292   AsyncLookupCertificateIssuer *args = data;
293 
294   g_clear_object (&args->certificate);
295   g_clear_object (&args->interaction);
296   g_slice_free (AsyncLookupCertificateIssuer, args);
297 }
298 
299 static void
async_lookup_certificate_issuer_thread(GTask * task,gpointer object,gpointer task_data,GCancellable * cancellable)300 async_lookup_certificate_issuer_thread (GTask         *task,
301 					gpointer       object,
302 					gpointer       task_data,
303 					GCancellable  *cancellable)
304 {
305   AsyncLookupCertificateIssuer *args = task_data;
306   GTlsCertificate *issuer;
307   GError *error = NULL;
308 
309   issuer = g_tls_database_lookup_certificate_issuer (G_TLS_DATABASE (object),
310 						     args->certificate,
311 						     args->interaction,
312 						     args->flags,
313 						     cancellable,
314 						     &error);
315   if (issuer)
316     g_task_return_pointer (task, issuer, g_object_unref);
317   else
318     g_task_return_error (task, error);
319 }
320 
321 static void
g_tls_database_real_lookup_certificate_issuer_async(GTlsDatabase * self,GTlsCertificate * certificate,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GAsyncReadyCallback callback,gpointer user_data)322 g_tls_database_real_lookup_certificate_issuer_async (GTlsDatabase           *self,
323                                                      GTlsCertificate        *certificate,
324                                                      GTlsInteraction        *interaction,
325                                                      GTlsDatabaseLookupFlags flags,
326                                                      GCancellable           *cancellable,
327                                                      GAsyncReadyCallback     callback,
328                                                      gpointer                user_data)
329 {
330   GTask *task;
331   AsyncLookupCertificateIssuer *args;
332 
333   args = g_slice_new0 (AsyncLookupCertificateIssuer);
334   args->certificate = g_object_ref (certificate);
335   args->flags = flags;
336   args->interaction = interaction ? g_object_ref (interaction) : NULL;
337 
338   task = g_task_new (self, cancellable, callback, user_data);
339   g_task_set_source_tag (task,
340                          g_tls_database_real_lookup_certificate_issuer_async);
341   g_task_set_task_data (task, args, async_lookup_certificate_issuer_free);
342   g_task_run_in_thread (task, async_lookup_certificate_issuer_thread);
343   g_object_unref (task);
344 }
345 
346 static GTlsCertificate *
g_tls_database_real_lookup_certificate_issuer_finish(GTlsDatabase * self,GAsyncResult * result,GError ** error)347 g_tls_database_real_lookup_certificate_issuer_finish (GTlsDatabase          *self,
348                                                       GAsyncResult          *result,
349                                                       GError               **error)
350 {
351   g_return_val_if_fail (g_task_is_valid (result, self), NULL);
352 
353   return g_task_propagate_pointer (G_TASK (result), error);
354 }
355 
356 typedef struct {
357   GByteArray *issuer;
358   GTlsInteraction *interaction;
359   GTlsDatabaseLookupFlags flags;
360 } AsyncLookupCertificatesIssuedBy;
361 
362 static void
async_lookup_certificates_issued_by_free(gpointer data)363 async_lookup_certificates_issued_by_free (gpointer data)
364 {
365   AsyncLookupCertificatesIssuedBy *args = data;
366 
367   g_byte_array_unref (args->issuer);
368   g_clear_object (&args->interaction);
369   g_slice_free (AsyncLookupCertificatesIssuedBy, args);
370 }
371 
372 static void
async_lookup_certificates_free_certificates(gpointer data)373 async_lookup_certificates_free_certificates (gpointer data)
374 {
375   GList *list = data;
376 
377   g_list_free_full (list, g_object_unref);
378 }
379 
380 static void
async_lookup_certificates_issued_by_thread(GTask * task,gpointer object,gpointer task_data,GCancellable * cancellable)381 async_lookup_certificates_issued_by_thread (GTask         *task,
382 					    gpointer       object,
383 					    gpointer       task_data,
384                                             GCancellable  *cancellable)
385 {
386   AsyncLookupCertificatesIssuedBy *args = task_data;
387   GList *results;
388   GError *error = NULL;
389 
390   results = g_tls_database_lookup_certificates_issued_by (G_TLS_DATABASE (object),
391 							  args->issuer,
392 							  args->interaction,
393 							  args->flags,
394 							  cancellable,
395 							  &error);
396   if (results)
397     g_task_return_pointer (task, results, async_lookup_certificates_free_certificates);
398   else
399     g_task_return_error (task, error);
400 }
401 
402 static void
g_tls_database_real_lookup_certificates_issued_by_async(GTlsDatabase * self,GByteArray * issuer,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GAsyncReadyCallback callback,gpointer user_data)403 g_tls_database_real_lookup_certificates_issued_by_async (GTlsDatabase           *self,
404                                                          GByteArray             *issuer,
405                                                          GTlsInteraction        *interaction,
406                                                          GTlsDatabaseLookupFlags flags,
407                                                          GCancellable           *cancellable,
408                                                          GAsyncReadyCallback     callback,
409                                                          gpointer                user_data)
410 {
411   GTask *task;
412   AsyncLookupCertificatesIssuedBy *args;
413 
414   args = g_slice_new0 (AsyncLookupCertificatesIssuedBy);
415   args->issuer = g_byte_array_ref (issuer);
416   args->flags = flags;
417   args->interaction = interaction ? g_object_ref (interaction) : NULL;
418 
419   task = g_task_new (self, cancellable, callback, user_data);
420   g_task_set_source_tag (task,
421                          g_tls_database_real_lookup_certificates_issued_by_async);
422   g_task_set_task_data (task, args, async_lookup_certificates_issued_by_free);
423   g_task_run_in_thread (task, async_lookup_certificates_issued_by_thread);
424   g_object_unref (task);
425 }
426 
427 static GList *
g_tls_database_real_lookup_certificates_issued_by_finish(GTlsDatabase * self,GAsyncResult * result,GError ** error)428 g_tls_database_real_lookup_certificates_issued_by_finish (GTlsDatabase          *self,
429                                                           GAsyncResult          *result,
430                                                           GError               **error)
431 {
432   g_return_val_if_fail (g_task_is_valid (result, self), NULL);
433 
434   return g_task_propagate_pointer (G_TASK (result), error);
435 }
436 
437 static void
g_tls_database_class_init(GTlsDatabaseClass * klass)438 g_tls_database_class_init (GTlsDatabaseClass *klass)
439 {
440   klass->verify_chain_async = g_tls_database_real_verify_chain_async;
441   klass->verify_chain_finish = g_tls_database_real_verify_chain_finish;
442   klass->lookup_certificate_for_handle_async = g_tls_database_real_lookup_certificate_for_handle_async;
443   klass->lookup_certificate_for_handle_finish = g_tls_database_real_lookup_certificate_for_handle_finish;
444   klass->lookup_certificate_issuer_async = g_tls_database_real_lookup_certificate_issuer_async;
445   klass->lookup_certificate_issuer_finish = g_tls_database_real_lookup_certificate_issuer_finish;
446   klass->lookup_certificates_issued_by_async = g_tls_database_real_lookup_certificates_issued_by_async;
447   klass->lookup_certificates_issued_by_finish = g_tls_database_real_lookup_certificates_issued_by_finish;
448 }
449 
450 /**
451  * g_tls_database_verify_chain:
452  * @self: a #GTlsDatabase
453  * @chain: a #GTlsCertificate chain
454  * @purpose: the purpose that this certificate chain will be used for.
455  * @identity: (nullable): the expected peer identity
456  * @interaction: (nullable): used to interact with the user if necessary
457  * @flags: additional verify flags
458  * @cancellable: (nullable): a #GCancellable, or %NULL
459  * @error: (nullable): a #GError, or %NULL
460  *
461  * Determines the validity of a certificate chain after looking up and
462  * adding any missing certificates to the chain.
463  *
464  * @chain is a chain of #GTlsCertificate objects each pointing to the next
465  * certificate in the chain by its #GTlsCertificate:issuer property. The chain may initially
466  * consist of one or more certificates. After the verification process is
467  * complete, @chain may be modified by adding missing certificates, or removing
468  * extra certificates. If a certificate anchor was found, then it is added to
469  * the @chain.
470  *
471  * @purpose describes the purpose (or usage) for which the certificate
472  * is being used. Typically @purpose will be set to #G_TLS_DATABASE_PURPOSE_AUTHENTICATE_SERVER
473  * which means that the certificate is being used to authenticate a server
474  * (and we are acting as the client).
475  *
476  * The @identity is used to check for pinned certificates (trust exceptions)
477  * in the database. These will override the normal verification process on a
478  * host by host basis.
479  *
480  * Currently there are no @flags, and %G_TLS_DATABASE_VERIFY_NONE should be
481  * used.
482  *
483  * If @chain is found to be valid, then the return value will be 0. If
484  * @chain is found to be invalid, then the return value will indicate
485  * the problems found. If the function is unable to determine whether
486  * @chain is valid or not (eg, because @cancellable is triggered
487  * before it completes) then the return value will be
488  * %G_TLS_CERTIFICATE_GENERIC_ERROR and @error will be set
489  * accordingly. @error is not set when @chain is successfully analyzed
490  * but found to be invalid.
491  *
492  * This function can block, use g_tls_database_verify_chain_async() to perform
493  * the verification operation asynchronously.
494  *
495  * Returns: the appropriate #GTlsCertificateFlags which represents the
496  * result of verification.
497  *
498  * Since: 2.30
499  */
500 GTlsCertificateFlags
g_tls_database_verify_chain(GTlsDatabase * self,GTlsCertificate * chain,const gchar * purpose,GSocketConnectable * identity,GTlsInteraction * interaction,GTlsDatabaseVerifyFlags flags,GCancellable * cancellable,GError ** error)501 g_tls_database_verify_chain (GTlsDatabase           *self,
502                              GTlsCertificate        *chain,
503                              const gchar            *purpose,
504                              GSocketConnectable     *identity,
505                              GTlsInteraction        *interaction,
506                              GTlsDatabaseVerifyFlags flags,
507                              GCancellable           *cancellable,
508                              GError                **error)
509 {
510   g_return_val_if_fail (G_IS_TLS_DATABASE (self), G_TLS_CERTIFICATE_GENERIC_ERROR);
511   g_return_val_if_fail (G_IS_TLS_DATABASE (self),
512                         G_TLS_CERTIFICATE_GENERIC_ERROR);
513   g_return_val_if_fail (G_IS_TLS_CERTIFICATE (chain),
514                         G_TLS_CERTIFICATE_GENERIC_ERROR);
515   g_return_val_if_fail (purpose, G_TLS_CERTIFICATE_GENERIC_ERROR);
516   g_return_val_if_fail (interaction == NULL || G_IS_TLS_INTERACTION (interaction),
517                         G_TLS_CERTIFICATE_GENERIC_ERROR);
518   g_return_val_if_fail (identity == NULL || G_IS_SOCKET_CONNECTABLE (identity),
519                         G_TLS_CERTIFICATE_GENERIC_ERROR);
520   g_return_val_if_fail (error == NULL || *error == NULL, G_TLS_CERTIFICATE_GENERIC_ERROR);
521 
522   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->verify_chain,
523                         G_TLS_CERTIFICATE_GENERIC_ERROR);
524 
525   return G_TLS_DATABASE_GET_CLASS (self)->verify_chain (self,
526                                                         chain,
527                                                         purpose,
528                                                         identity,
529                                                         interaction,
530                                                         flags,
531                                                         cancellable,
532                                                         error);
533 }
534 
535 /**
536  * g_tls_database_verify_chain_async:
537  * @self: a #GTlsDatabase
538  * @chain: a #GTlsCertificate chain
539  * @purpose: the purpose that this certificate chain will be used for.
540  * @identity: (nullable): the expected peer identity
541  * @interaction: (nullable): used to interact with the user if necessary
542  * @flags: additional verify flags
543  * @cancellable: (nullable): a #GCancellable, or %NULL
544  * @callback: callback to call when the operation completes
545  * @user_data: the data to pass to the callback function
546  *
547  * Asynchronously determines the validity of a certificate chain after
548  * looking up and adding any missing certificates to the chain. See
549  * g_tls_database_verify_chain() for more information.
550  *
551  * Since: 2.30
552  */
553 void
g_tls_database_verify_chain_async(GTlsDatabase * self,GTlsCertificate * chain,const gchar * purpose,GSocketConnectable * identity,GTlsInteraction * interaction,GTlsDatabaseVerifyFlags flags,GCancellable * cancellable,GAsyncReadyCallback callback,gpointer user_data)554 g_tls_database_verify_chain_async (GTlsDatabase           *self,
555                                    GTlsCertificate        *chain,
556                                    const gchar            *purpose,
557                                    GSocketConnectable     *identity,
558                                    GTlsInteraction        *interaction,
559                                    GTlsDatabaseVerifyFlags flags,
560                                    GCancellable           *cancellable,
561                                    GAsyncReadyCallback     callback,
562                                    gpointer                user_data)
563 {
564   g_return_if_fail (G_IS_TLS_DATABASE (self));
565   g_return_if_fail (G_IS_TLS_CERTIFICATE (chain));
566   g_return_if_fail (purpose != NULL);
567   g_return_if_fail (interaction == NULL || G_IS_TLS_INTERACTION (interaction));
568   g_return_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable));
569   g_return_if_fail (identity == NULL || G_IS_SOCKET_CONNECTABLE (identity));
570   g_return_if_fail (callback != NULL);
571 
572   g_return_if_fail (G_TLS_DATABASE_GET_CLASS (self)->verify_chain_async);
573   G_TLS_DATABASE_GET_CLASS (self)->verify_chain_async (self,
574                                                        chain,
575                                                        purpose,
576                                                        identity,
577                                                        interaction,
578                                                        flags,
579                                                        cancellable,
580                                                        callback,
581                                                        user_data);
582 }
583 
584 /**
585  * g_tls_database_verify_chain_finish:
586  * @self: a #GTlsDatabase
587  * @result: a #GAsyncResult.
588  * @error: a #GError pointer, or %NULL
589  *
590  * Finish an asynchronous verify chain operation. See
591  * g_tls_database_verify_chain() for more information.
592  *
593  * If @chain is found to be valid, then the return value will be 0. If
594  * @chain is found to be invalid, then the return value will indicate
595  * the problems found. If the function is unable to determine whether
596  * @chain is valid or not (eg, because @cancellable is triggered
597  * before it completes) then the return value will be
598  * %G_TLS_CERTIFICATE_GENERIC_ERROR and @error will be set
599  * accordingly. @error is not set when @chain is successfully analyzed
600  * but found to be invalid.
601  *
602  * Returns: the appropriate #GTlsCertificateFlags which represents the
603  * result of verification.
604  *
605  * Since: 2.30
606  */
607 GTlsCertificateFlags
g_tls_database_verify_chain_finish(GTlsDatabase * self,GAsyncResult * result,GError ** error)608 g_tls_database_verify_chain_finish (GTlsDatabase          *self,
609                                     GAsyncResult          *result,
610                                     GError               **error)
611 {
612   g_return_val_if_fail (G_IS_TLS_DATABASE (self), G_TLS_CERTIFICATE_GENERIC_ERROR);
613   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), G_TLS_CERTIFICATE_GENERIC_ERROR);
614   g_return_val_if_fail (error == NULL || *error == NULL, G_TLS_CERTIFICATE_GENERIC_ERROR);
615   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->verify_chain_finish,
616                         G_TLS_CERTIFICATE_GENERIC_ERROR);
617   return G_TLS_DATABASE_GET_CLASS (self)->verify_chain_finish (self,
618                                                                result,
619                                                                error);
620 }
621 
622 /**
623  * g_tls_database_create_certificate_handle:
624  * @self: a #GTlsDatabase
625  * @certificate: certificate for which to create a handle.
626  *
627  * Create a handle string for the certificate. The database will only be able
628  * to create a handle for certificates that originate from the database. In
629  * cases where the database cannot create a handle for a certificate, %NULL
630  * will be returned.
631  *
632  * This handle should be stable across various instances of the application,
633  * and between applications. If a certificate is modified in the database,
634  * then it is not guaranteed that this handle will continue to point to it.
635  *
636  * Returns: (nullable): a newly allocated string containing the
637  * handle.
638  *
639  * Since: 2.30
640  */
641 gchar*
g_tls_database_create_certificate_handle(GTlsDatabase * self,GTlsCertificate * certificate)642 g_tls_database_create_certificate_handle (GTlsDatabase            *self,
643                                           GTlsCertificate         *certificate)
644 {
645   g_return_val_if_fail (G_IS_TLS_DATABASE (self), NULL);
646   g_return_val_if_fail (G_IS_TLS_CERTIFICATE (certificate), NULL);
647   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->create_certificate_handle, NULL);
648   return G_TLS_DATABASE_GET_CLASS (self)->create_certificate_handle (self,
649                                                                      certificate);
650 }
651 
652 /**
653  * g_tls_database_lookup_certificate_for_handle:
654  * @self: a #GTlsDatabase
655  * @handle: a certificate handle
656  * @interaction: (nullable): used to interact with the user if necessary
657  * @flags: Flags which affect the lookup.
658  * @cancellable: (nullable): a #GCancellable, or %NULL
659  * @error: (nullable): a #GError, or %NULL
660  *
661  * Look up a certificate by its handle.
662  *
663  * The handle should have been created by calling
664  * g_tls_database_create_certificate_handle() on a #GTlsDatabase object of
665  * the same TLS backend. The handle is designed to remain valid across
666  * instantiations of the database.
667  *
668  * If the handle is no longer valid, or does not point to a certificate in
669  * this database, then %NULL will be returned.
670  *
671  * This function can block, use g_tls_database_lookup_certificate_for_handle_async() to perform
672  * the lookup operation asynchronously.
673  *
674  * Returns: (transfer full) (nullable): a newly allocated
675  * #GTlsCertificate, or %NULL. Use g_object_unref() to release the certificate.
676  *
677  * Since: 2.30
678  */
679 GTlsCertificate*
g_tls_database_lookup_certificate_for_handle(GTlsDatabase * self,const gchar * handle,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GError ** error)680 g_tls_database_lookup_certificate_for_handle (GTlsDatabase            *self,
681                                               const gchar             *handle,
682                                               GTlsInteraction         *interaction,
683                                               GTlsDatabaseLookupFlags  flags,
684                                               GCancellable            *cancellable,
685                                               GError                 **error)
686 {
687   g_return_val_if_fail (G_IS_TLS_DATABASE (self), NULL);
688   g_return_val_if_fail (handle != NULL, NULL);
689   g_return_val_if_fail (interaction == NULL || G_IS_TLS_INTERACTION (interaction), NULL);
690   g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), NULL);
691   g_return_val_if_fail (error == NULL || *error == NULL, NULL);
692   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_for_handle, NULL);
693   return G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_for_handle (self,
694                                                                          handle,
695                                                                          interaction,
696                                                                          flags,
697                                                                          cancellable,
698                                                                          error);
699 }
700 
701 
702 /**
703  * g_tls_database_lookup_certificate_for_handle_async:
704  * @self: a #GTlsDatabase
705  * @handle: a certificate handle
706  * @interaction: (nullable): used to interact with the user if necessary
707  * @flags: Flags which affect the lookup.
708  * @cancellable: (nullable): a #GCancellable, or %NULL
709  * @callback: callback to call when the operation completes
710  * @user_data: the data to pass to the callback function
711  *
712  * Asynchronously look up a certificate by its handle in the database. See
713  * g_tls_database_lookup_certificate_for_handle() for more information.
714  *
715  * Since: 2.30
716  */
717 void
g_tls_database_lookup_certificate_for_handle_async(GTlsDatabase * self,const gchar * handle,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GAsyncReadyCallback callback,gpointer user_data)718 g_tls_database_lookup_certificate_for_handle_async (GTlsDatabase            *self,
719                                                     const gchar             *handle,
720                                                     GTlsInteraction         *interaction,
721                                                     GTlsDatabaseLookupFlags  flags,
722                                                     GCancellable            *cancellable,
723                                                     GAsyncReadyCallback      callback,
724                                                     gpointer                 user_data)
725 {
726   g_return_if_fail (G_IS_TLS_DATABASE (self));
727   g_return_if_fail (handle != NULL);
728   g_return_if_fail (interaction == NULL || G_IS_TLS_INTERACTION (interaction));
729   g_return_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable));
730   g_return_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_for_handle_async);
731   G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_for_handle_async (self,
732                                                                                handle,
733                                                                                interaction,
734                                                                                flags,
735                                                                                cancellable,
736                                                                                callback,
737                                                                                user_data);
738 }
739 
740 /**
741  * g_tls_database_lookup_certificate_for_handle_finish:
742  * @self: a #GTlsDatabase
743  * @result: a #GAsyncResult.
744  * @error: a #GError pointer, or %NULL
745  *
746  * Finish an asynchronous lookup of a certificate by its handle. See
747  * g_tls_database_lookup_certificate_for_handle() for more information.
748  *
749  * If the handle is no longer valid, or does not point to a certificate in
750  * this database, then %NULL will be returned.
751  *
752  * Returns: (transfer full): a newly allocated #GTlsCertificate object.
753  * Use g_object_unref() to release the certificate.
754  *
755  * Since: 2.30
756  */
757 GTlsCertificate*
g_tls_database_lookup_certificate_for_handle_finish(GTlsDatabase * self,GAsyncResult * result,GError ** error)758 g_tls_database_lookup_certificate_for_handle_finish (GTlsDatabase            *self,
759                                                      GAsyncResult            *result,
760                                                      GError                 **error)
761 {
762   g_return_val_if_fail (G_IS_TLS_DATABASE (self), NULL);
763   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), NULL);
764   g_return_val_if_fail (error == NULL || *error == NULL, NULL);
765   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_for_handle_finish, NULL);
766   return G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_for_handle_finish (self,
767                                                                                 result,
768                                                                                 error);
769 }
770 
771 /**
772  * g_tls_database_lookup_certificate_issuer:
773  * @self: a #GTlsDatabase
774  * @certificate: a #GTlsCertificate
775  * @interaction: (nullable): used to interact with the user if necessary
776  * @flags: flags which affect the lookup operation
777  * @cancellable: (nullable): a #GCancellable, or %NULL
778  * @error: (nullable): a #GError, or %NULL
779  *
780  * Look up the issuer of @certificate in the database.
781  *
782  * The #GTlsCertificate:issuer property
783  * of @certificate is not modified, and the two certificates are not hooked
784  * into a chain.
785  *
786  * This function can block, use g_tls_database_lookup_certificate_issuer_async() to perform
787  * the lookup operation asynchronously.
788  *
789  * Returns: (transfer full): a newly allocated issuer #GTlsCertificate,
790  * or %NULL. Use g_object_unref() to release the certificate.
791  *
792  * Since: 2.30
793  */
794 GTlsCertificate*
g_tls_database_lookup_certificate_issuer(GTlsDatabase * self,GTlsCertificate * certificate,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GError ** error)795 g_tls_database_lookup_certificate_issuer (GTlsDatabase           *self,
796                                           GTlsCertificate        *certificate,
797                                           GTlsInteraction        *interaction,
798                                           GTlsDatabaseLookupFlags flags,
799                                           GCancellable           *cancellable,
800                                           GError                **error)
801 {
802   g_return_val_if_fail (G_IS_TLS_DATABASE (self), NULL);
803   g_return_val_if_fail (G_IS_TLS_CERTIFICATE (certificate), NULL);
804   g_return_val_if_fail (interaction == NULL || G_IS_TLS_INTERACTION (interaction), NULL);
805   g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), NULL);
806   g_return_val_if_fail (error == NULL || *error == NULL, NULL);
807   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_issuer, NULL);
808   return G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_issuer (self,
809                                                                      certificate,
810                                                                      interaction,
811                                                                      flags,
812                                                                      cancellable,
813                                                                      error);
814 }
815 
816 /**
817  * g_tls_database_lookup_certificate_issuer_async:
818  * @self: a #GTlsDatabase
819  * @certificate: a #GTlsCertificate
820  * @interaction: (nullable): used to interact with the user if necessary
821  * @flags: flags which affect the lookup operation
822  * @cancellable: (nullable): a #GCancellable, or %NULL
823  * @callback: callback to call when the operation completes
824  * @user_data: the data to pass to the callback function
825  *
826  * Asynchronously look up the issuer of @certificate in the database. See
827  * g_tls_database_lookup_certificate_issuer() for more information.
828  *
829  * Since: 2.30
830  */
831 void
g_tls_database_lookup_certificate_issuer_async(GTlsDatabase * self,GTlsCertificate * certificate,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GAsyncReadyCallback callback,gpointer user_data)832 g_tls_database_lookup_certificate_issuer_async (GTlsDatabase           *self,
833                                                 GTlsCertificate        *certificate,
834                                                 GTlsInteraction        *interaction,
835                                                 GTlsDatabaseLookupFlags flags,
836                                                 GCancellable           *cancellable,
837                                                 GAsyncReadyCallback     callback,
838                                                 gpointer                user_data)
839 {
840   g_return_if_fail (G_IS_TLS_DATABASE (self));
841   g_return_if_fail (G_IS_TLS_CERTIFICATE (certificate));
842   g_return_if_fail (interaction == NULL || G_IS_TLS_INTERACTION (interaction));
843   g_return_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable));
844   g_return_if_fail (callback != NULL);
845   g_return_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_issuer_async);
846   G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_issuer_async (self,
847                                                         certificate,
848                                                         interaction,
849                                                         flags,
850                                                         cancellable,
851                                                         callback,
852                                                         user_data);
853 }
854 
855 /**
856  * g_tls_database_lookup_certificate_issuer_finish:
857  * @self: a #GTlsDatabase
858  * @result: a #GAsyncResult.
859  * @error: a #GError pointer, or %NULL
860  *
861  * Finish an asynchronous lookup issuer operation. See
862  * g_tls_database_lookup_certificate_issuer() for more information.
863  *
864  * Returns: (transfer full): a newly allocated issuer #GTlsCertificate,
865  * or %NULL. Use g_object_unref() to release the certificate.
866  *
867  * Since: 2.30
868  */
869 GTlsCertificate*
g_tls_database_lookup_certificate_issuer_finish(GTlsDatabase * self,GAsyncResult * result,GError ** error)870 g_tls_database_lookup_certificate_issuer_finish (GTlsDatabase          *self,
871                                                  GAsyncResult          *result,
872                                                  GError               **error)
873 {
874   g_return_val_if_fail (G_IS_TLS_DATABASE (self), NULL);
875   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), NULL);
876   g_return_val_if_fail (error == NULL || *error == NULL, NULL);
877   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_issuer_finish, NULL);
878   return G_TLS_DATABASE_GET_CLASS (self)->lookup_certificate_issuer_finish (self,
879                                                                 result,
880                                                                 error);
881 }
882 
883 /**
884  * g_tls_database_lookup_certificates_issued_by:
885  * @self: a #GTlsDatabase
886  * @issuer_raw_dn: a #GByteArray which holds the DER encoded issuer DN.
887  * @interaction: (nullable): used to interact with the user if necessary
888  * @flags: Flags which affect the lookup operation.
889  * @cancellable: (nullable): a #GCancellable, or %NULL
890  * @error: (nullable): a #GError, or %NULL
891  *
892  * Look up certificates issued by this issuer in the database.
893  *
894  * This function can block, use g_tls_database_lookup_certificates_issued_by_async() to perform
895  * the lookup operation asynchronously.
896  *
897  * Returns: (transfer full) (element-type GTlsCertificate): a newly allocated list of #GTlsCertificate
898  * objects. Use g_object_unref() on each certificate, and g_list_free() on the release the list.
899  *
900  * Since: 2.30
901  */
902 GList*
g_tls_database_lookup_certificates_issued_by(GTlsDatabase * self,GByteArray * issuer_raw_dn,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GError ** error)903 g_tls_database_lookup_certificates_issued_by (GTlsDatabase           *self,
904                                               GByteArray             *issuer_raw_dn,
905                                               GTlsInteraction        *interaction,
906                                               GTlsDatabaseLookupFlags flags,
907                                               GCancellable           *cancellable,
908                                               GError                **error)
909 {
910   g_return_val_if_fail (G_IS_TLS_DATABASE (self), NULL);
911   g_return_val_if_fail (issuer_raw_dn, NULL);
912   g_return_val_if_fail (interaction == NULL || G_IS_TLS_INTERACTION (interaction), NULL);
913   g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), NULL);
914   g_return_val_if_fail (error == NULL || *error == NULL, NULL);
915   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificates_issued_by, NULL);
916   return G_TLS_DATABASE_GET_CLASS (self)->lookup_certificates_issued_by (self,
917                                                                          issuer_raw_dn,
918                                                                          interaction,
919                                                                          flags,
920                                                                          cancellable,
921                                                                          error);
922 }
923 
924 /**
925  * g_tls_database_lookup_certificates_issued_by_async:
926  * @self: a #GTlsDatabase
927  * @issuer_raw_dn: a #GByteArray which holds the DER encoded issuer DN.
928  * @interaction: (nullable): used to interact with the user if necessary
929  * @flags: Flags which affect the lookup operation.
930  * @cancellable: (nullable): a #GCancellable, or %NULL
931  * @callback: callback to call when the operation completes
932  * @user_data: the data to pass to the callback function
933  *
934  * Asynchronously look up certificates issued by this issuer in the database. See
935  * g_tls_database_lookup_certificates_issued_by() for more information.
936  *
937  * The database may choose to hold a reference to the issuer byte array for the duration
938  * of of this asynchronous operation. The byte array should not be modified during
939  * this time.
940  *
941  * Since: 2.30
942  */
943 void
g_tls_database_lookup_certificates_issued_by_async(GTlsDatabase * self,GByteArray * issuer_raw_dn,GTlsInteraction * interaction,GTlsDatabaseLookupFlags flags,GCancellable * cancellable,GAsyncReadyCallback callback,gpointer user_data)944 g_tls_database_lookup_certificates_issued_by_async (GTlsDatabase           *self,
945                                                     GByteArray             *issuer_raw_dn,
946                                                     GTlsInteraction        *interaction,
947                                                     GTlsDatabaseLookupFlags flags,
948                                                     GCancellable           *cancellable,
949                                                     GAsyncReadyCallback     callback,
950                                                     gpointer                user_data)
951 {
952   g_return_if_fail (G_IS_TLS_DATABASE (self));
953   g_return_if_fail (issuer_raw_dn != NULL);
954   g_return_if_fail (interaction == NULL || G_IS_TLS_INTERACTION (interaction));
955   g_return_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable));
956   g_return_if_fail (callback != NULL);
957   g_return_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificates_issued_by_async);
958   G_TLS_DATABASE_GET_CLASS (self)->lookup_certificates_issued_by_async (self,
959                                                                         issuer_raw_dn,
960                                                                         interaction,
961                                                                         flags,
962                                                                         cancellable,
963                                                                         callback,
964                                                                         user_data);
965 }
966 
967 /**
968  * g_tls_database_lookup_certificates_issued_by_finish:
969  * @self: a #GTlsDatabase
970  * @result: a #GAsyncResult.
971  * @error: a #GError pointer, or %NULL
972  *
973  * Finish an asynchronous lookup of certificates. See
974  * g_tls_database_lookup_certificates_issued_by() for more information.
975  *
976  * Returns: (transfer full) (element-type GTlsCertificate): a newly allocated list of #GTlsCertificate
977  * objects. Use g_object_unref() on each certificate, and g_list_free() on the release the list.
978  *
979  * Since: 2.30
980  */
981 GList*
g_tls_database_lookup_certificates_issued_by_finish(GTlsDatabase * self,GAsyncResult * result,GError ** error)982 g_tls_database_lookup_certificates_issued_by_finish (GTlsDatabase          *self,
983                                                      GAsyncResult          *result,
984                                                      GError               **error)
985 {
986   g_return_val_if_fail (G_IS_TLS_DATABASE (self), NULL);
987   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), NULL);
988   g_return_val_if_fail (error == NULL || *error == NULL, NULL);
989   g_return_val_if_fail (G_TLS_DATABASE_GET_CLASS (self)->lookup_certificates_issued_by_finish, NULL);
990   return G_TLS_DATABASE_GET_CLASS (self)->lookup_certificates_issued_by_finish (self,
991                                                                                 result,
992                                                                                 error);
993 }
994