Merge branch 'master' into justus/pyme3
[gpgme.git] / src / gpgme.c
1 /* gpgme.c - GnuPG Made Easy.
2    Copyright (C) 2000 Werner Koch (dd9jn)
3    Copyright (C) 2001, 2002, 2003, 2004, 2005, 2007, 2012,
4                  2014, 2015 g10 Code GmbH
5
6    This file is part of GPGME.
7
8    GPGME is free software; you can redistribute it and/or modify it
9    under the terms of the GNU Lesser General Public License as
10    published by the Free Software Foundation; either version 2.1 of
11    the License, or (at your option) any later version.
12
13    GPGME is distributed in the hope that it will be useful, but
14    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 Public
19    License along with this program; if not, see <http://www.gnu.org/licenses/>.
20  */
21
22 #if HAVE_CONFIG_H
23 #include <config.h>
24 #endif
25 #include <stdio.h>
26 #include <stdlib.h>
27 #include <string.h>
28 #include <assert.h>
29 #include <errno.h>
30 #ifdef HAVE_LOCALE_H
31 #include <locale.h>
32 #endif
33
34 #include "util.h"
35 #include "context.h"
36 #include "ops.h"
37 #include "wait.h"
38 #include "debug.h"
39 #include "priv-io.h"
40 #include "sys-util.h"
41
42 \f
43 /* The default locale.  */
44 DEFINE_STATIC_LOCK (def_lc_lock);
45 static char *def_lc_ctype;
46 static char *def_lc_messages;
47
48 \f
49 gpgme_error_t _gpgme_selftest = GPG_ERR_NOT_OPERATIONAL;
50
51 /* Protects all reference counters in result structures.  All other
52    accesses to a result structure are read only.  */
53 DEFINE_STATIC_LOCK (result_ref_lock);
54
55 \f
56 /* Set the global flag NAME to VALUE.  Return 0 on success.  Note that
57    this function does not use gpgme_error and thus a non-zero return
58    value merely means "error".  Certain flags may be set before
59    gpgme_check_version is called.  See the manual for a description of
60    supported flags.  The caller must assure that this function is
61    called only by one thread at a time.  */
62 int
63 gpgme_set_global_flag (const char *name, const char *value)
64 {
65   if (!name || !value)
66     return -1;
67   else if (!strcmp (name, "debug"))
68     return _gpgme_debug_set_debug_envvar (value);
69   else if (!strcmp (name, "disable-gpgconf"))
70     {
71       _gpgme_dirinfo_disable_gpgconf ();
72       return 0;
73     }
74   else if (!strcmp (name, "gpgconf-name"))
75     return _gpgme_set_default_gpgconf_name (value);
76   else if (!strcmp (name, "gpg-name"))
77     return _gpgme_set_default_gpg_name (value);
78   else if (!strcmp (name, "w32-inst-dir"))
79     return _gpgme_set_override_inst_dir (value);
80   else
81     return -1;
82 }
83
84
85 \f
86 /* Create a new context as an environment for GPGME crypto
87    operations.  */
88 gpgme_error_t
89 gpgme_new (gpgme_ctx_t *r_ctx)
90 {
91   gpgme_error_t err;
92   gpgme_ctx_t ctx;
93   TRACE_BEG (DEBUG_CTX, "gpgme_new", r_ctx);
94
95   if (_gpgme_selftest)
96     return TRACE_ERR (_gpgme_selftest);
97
98   if (!r_ctx)
99     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
100
101   ctx = calloc (1, sizeof *ctx);
102   if (!ctx)
103     return TRACE_ERR (gpg_error_from_syserror ());
104
105   INIT_LOCK (ctx->lock);
106
107   err = _gpgme_engine_info_copy (&ctx->engine_info);
108   if (!err && !ctx->engine_info)
109     err = gpg_error (GPG_ERR_NO_ENGINE);
110   if (err)
111     {
112       free (ctx);
113       return TRACE_ERR (err);
114     }
115
116   ctx->keylist_mode = GPGME_KEYLIST_MODE_LOCAL;
117   ctx->include_certs = GPGME_INCLUDE_CERTS_DEFAULT;
118   ctx->protocol = GPGME_PROTOCOL_OpenPGP;
119   ctx->sub_protocol = GPGME_PROTOCOL_DEFAULT;
120   _gpgme_fd_table_init (&ctx->fdt);
121
122   LOCK (def_lc_lock);
123   if (def_lc_ctype)
124     {
125       ctx->lc_ctype = strdup (def_lc_ctype);
126       if (!ctx->lc_ctype)
127         {
128           int saved_err = gpg_error_from_syserror ();
129           UNLOCK (def_lc_lock);
130           _gpgme_engine_info_release (ctx->engine_info);
131           free (ctx);
132           return TRACE_ERR (saved_err);
133         }
134     }
135   else
136     def_lc_ctype = NULL;
137
138   if (def_lc_messages)
139     {
140       ctx->lc_messages = strdup (def_lc_messages);
141       if (!ctx->lc_messages)
142         {
143           int saved_err = gpg_error_from_syserror ();
144           UNLOCK (def_lc_lock);
145           if (ctx->lc_ctype)
146             free (ctx->lc_ctype);
147           _gpgme_engine_info_release (ctx->engine_info);
148           free (ctx);
149           return TRACE_ERR (saved_err);
150         }
151     }
152   else
153     def_lc_messages = NULL;
154   UNLOCK (def_lc_lock);
155
156   *r_ctx = ctx;
157
158   return TRACE_SUC1 ("ctx=%p", ctx);
159 }
160
161
162 gpgme_error_t
163 _gpgme_cancel_with_err (gpgme_ctx_t ctx, gpg_error_t ctx_err,
164                         gpg_error_t op_err)
165 {
166   gpgme_error_t err;
167   struct gpgme_io_event_done_data data;
168
169   TRACE_BEG2 (DEBUG_CTX, "_gpgme_cancel_with_err", ctx, "ctx_err=%i, op_err=%i",
170               ctx_err, op_err);
171
172   if (ctx_err)
173     {
174       err = _gpgme_engine_cancel (ctx->engine);
175       if (err)
176         return TRACE_ERR (err);
177     }
178   else
179     {
180       err = _gpgme_engine_cancel_op (ctx->engine);
181       if (err)
182         return TRACE_ERR (err);
183     }
184
185   data.err = ctx_err;
186   data.op_err = op_err;
187
188   _gpgme_engine_io_event (ctx->engine, GPGME_EVENT_DONE, &data);
189
190   return TRACE_ERR (0);
191 }
192
193
194 /* Cancel a pending asynchronous operation.  */
195 gpgme_error_t
196 gpgme_cancel (gpgme_ctx_t ctx)
197 {
198   gpg_error_t err;
199
200   TRACE_BEG (DEBUG_CTX, "gpgme_cancel", ctx);
201
202   if (!ctx)
203     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
204
205   err = _gpgme_cancel_with_err (ctx, gpg_error (GPG_ERR_CANCELED), 0);
206
207   return TRACE_ERR (err);
208 }
209
210
211 /* Cancel a pending operation asynchronously.  */
212 gpgme_error_t
213 gpgme_cancel_async (gpgme_ctx_t ctx)
214 {
215   TRACE_BEG (DEBUG_CTX, "gpgme_cancel_async", ctx);
216
217   if (!ctx)
218     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
219
220   LOCK (ctx->lock);
221   ctx->canceled = 1;
222   UNLOCK (ctx->lock);
223
224   return TRACE_ERR (0);
225 }
226
227
228 /* Release all resources associated with the given context.  */
229 void
230 gpgme_release (gpgme_ctx_t ctx)
231 {
232   TRACE (DEBUG_CTX, "gpgme_release", ctx);
233
234   if (!ctx)
235     return;
236
237   _gpgme_engine_release (ctx->engine);
238   ctx->engine = NULL;
239   _gpgme_fd_table_deinit (&ctx->fdt);
240   _gpgme_release_result (ctx);
241   _gpgme_signers_clear (ctx);
242   _gpgme_sig_notation_clear (ctx);
243   if (ctx->signers)
244     free (ctx->signers);
245   if (ctx->lc_ctype)
246     free (ctx->lc_ctype);
247   if (ctx->lc_messages)
248     free (ctx->lc_messages);
249   _gpgme_engine_info_release (ctx->engine_info);
250   ctx->engine_info = NULL;
251   DESTROY_LOCK (ctx->lock);
252   free (ctx);
253 }
254
255
256 void
257 gpgme_result_ref (void *result)
258 {
259   struct ctx_op_data *data;
260
261   if (! result)
262     return;
263
264   data = (void*)((char*)result - sizeof (struct ctx_op_data));
265
266   assert (data->magic == CTX_OP_DATA_MAGIC);
267
268   LOCK (result_ref_lock);
269   data->references++;
270   UNLOCK (result_ref_lock);
271 }
272
273
274 void
275 gpgme_result_unref (void *result)
276 {
277   struct ctx_op_data *data;
278
279   if (! result)
280     return;
281
282   data = (void*)((char*)result - sizeof (struct ctx_op_data));
283
284   assert (data->magic == CTX_OP_DATA_MAGIC);
285
286   LOCK (result_ref_lock);
287   if (--data->references)
288     {
289       UNLOCK (result_ref_lock);
290       return;
291     }
292   UNLOCK (result_ref_lock);
293
294   if (data->cleanup)
295     (*data->cleanup) (data->hook);
296   free (data);
297 }
298
299
300 void
301 _gpgme_release_result (gpgme_ctx_t ctx)
302 {
303   struct ctx_op_data *data = ctx->op_data;
304
305   while (data)
306     {
307       struct ctx_op_data *next_data = data->next;
308       data->next = NULL;
309       gpgme_result_unref (data->hook);
310       data = next_data;
311     }
312   ctx->op_data = NULL;
313 }
314
315
316 gpgme_error_t
317 gpgme_set_protocol (gpgme_ctx_t ctx, gpgme_protocol_t protocol)
318 {
319   TRACE_BEG2 (DEBUG_CTX, "gpgme_set_protocol", ctx, "protocol=%i (%s)",
320               protocol, gpgme_get_protocol_name (protocol)
321               ? gpgme_get_protocol_name (protocol) : "invalid");
322
323   if (protocol != GPGME_PROTOCOL_OpenPGP
324       && protocol != GPGME_PROTOCOL_CMS
325       && protocol != GPGME_PROTOCOL_GPGCONF
326       && protocol != GPGME_PROTOCOL_ASSUAN
327       && protocol != GPGME_PROTOCOL_G13
328       && protocol != GPGME_PROTOCOL_UISERVER
329       && protocol != GPGME_PROTOCOL_SPAWN)
330     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
331
332   if (!ctx)
333     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
334
335   if (ctx->protocol != protocol)
336     {
337       /* Shut down the engine when switching protocols.  */
338       if (ctx->engine)
339         {
340           TRACE_LOG1 ("releasing ctx->engine=%p", ctx->engine);
341           _gpgme_engine_release (ctx->engine);
342           ctx->engine = NULL;
343         }
344
345       ctx->protocol = protocol;
346     }
347   return TRACE_ERR (0);
348 }
349
350
351 gpgme_protocol_t
352 gpgme_get_protocol (gpgme_ctx_t ctx)
353 {
354   TRACE2 (DEBUG_CTX, "gpgme_get_protocol", ctx,
355           "ctx->protocol=%i (%s)", ctx->protocol,
356           gpgme_get_protocol_name (ctx->protocol)
357           ? gpgme_get_protocol_name (ctx->protocol) : "invalid");
358
359   return ctx->protocol;
360 }
361
362
363 gpgme_error_t
364 gpgme_set_sub_protocol (gpgme_ctx_t ctx, gpgme_protocol_t protocol)
365 {
366   TRACE2 (DEBUG_CTX, "gpgme_set_sub_protocol", ctx, "protocol=%i (%s)",
367           protocol, gpgme_get_protocol_name (protocol)
368           ? gpgme_get_protocol_name (protocol) : "invalid");
369
370   if (!ctx)
371     return gpg_error (GPG_ERR_INV_VALUE);
372
373   ctx->sub_protocol = protocol;
374   return 0;
375 }
376
377
378 gpgme_protocol_t
379 gpgme_get_sub_protocol (gpgme_ctx_t ctx)
380 {
381   TRACE2 (DEBUG_CTX, "gpgme_get_sub_protocol", ctx,
382           "ctx->sub_protocol=%i (%s)", ctx->sub_protocol,
383           gpgme_get_protocol_name (ctx->sub_protocol)
384           ? gpgme_get_protocol_name (ctx->sub_protocol) : "invalid");
385
386   return ctx->sub_protocol;
387 }
388
389
390 const char *
391 gpgme_get_protocol_name (gpgme_protocol_t protocol)
392 {
393   switch (protocol)
394     {
395     case GPGME_PROTOCOL_OpenPGP:
396       return "OpenPGP";
397
398     case GPGME_PROTOCOL_CMS:
399       return "CMS";
400
401     case GPGME_PROTOCOL_GPGCONF:
402       return "GPGCONF";
403
404     case GPGME_PROTOCOL_ASSUAN:
405       return "Assuan";
406
407     case GPGME_PROTOCOL_G13:
408       return "G13";
409
410     case GPGME_PROTOCOL_UISERVER:
411       return "UIServer";
412
413     case GPGME_PROTOCOL_SPAWN:
414       return "Spawn";
415
416     case GPGME_PROTOCOL_DEFAULT:
417       return "default";
418
419     case GPGME_PROTOCOL_UNKNOWN:
420       return "unknown";
421
422     default:
423       return NULL;
424     }
425 }
426
427 /* Enable or disable the use of an ascii armor for all output.  */
428 void
429 gpgme_set_armor (gpgme_ctx_t ctx, int use_armor)
430 {
431   TRACE2 (DEBUG_CTX, "gpgme_set_armor", ctx, "use_armor=%i (%s)",
432           use_armor, use_armor ? "yes" : "no");
433
434   if (!ctx)
435     return;
436
437   ctx->use_armor = use_armor;
438 }
439
440
441 /* Return the state of the armor flag.  */
442 int
443 gpgme_get_armor (gpgme_ctx_t ctx)
444 {
445   TRACE2 (DEBUG_CTX, "gpgme_get_armor", ctx, "ctx->use_armor=%i (%s)",
446           ctx->use_armor, ctx->use_armor ? "yes" : "no");
447   return ctx->use_armor;
448 }
449
450
451 /* Enable or disable the use of the special textmode.  Textmode is for
452   example used for the RFC2015 signatures; note that the updated RFC
453   3156 mandates that the MUA does some preparations so that textmode
454   is not needed anymore.  */
455 void
456 gpgme_set_textmode (gpgme_ctx_t ctx, int use_textmode)
457 {
458   TRACE2 (DEBUG_CTX, "gpgme_set_textmode", ctx, "use_textmode=%i (%s)",
459           use_textmode, use_textmode ? "yes" : "no");
460
461   if (!ctx)
462     return;
463
464   ctx->use_textmode = use_textmode;
465 }
466
467 /* Return the state of the textmode flag.  */
468 int
469 gpgme_get_textmode (gpgme_ctx_t ctx)
470 {
471   TRACE2 (DEBUG_CTX, "gpgme_get_textmode", ctx, "ctx->use_textmode=%i (%s)",
472           ctx->use_textmode, ctx->use_textmode ? "yes" : "no");
473   return ctx->use_textmode;
474 }
475
476
477 /* Enable offline mode for this context. In offline mode dirmngr
478   will be disabled. */
479 void
480 gpgme_set_offline (gpgme_ctx_t ctx, int offline)
481 {
482   TRACE2 (DEBUG_CTX, "gpgme_set_offline", ctx, "offline=%i (%s)",
483           offline, offline ? "yes" : "no");
484
485   if (!ctx)
486     return;
487
488   ctx->offline = offline;
489 }
490
491 /* Return the state of the offline flag.  */
492 int
493 gpgme_get_offline (gpgme_ctx_t ctx)
494 {
495   TRACE2 (DEBUG_CTX, "gpgme_get_offline", ctx, "ctx->offline=%i (%s)",
496           ctx->offline, ctx->offline ? "yes" : "no");
497   return ctx->offline;
498 }
499
500
501 /* Set the number of certifications to include in an S/MIME message.
502    The default is GPGME_INCLUDE_CERTS_DEFAULT.  -1 means all certs,
503    and -2 means all certs except the root cert.  */
504 void
505 gpgme_set_include_certs (gpgme_ctx_t ctx, int nr_of_certs)
506 {
507   if (!ctx)
508     return;
509
510   if (nr_of_certs == GPGME_INCLUDE_CERTS_DEFAULT)
511     ctx->include_certs = GPGME_INCLUDE_CERTS_DEFAULT;
512   else if (nr_of_certs < -2)
513     ctx->include_certs = -2;
514   else
515     ctx->include_certs = nr_of_certs;
516
517   TRACE2 (DEBUG_CTX, "gpgme_set_include_certs", ctx, "nr_of_certs=%i%s",
518           nr_of_certs, nr_of_certs == ctx->include_certs ? "" : " (-2)");
519 }
520
521
522 /* Get the number of certifications to include in an S/MIME
523    message.  */
524 int
525 gpgme_get_include_certs (gpgme_ctx_t ctx)
526 {
527   TRACE1 (DEBUG_CTX, "gpgme_get_include_certs", ctx, "ctx->include_certs=%i",
528           ctx->include_certs);
529   return ctx->include_certs;
530 }
531
532
533 /* This function changes the default behaviour of the keylisting
534    functions.  MODE is a bitwise-OR of the GPGME_KEYLIST_* flags.  The
535    default mode is GPGME_KEYLIST_MODE_LOCAL.  */
536 gpgme_error_t
537 gpgme_set_keylist_mode (gpgme_ctx_t ctx, gpgme_keylist_mode_t mode)
538 {
539   TRACE1 (DEBUG_CTX, "gpgme_set_keylist_mode", ctx, "keylist_mode=0x%x",
540           mode);
541
542   if (!ctx)
543     return gpg_error (GPG_ERR_INV_VALUE);
544
545   ctx->keylist_mode = mode;
546   return 0;
547 }
548
549 /* This function returns the default behaviour of the keylisting
550    functions.  */
551 gpgme_keylist_mode_t
552 gpgme_get_keylist_mode (gpgme_ctx_t ctx)
553 {
554   TRACE1 (DEBUG_CTX, "gpgme_get_keylist_mode", ctx,
555           "ctx->keylist_mode=0x%x", ctx->keylist_mode);
556   return ctx->keylist_mode;
557 }
558
559
560 /* Set the pinentry mode for CTX to MODE. */
561 gpgme_error_t
562 gpgme_set_pinentry_mode (gpgme_ctx_t ctx, gpgme_pinentry_mode_t mode)
563 {
564   TRACE1 (DEBUG_CTX, "gpgme_set_pinentry_mode", ctx, "pinentry_mode=%u",
565           (unsigned int)mode);
566
567   if (!ctx)
568     return gpg_error (GPG_ERR_INV_VALUE);
569
570   switch (mode)
571     {
572     case GPGME_PINENTRY_MODE_DEFAULT:
573     case GPGME_PINENTRY_MODE_ASK:
574     case GPGME_PINENTRY_MODE_CANCEL:
575     case GPGME_PINENTRY_MODE_ERROR:
576     case GPGME_PINENTRY_MODE_LOOPBACK:
577       break;
578     default:
579       return gpg_error (GPG_ERR_INV_VALUE);
580     }
581
582   ctx->pinentry_mode = mode;
583   return 0;
584 }
585
586
587 /* Get the pinentry mode of CTX.  */
588 gpgme_pinentry_mode_t
589 gpgme_get_pinentry_mode (gpgme_ctx_t ctx)
590 {
591   TRACE1 (DEBUG_CTX, "gpgme_get_pinentry_mode", ctx,
592           "ctx->pinentry_mode=%u", (unsigned int)ctx->pinentry_mode);
593   return ctx->pinentry_mode;
594 }
595
596
597 /* This function sets a callback function to be used to pass a
598    passphrase to gpg.  */
599 void
600 gpgme_set_passphrase_cb (gpgme_ctx_t ctx, gpgme_passphrase_cb_t cb,
601                          void *cb_value)
602 {
603   TRACE2 (DEBUG_CTX, "gpgme_set_passphrase_cb", ctx,
604           "passphrase_cb=%p/%p", cb, cb_value);
605
606   if (!ctx)
607     return;
608
609   ctx->passphrase_cb = cb;
610   ctx->passphrase_cb_value = cb_value;
611 }
612
613
614 /* This function returns the callback function to be used to pass a
615    passphrase to the crypto engine.  */
616 void
617 gpgme_get_passphrase_cb (gpgme_ctx_t ctx, gpgme_passphrase_cb_t *r_cb,
618                          void **r_cb_value)
619 {
620   TRACE2 (DEBUG_CTX, "gpgme_get_passphrase_cb", ctx,
621           "ctx->passphrase_cb=%p/%p",
622           ctx->passphrase_cb, ctx->passphrase_cb_value);
623   if (r_cb)
624     *r_cb = ctx->passphrase_cb;
625   if (r_cb_value)
626     *r_cb_value = ctx->passphrase_cb_value;
627 }
628
629
630 /* This function sets a callback function to be used as a progress
631    indicator.  */
632 void
633 gpgme_set_progress_cb (gpgme_ctx_t ctx, gpgme_progress_cb_t cb, void *cb_value)
634 {
635   TRACE2 (DEBUG_CTX, "gpgme_set_progress_cb", ctx, "progress_cb=%p/%p",
636           cb, cb_value);
637
638   if (!ctx)
639     return;
640
641   ctx->progress_cb = cb;
642   ctx->progress_cb_value = cb_value;
643 }
644
645
646 /* This function returns the callback function to be used as a
647    progress indicator.  */
648 void
649 gpgme_get_progress_cb (gpgme_ctx_t ctx, gpgme_progress_cb_t *r_cb,
650                        void **r_cb_value)
651 {
652   TRACE2 (DEBUG_CTX, "gpgme_get_progress_cb", ctx, "ctx->progress_cb=%p/%p",
653           ctx->progress_cb, ctx->progress_cb_value);
654   if (r_cb)
655     *r_cb = ctx->progress_cb;
656   if (r_cb_value)
657     *r_cb_value = ctx->progress_cb_value;
658 }
659
660
661 /* This function sets a callback function to be used as a status
662    message forwarder.  */
663 void
664 gpgme_set_status_cb (gpgme_ctx_t ctx, gpgme_status_cb_t cb, void *cb_value)
665 {
666   TRACE2 (DEBUG_CTX, "gpgme_set_status_cb", ctx, "status_cb=%p/%p",
667           cb, cb_value);
668
669   if (!ctx)
670     return;
671
672   ctx->status_cb = cb;
673   ctx->status_cb_value = cb_value;
674 }
675
676
677 /* This function returns the callback function to be used as a
678    status message forwarder.  */
679 void
680 gpgme_get_status_cb (gpgme_ctx_t ctx, gpgme_status_cb_t *r_cb,
681                        void **r_cb_value)
682 {
683   TRACE2 (DEBUG_CTX, "gpgme_get_status_cb", ctx, "ctx->status_cb=%p/%p",
684           ctx ? ctx->status_cb : NULL, ctx ? ctx->status_cb_value : NULL);
685
686   if (r_cb)
687     *r_cb = NULL;
688
689   if (r_cb_value)
690     *r_cb_value = NULL;
691
692   if (!ctx || !ctx->status_cb)
693     return;
694
695   if (r_cb)
696     *r_cb = ctx->status_cb;
697   if (r_cb_value)
698     *r_cb_value = ctx->status_cb_value;
699 }
700
701
702 /* Set the I/O callback functions for CTX to IO_CBS.  */
703 void
704 gpgme_set_io_cbs (gpgme_ctx_t ctx, gpgme_io_cbs_t io_cbs)
705 {
706   if (!ctx)
707     return;
708
709   if (io_cbs)
710     {
711       TRACE6 (DEBUG_CTX, "gpgme_set_io_cbs", ctx,
712               "io_cbs=%p (add=%p/%p, remove=%p, event=%p/%p",
713               io_cbs, io_cbs->add, io_cbs->add_priv, io_cbs->remove,
714               io_cbs->event, io_cbs->event_priv);
715       ctx->io_cbs = *io_cbs;
716     }
717   else
718     {
719       TRACE1 (DEBUG_CTX, "gpgme_set_io_cbs", ctx,
720               "io_cbs=%p (default)", io_cbs);
721       ctx->io_cbs.add = NULL;
722       ctx->io_cbs.add_priv = NULL;
723       ctx->io_cbs.remove = NULL;
724       ctx->io_cbs.event = NULL;
725       ctx->io_cbs.event_priv = NULL;
726     }
727 }
728
729
730 /* This function provides access to the internal read function; it is
731    normally not used.  */
732 gpgme_ssize_t
733 gpgme_io_read (int fd, void *buffer, size_t count)
734 {
735   int ret;
736   TRACE_BEG2 (DEBUG_GLOBAL, "gpgme_io_read", fd,
737               "buffer=%p, count=%u", buffer, count);
738
739   ret = _gpgme_io_read (fd, buffer, count);
740
741   return TRACE_SYSRES (ret);
742 }
743
744
745 /* This function provides access to the internal write function.  It
746    is to be used by user callbacks to return data to gpgme.  See
747    gpgme_passphrase_cb_t and gpgme_edit_cb_t.  */
748 gpgme_ssize_t
749 gpgme_io_write (int fd, const void *buffer, size_t count)
750 {
751   int ret;
752   TRACE_BEG2 (DEBUG_GLOBAL, "gpgme_io_write", fd,
753               "buffer=%p, count=%u", buffer, count);
754
755   ret = _gpgme_io_write (fd, buffer, count);
756
757   return TRACE_SYSRES (ret);
758 }
759
760 /* This function provides access to the internal write function.  It
761    is to be used by user callbacks to return data to gpgme.  See
762    gpgme_passphrase_cb_t and gpgme_edit_cb_t.  Note that this is a
763    variant of gpgme_io_write which guarantees that all COUNT bytes are
764    written or an error is return.  Returns: 0 on success or -1 on
765    error and the sets errno. */
766 int
767 gpgme_io_writen (int fd, const void *buffer_arg, size_t count)
768 {
769   const char *buffer = buffer_arg;
770   int ret = 0;
771   TRACE_BEG2 (DEBUG_GLOBAL, "gpgme_io_writen", fd,
772               "buffer=%p, count=%u", buffer, count);
773   while (count)
774     {
775       ret = _gpgme_io_write (fd, buffer, count);
776       if (ret < 0)
777         break;
778       buffer += ret;
779       count -= ret;
780       ret = 0;
781     }
782   return TRACE_SYSRES (ret);
783 }
784
785
786 /* This function returns the callback function for I/O.  */
787 void
788 gpgme_get_io_cbs (gpgme_ctx_t ctx, gpgme_io_cbs_t io_cbs)
789 {
790   TRACE6 (DEBUG_CTX, "gpgme_get_io_cbs", ctx,
791           "io_cbs=%p, ctx->io_cbs.add=%p/%p, .remove=%p, .event=%p/%p",
792           io_cbs, io_cbs->add, io_cbs->add_priv, io_cbs->remove,
793           io_cbs->event, io_cbs->event_priv);
794
795   *io_cbs = ctx->io_cbs;
796 }
797
798 \f
799 /* This function sets the locale for the context CTX, or the default
800    locale if CTX is a null pointer.  */
801 gpgme_error_t
802 gpgme_set_locale (gpgme_ctx_t ctx, int category, const char *value)
803 {
804   int failed = 0;
805   char *new_lc_ctype = NULL;
806   char *new_lc_messages = NULL;
807
808   TRACE_BEG2 (DEBUG_CTX, "gpgme_set_locale", ctx,
809                "category=%i, value=%s", category, value ? value : "(null)");
810
811 #define PREPARE_ONE_LOCALE(lcat, ucat)                          \
812   if (!failed && value                                          \
813       && (category == LC_ALL || category == LC_ ## ucat))       \
814     {                                                           \
815       new_lc_ ## lcat = strdup (value);                         \
816       if (!new_lc_ ## lcat)                                     \
817         failed = 1;                                             \
818     }
819
820 #ifdef LC_CTYPE
821   PREPARE_ONE_LOCALE (ctype, CTYPE);
822 #endif
823 #ifdef LC_MESSAGES
824   PREPARE_ONE_LOCALE (messages, MESSAGES);
825 #endif
826
827   if (failed)
828     {
829       int saved_err = gpg_error_from_syserror ();
830
831       if (new_lc_ctype)
832         free (new_lc_ctype);
833       if (new_lc_messages)
834         free (new_lc_messages);
835
836       return TRACE_ERR (saved_err);
837     }
838
839 #define SET_ONE_LOCALE(lcat, ucat)                      \
840   if (category == LC_ALL || category == LC_ ## ucat)    \
841     {                                                   \
842       if (ctx)                                          \
843         {                                               \
844           if (ctx->lc_ ## lcat)                         \
845             free (ctx->lc_ ## lcat);                    \
846           ctx->lc_ ## lcat = new_lc_ ## lcat;           \
847         }                                               \
848       else                                              \
849         {                                               \
850           if (def_lc_ ## lcat)                          \
851             free (def_lc_ ## lcat);                     \
852           def_lc_ ## lcat = new_lc_ ## lcat;            \
853         }                                               \
854     }
855
856   if (!ctx)
857     LOCK (def_lc_lock);
858 #ifdef LC_CTYPE
859   SET_ONE_LOCALE (ctype, CTYPE);
860 #endif
861 #ifdef LC_MESSAGES
862   SET_ONE_LOCALE (messages, MESSAGES);
863 #endif
864   if (!ctx)
865     UNLOCK (def_lc_lock);
866
867   return TRACE_ERR (0);
868 }
869
870 \f
871 /* Get the information about the configured engines.  A pointer to the
872    first engine in the statically allocated linked list is returned.
873    The returned data is valid until the next gpgme_ctx_set_engine_info.  */
874 gpgme_engine_info_t
875 gpgme_ctx_get_engine_info (gpgme_ctx_t ctx)
876 {
877   TRACE1 (DEBUG_CTX, "gpgme_ctx_get_engine_info", ctx,
878           "ctx->engine_info=%p", ctx->engine_info);
879   return ctx->engine_info;
880 }
881
882
883 /* Set the engine info for the context CTX, protocol PROTO, to the
884    file name FILE_NAME and the home directory HOME_DIR.  */
885 gpgme_error_t
886 gpgme_ctx_set_engine_info (gpgme_ctx_t ctx, gpgme_protocol_t proto,
887                            const char *file_name, const char *home_dir)
888 {
889   gpgme_error_t err;
890   TRACE_BEG4 (DEBUG_CTX, "gpgme_ctx_set_engine_info", ctx,
891               "protocol=%i (%s), file_name=%s, home_dir=%s",
892               proto, gpgme_get_protocol_name (proto)
893               ? gpgme_get_protocol_name (proto) : "unknown",
894               file_name ? file_name : "(default)",
895               home_dir ? home_dir : "(default)");
896
897   if (!ctx)
898     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
899
900   /* Shut down the engine when changing engine info.  */
901   if (ctx->engine)
902     {
903       TRACE_LOG1 ("releasing ctx->engine=%p", ctx->engine);
904       _gpgme_engine_release (ctx->engine);
905       ctx->engine = NULL;
906     }
907   err = _gpgme_set_engine_info (ctx->engine_info, proto,
908                                 file_name, home_dir);
909   return TRACE_ERR (err);
910 }
911
912 \f
913 /* Clear all notation data from the context.  */
914 void
915 _gpgme_sig_notation_clear (gpgme_ctx_t ctx)
916 {
917   gpgme_sig_notation_t notation;
918
919   if (!ctx)
920     return;
921
922   notation = ctx->sig_notations;
923   while (notation)
924     {
925       gpgme_sig_notation_t next_notation = notation->next;
926       _gpgme_sig_notation_free (notation);
927       notation = next_notation;
928     }
929   ctx->sig_notations = NULL;
930 }
931
932 void
933 gpgme_sig_notation_clear (gpgme_ctx_t ctx)
934 {
935   TRACE (DEBUG_CTX, "gpgme_sig_notation_clear", ctx);
936
937   if (!ctx)
938     return;
939
940   _gpgme_sig_notation_clear (ctx);
941 }
942
943
944 /* Add the human-readable notation data with name NAME and value VALUE
945    to the context CTX, using the flags FLAGS.  If NAME is NULL, then
946    VALUE should be a policy URL.  The flag
947    GPGME_SIG_NOTATION_HUMAN_READABLE is forced to be true for notation
948    data, and false for policy URLs.  */
949 gpgme_error_t
950 gpgme_sig_notation_add (gpgme_ctx_t ctx, const char *name,
951                         const char *value, gpgme_sig_notation_flags_t flags)
952 {
953   gpgme_error_t err;
954   gpgme_sig_notation_t notation;
955   gpgme_sig_notation_t *lastp;
956
957   TRACE_BEG3 (DEBUG_CTX, "gpgme_sig_notation_add", ctx,
958               "name=%s, value=%s, flags=0x%x",
959               name ? name : "(null)", value ? value : "(null)",
960               flags);
961
962   if (!ctx)
963     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
964
965   if (name)
966     flags |= GPGME_SIG_NOTATION_HUMAN_READABLE;
967   else
968     flags &= ~GPGME_SIG_NOTATION_HUMAN_READABLE;
969
970   err = _gpgme_sig_notation_create (&notation, name, name ? strlen (name) : 0,
971                                     value, value ? strlen (value) : 0, flags);
972   if (err)
973     return TRACE_ERR (err);
974
975   lastp = &ctx->sig_notations;
976   while (*lastp)
977     lastp = &(*lastp)->next;
978
979   *lastp = notation;
980   return TRACE_ERR (0);
981 }
982
983
984 /* Get the sig notations for this context.  */
985 gpgme_sig_notation_t
986 gpgme_sig_notation_get (gpgme_ctx_t ctx)
987 {
988   if (!ctx)
989     {
990       TRACE (DEBUG_CTX, "gpgme_sig_notation_get", ctx);
991       return NULL;
992     }
993   TRACE1 (DEBUG_CTX, "gpgme_sig_notation_get", ctx,
994           "ctx->sig_notations=%p", ctx->sig_notations);
995
996   return ctx->sig_notations;
997 }
998
999
1000 \f
1001 /* Return a public key algorithm string made of the algorithm and size
1002    or the curve name.  May return NULL on error.  Caller must free the
1003    result using gpgme_free.  */
1004 char *
1005 gpgme_pubkey_algo_string (gpgme_subkey_t subkey)
1006 {
1007   const char *prefix = NULL;
1008   char *result;
1009
1010   if (!subkey)
1011     {
1012       gpg_err_set_errno (EINVAL);
1013       return NULL;
1014     }
1015
1016   switch (subkey->pubkey_algo)
1017     {
1018     case GPGME_PK_RSA:
1019     case GPGME_PK_RSA_E:
1020     case GPGME_PK_RSA_S: prefix = "rsa"; break;
1021     case GPGME_PK_ELG_E: prefix = "elg"; break;
1022     case GPGME_PK_DSA:   prefix = "dsa"; break;
1023     case GPGME_PK_ELG:   prefix = "xxx"; break;
1024     case GPGME_PK_ECC:
1025     case GPGME_PK_ECDH:
1026     case GPGME_PK_ECDSA:
1027     case GPGME_PK_EDDSA: prefix = "";    break;
1028     }
1029
1030   if (prefix && *prefix)
1031     {
1032       char buffer[40];
1033       snprintf (buffer, sizeof buffer, "%s%u", prefix, subkey->length);
1034       result = strdup (buffer);
1035     }
1036   else if (prefix && subkey->curve && *subkey->curve)
1037     result = strdup (subkey->curve);
1038   else if (prefix)
1039     result =  strdup ("E_error");
1040   else
1041     result = strdup  ("unknown");
1042
1043   return result;
1044 }
1045
1046
1047 const char *
1048 gpgme_pubkey_algo_name (gpgme_pubkey_algo_t algo)
1049 {
1050   switch (algo)
1051     {
1052     case GPGME_PK_RSA:   return "RSA";
1053     case GPGME_PK_RSA_E: return "RSA-E";
1054     case GPGME_PK_RSA_S: return "RSA-S";
1055     case GPGME_PK_ELG_E: return "ELG-E";
1056     case GPGME_PK_DSA:   return "DSA";
1057     case GPGME_PK_ECC:   return "ECC";
1058     case GPGME_PK_ELG:   return "ELG";
1059     case GPGME_PK_ECDSA: return "ECDSA";
1060     case GPGME_PK_ECDH:  return "ECDH";
1061     case GPGME_PK_EDDSA: return "EdDSA";
1062     default:             return NULL;
1063     }
1064 }
1065
1066
1067 const char *
1068 gpgme_hash_algo_name (gpgme_hash_algo_t algo)
1069 {
1070   switch (algo)
1071     {
1072     case GPGME_MD_MD5:
1073       return "MD5";
1074
1075     case GPGME_MD_SHA1:
1076       return "SHA1";
1077
1078     case GPGME_MD_RMD160:
1079       return "RIPEMD160";
1080
1081     case GPGME_MD_MD2:
1082       return "MD2";
1083
1084     case GPGME_MD_TIGER:
1085       return "TIGER192";
1086
1087     case GPGME_MD_HAVAL:
1088       return "HAVAL";
1089
1090     case GPGME_MD_SHA256:
1091       return "SHA256";
1092
1093     case GPGME_MD_SHA384:
1094       return "SHA384";
1095
1096     case GPGME_MD_SHA512:
1097       return "SHA512";
1098
1099     case GPGME_MD_SHA224:
1100       return "SHA224";
1101
1102     case GPGME_MD_MD4:
1103       return "MD4";
1104
1105     case GPGME_MD_CRC32:
1106       return "CRC32";
1107
1108     case GPGME_MD_CRC32_RFC1510:
1109       return "CRC32RFC1510";
1110
1111     case GPGME_MD_CRC24_RFC2440:
1112       return "CRC24RFC2440";
1113
1114     default:
1115       return NULL;
1116     }
1117 }