NeoMutt  2021-02-05-666-ge300cd
Teaching an old dog new tricks
DOXYGEN
cryptglue.c
Go to the documentation of this file.
1 
38 #include "config.h"
39 #include <stdbool.h>
40 #include <stdio.h>
41 #include "mutt/lib.h"
42 #include "core/lib.h"
43 #include "cryptglue.h"
44 #include "lib.h"
45 #include "crypt_mod.h"
46 #ifndef CRYPT_BACKEND_GPGME
47 #include "gui/lib.h"
48 #endif
49 #if defined(CRYPT_BACKEND_GPGME) || defined(USE_AUTOCRYPT)
50 #include "config/lib.h"
51 #endif
52 #ifdef USE_AUTOCRYPT
53 #include "email/lib.h"
54 #include "autocrypt/lib.h"
55 #include "crypt_gpgme.h"
56 #include "options.h"
57 #else
58 struct Envelope;
59 #endif
60 
61 struct Address;
62 struct AddressList;
63 
64 #ifdef CRYPT_BACKEND_CLASSIC_PGP
66 #endif
67 
68 #ifdef CRYPT_BACKEND_CLASSIC_SMIME
70 #endif
71 
72 #ifdef CRYPT_BACKEND_GPGME
75 #endif
76 
77 /* If the crypto module identifier by IDENTIFIER has been registered,
78  * call its function FUNC. Do nothing else. This may be used as an
79  * expression. */
80 #define CRYPT_MOD_CALL_CHECK(identifier, func) \
81  (crypto_module_lookup(APPLICATION_##identifier) && \
82  (crypto_module_lookup(APPLICATION_##identifier))->func)
83 
84 /* Call the function FUNC in the crypto module identified by
85  * IDENTIFIER. This may be used as an expression. */
86 #define CRYPT_MOD_CALL(identifier, func) \
87  (*(crypto_module_lookup(APPLICATION_##identifier))->func)
88 
94 void crypt_init(void)
95 {
96 #ifdef CRYPT_BACKEND_GPGME
97  const bool c_crypt_use_gpgme =
98  cs_subset_bool(NeoMutt->sub, "crypt_use_gpgme");
99 #endif
100 #ifdef CRYPT_BACKEND_CLASSIC_PGP
101  if (
102 #ifdef CRYPT_BACKEND_GPGME
103  (!c_crypt_use_gpgme)
104 #else
105  1
106 #endif
107  )
109 #endif
110 
111 #ifdef CRYPT_BACKEND_CLASSIC_SMIME
112  if (
113 #ifdef CRYPT_BACKEND_GPGME
114  (!c_crypt_use_gpgme)
115 #else
116  1
117 #endif
118  )
120 #endif
121 
122 #ifdef CRYPT_BACKEND_GPGME
123  if (c_crypt_use_gpgme)
124  {
127  }
128 #endif
129 
130 #if defined(CRYPT_BACKEND_CLASSIC_PGP) || \
131  defined(CRYPT_BACKEND_CLASSIC_SMIME) || defined(CRYPT_BACKEND_GPGME)
132  if (CRYPT_MOD_CALL_CHECK(PGP, init))
133  CRYPT_MOD_CALL(PGP, init)();
134 
135  if (CRYPT_MOD_CALL_CHECK(SMIME, init))
136  CRYPT_MOD_CALL(SMIME, init)();
137 #endif
138 }
139 
143 void crypt_cleanup(void)
144 {
145  if (CRYPT_MOD_CALL_CHECK(PGP, cleanup))
146  (CRYPT_MOD_CALL(PGP, cleanup))();
147 
148  if (CRYPT_MOD_CALL_CHECK(SMIME, cleanup))
149  (CRYPT_MOD_CALL(SMIME, cleanup))();
150 }
151 
159 {
160  if (((WithCrypto & APPLICATION_PGP) != 0) && (type & APPLICATION_PGP))
161  mutt_message(_("Invoking PGP..."));
162  else if (((WithCrypto & APPLICATION_SMIME) != 0) && (type & APPLICATION_SMIME))
163  mutt_message(_("Invoking S/MIME..."));
164 }
165 
173 {
174  if (((WithCrypto & APPLICATION_PGP) != 0) && (type & APPLICATION_PGP) &&
175  crypto_module_lookup(APPLICATION_PGP))
176  {
177  return true;
178  }
179 
180  if (((WithCrypto & APPLICATION_SMIME) != 0) && (type & APPLICATION_SMIME) &&
181  crypto_module_lookup(APPLICATION_SMIME))
182  {
183  return true;
184  }
185 
186  return false;
187 }
188 
193 {
196 }
197 
202 {
204  return CRYPT_MOD_CALL(PGP, valid_passphrase)();
205 
206  return false;
207 }
208 
212 int crypt_pgp_decrypt_mime(FILE *fp_in, FILE **fp_out, struct Body *b, struct Body **cur)
213 {
214 #ifdef USE_AUTOCRYPT
215  const bool c_autocrypt = cs_subset_bool(NeoMutt->sub, "autocrypt");
216  if (c_autocrypt)
217  {
218  OptAutocryptGpgme = true;
219  int result = pgp_gpgme_decrypt_mime(fp_in, fp_out, b, cur);
220  OptAutocryptGpgme = false;
221  if (result == 0)
222  {
223  b->is_autocrypt = true;
224  return result;
225  }
226  }
227 #endif
228 
230  return CRYPT_MOD_CALL(PGP, decrypt_mime)(fp_in, fp_out, b, cur);
231 
232  return -1;
233 }
234 
240 int crypt_pgp_application_handler(struct Body *b, struct State *s)
241 {
243  return CRYPT_MOD_CALL(PGP, application_handler)(b, s);
244 
245  return -1;
246 }
247 
253 int crypt_pgp_encrypted_handler(struct Body *b, struct State *s)
254 {
255 #ifdef USE_AUTOCRYPT
256  const bool c_autocrypt = cs_subset_bool(NeoMutt->sub, "autocrypt");
257  if (c_autocrypt)
258  {
259  OptAutocryptGpgme = true;
260  int result = pgp_gpgme_encrypted_handler(b, s);
261  OptAutocryptGpgme = false;
262  if (result == 0)
263  {
264  b->is_autocrypt = true;
265  return result;
266  }
267  }
268 #endif
269 
271  return CRYPT_MOD_CALL(PGP, encrypted_handler)(b, s);
272 
273  return -1;
274 }
275 
280 {
283 }
284 
288 bool crypt_pgp_check_traditional(FILE *fp, struct Body *b, bool just_one)
289 {
291  return CRYPT_MOD_CALL(PGP, pgp_check_traditional)(fp, b, just_one);
292 
293  return false;
294 }
295 
299 struct Body *crypt_pgp_traditional_encryptsign(struct Body *a, SecurityFlags flags, char *keylist)
300 {
301  if (CRYPT_MOD_CALL_CHECK(PGP, pgp_traditional_encryptsign))
302  return CRYPT_MOD_CALL(PGP, pgp_traditional_encryptsign)(a, flags, keylist);
303 
304  return NULL;
305 }
306 
311 {
312  if (CRYPT_MOD_CALL_CHECK(PGP, pgp_make_key_attachment))
313  return CRYPT_MOD_CALL(PGP, pgp_make_key_attachment)();
314 
315  return NULL;
316 }
317 
321 char *crypt_pgp_find_keys(struct AddressList *addrlist, bool oppenc_mode)
322 {
324  return CRYPT_MOD_CALL(PGP, find_keys)(addrlist, oppenc_mode);
325 
326  return NULL;
327 }
328 
332 struct Body *crypt_pgp_sign_message(struct Body *a, const struct AddressList *from)
333 {
335  return CRYPT_MOD_CALL(PGP, sign_message)(a, from);
336 
337  return NULL;
338 }
339 
343 struct Body *crypt_pgp_encrypt_message(struct Mailbox *m, struct Email *e,
344  struct Body *a, char *keylist, int sign,
345  const struct AddressList *from)
346 {
347 #ifdef USE_AUTOCRYPT
348  if (e->security & SEC_AUTOCRYPT)
349  {
351  return NULL;
352 
353  OptAutocryptGpgme = true;
354  struct Body *result = pgp_gpgme_encrypt_message(a, keylist, sign, from);
355  OptAutocryptGpgme = false;
356 
357  return result;
358  }
359 #endif
360 
361  if (CRYPT_MOD_CALL_CHECK(PGP, pgp_encrypt_message))
362  return CRYPT_MOD_CALL(PGP, pgp_encrypt_message)(a, keylist, sign, from);
363 
364  return NULL;
365 }
366 
370 void crypt_pgp_invoke_import(const char *fname)
371 {
372  if (CRYPT_MOD_CALL_CHECK(PGP, pgp_invoke_import))
373  CRYPT_MOD_CALL(PGP, pgp_invoke_import)(fname);
374 }
375 
379 int crypt_pgp_verify_one(struct Body *sigbdy, struct State *s, const char *tempf)
380 {
382  return CRYPT_MOD_CALL(PGP, verify_one)(sigbdy, s, tempf);
383 
384  return -1;
385 }
386 
391 {
392  if (CRYPT_MOD_CALL_CHECK(PGP, send_menu))
393  return CRYPT_MOD_CALL(PGP, send_menu)(m, e);
394 
395  return 0;
396 }
397 
401 void crypt_pgp_extract_key_from_attachment(FILE *fp, struct Body *top)
402 {
403  if (CRYPT_MOD_CALL_CHECK(PGP, pgp_extract_key_from_attachment))
404  CRYPT_MOD_CALL(PGP, pgp_extract_key_from_attachment)(fp, top);
405 }
406 
410 void crypt_pgp_set_sender(const char *sender)
411 {
412  if (CRYPT_MOD_CALL_CHECK(PGP, set_sender))
413  CRYPT_MOD_CALL(PGP, set_sender)(sender);
414 }
415 
420 {
421  if (CRYPT_MOD_CALL_CHECK(SMIME, void_passphrase))
422  CRYPT_MOD_CALL(SMIME, void_passphrase)();
423 }
424 
429 {
430  if (CRYPT_MOD_CALL_CHECK(SMIME, valid_passphrase))
431  return CRYPT_MOD_CALL(SMIME, valid_passphrase)();
432 
433  return false;
434 }
435 
439 int crypt_smime_decrypt_mime(FILE *fp_in, FILE **fp_out, struct Body *b, struct Body **cur)
440 {
441  if (CRYPT_MOD_CALL_CHECK(SMIME, decrypt_mime))
442  return CRYPT_MOD_CALL(SMIME, decrypt_mime)(fp_in, fp_out, b, cur);
443 
444  return -1;
445 }
446 
452 int crypt_smime_application_handler(struct Body *b, struct State *s)
453 {
454  if (CRYPT_MOD_CALL_CHECK(SMIME, application_handler))
455  return CRYPT_MOD_CALL(SMIME, application_handler)(b, s);
456 
457  return -1;
458 }
459 
463 void crypt_smime_getkeys(struct Envelope *env)
464 {
465  if (CRYPT_MOD_CALL_CHECK(SMIME, smime_getkeys))
466  CRYPT_MOD_CALL(SMIME, smime_getkeys)(env);
467 }
468 
472 int crypt_smime_verify_sender(struct Mailbox *m, struct Email *e, struct Message *msg)
473 {
474  if (CRYPT_MOD_CALL_CHECK(SMIME, smime_verify_sender))
475  return CRYPT_MOD_CALL(SMIME, smime_verify_sender)(m, e, msg);
476 
477  return 1;
478 }
479 
483 char *crypt_smime_find_keys(struct AddressList *addrlist, bool oppenc_mode)
484 {
485  if (CRYPT_MOD_CALL_CHECK(SMIME, find_keys))
486  return CRYPT_MOD_CALL(SMIME, find_keys)(addrlist, oppenc_mode);
487 
488  return NULL;
489 }
490 
494 struct Body *crypt_smime_sign_message(struct Body *a, const struct AddressList *from)
495 {
497  return CRYPT_MOD_CALL(SMIME, sign_message)(a, from);
498 
499  return NULL;
500 }
501 
505 struct Body *crypt_smime_build_smime_entity(struct Body *a, char *certlist)
506 {
507  if (CRYPT_MOD_CALL_CHECK(SMIME, smime_build_smime_entity))
508  return CRYPT_MOD_CALL(SMIME, smime_build_smime_entity)(a, certlist);
509 
510  return NULL;
511 }
512 
516 void crypt_smime_invoke_import(const char *infile, const char *mailbox)
517 {
518  if (CRYPT_MOD_CALL_CHECK(SMIME, smime_invoke_import))
519  CRYPT_MOD_CALL(SMIME, smime_invoke_import)(infile, mailbox);
520 }
521 
525 int crypt_smime_verify_one(struct Body *sigbdy, struct State *s, const char *tempf)
526 {
527  if (CRYPT_MOD_CALL_CHECK(SMIME, verify_one))
528  return CRYPT_MOD_CALL(SMIME, verify_one)(sigbdy, s, tempf);
529 
530  return -1;
531 }
532 
537 {
538  if (CRYPT_MOD_CALL_CHECK(SMIME, send_menu))
539  return CRYPT_MOD_CALL(SMIME, send_menu)(m, e);
540 
541  return 0;
542 }
543 
547 void crypt_smime_set_sender(const char *sender)
548 {
549  if (CRYPT_MOD_CALL_CHECK(SMIME, set_sender))
550  CRYPT_MOD_CALL(SMIME, set_sender)(sender);
551 }
Convenience wrapper for the gui headers.
bool cs_subset_bool(const struct ConfigSubset *sub, const char *name)
Get a boolean config item by name.
Definition: helpers.c:73
#define WithCrypto
Definition: lib.h:113
The envelope/body of an email.
Definition: email.h:37
int(* encrypted_handler)(struct Body *m, struct State *s)
Definition: crypt_mod.h:124
char * crypt_smime_find_keys(struct AddressList *addrlist, bool oppenc_mode)
Wrapper for CryptModuleSpecs::find_keys()
Definition: cryptglue.c:483
void crypt_cleanup(void)
Clean up backend.
Definition: cryptglue.c:143
int crypt_smime_verify_sender(struct Mailbox *m, struct Email *e, struct Message *msg)
Wrapper for CryptModuleSpecs::smime_verify_sender()
Definition: cryptglue.c:472
Wrapper for PGP/SMIME calls to GPGME.
Structs that make up an email.
Autocrypt end-to-end encryption.
int pgp_gpgme_decrypt_mime(FILE *fp_in, FILE **fp_out, struct Body *b, struct Body **cur)
Implements CryptModuleSpecs::decrypt_mime() -.
Definition: crypt_gpgme.c:2208
Wrapper around crypto functions.
SecurityFlags crypt_pgp_send_menu(struct Mailbox *m, struct Email *e)
Wrapper for CryptModuleSpecs::send_menu()
Definition: cryptglue.c:390
void crypt_pgp_void_passphrase(void)
Wrapper for CryptModuleSpecs::void_passphrase()
Definition: cryptglue.c:192
bool crypt_smime_valid_passphrase(void)
Wrapper for CryptModuleSpecs::valid_passphrase()
Definition: cryptglue.c:428
int(* application_handler)(struct Body *m, struct State *s)
Definition: crypt_mod.h:112
int pgp_gpgme_encrypted_handler(struct Body *a, struct State *s)
Implements CryptModuleSpecs::encrypted_handler() -This handler is passed the application/octet-stream...
Definition: crypt_gpgme.c:3061
void(* void_passphrase)(void)
Definition: crypt_mod.h:73
void crypt_pgp_set_sender(const char *sender)
Wrapper for CryptModuleSpecs::set_sender()
Definition: cryptglue.c:410
#define _(a)
Definition: message.h:28
bool is_autocrypt
Flag autocrypt-decrypted messages for replying.
Definition: body.h:80
An email address.
Definition: address.h:35
WHERE bool OptAutocryptGpgme
(pseudo) use Autocrypt context inside ncrypt/crypt_gpgme.c
Definition: options.h:33
#define CRYPT_MOD_CALL(identifier, func)
Definition: cryptglue.c:86
#define SEC_AUTOCRYPT
(Autocrypt) Message will be, or was Autocrypt encrypt+signed
Definition: lib.h:84
uint16_t SecurityFlags
Flags, e.g. SEC_ENCRYPT.
Definition: lib.h:71
static char * find_keys(struct AddressList *addrlist, unsigned int app, bool oppenc_mode)
Find keys of the recipients of the message.
Definition: crypt_gpgme.c:3826
void crypto_module_register(struct CryptModuleSpecs *specs)
Register a new crypto module.
Definition: crypt_mod.c:51
int crypt_smime_application_handler(struct Body *b, struct State *s)
Wrapper for CryptModuleSpecs::application_handler()
Definition: cryptglue.c:452
Container for Accounts, Notifications.
Definition: neomutt.h:36
The body of an email.
Definition: body.h:34
Convenience wrapper for the config headers.
struct CryptModuleSpecs CryptModSmimeClassic
CLI SMIME - Implements CryptModuleSpecs.
int crypt_pgp_application_handler(struct Body *b, struct State *s)
Wrapper for CryptModuleSpecs::application_handler()
Definition: cryptglue.c:240
void crypt_smime_set_sender(const char *sender)
Wrapper for CryptModuleSpecs::set_sender()
Definition: cryptglue.c:547
struct Body * crypt_smime_sign_message(struct Body *a, const struct AddressList *from)
Wrapper for CryptModuleSpecs::sign_message()
Definition: cryptglue.c:494
struct CryptModuleSpecs CryptModPgpClassic
CLI PGP - Implements CryptModuleSpecs.
Convenience wrapper for the core headers.
int(* decrypt_mime)(FILE *fp_in, FILE **fp_out, struct Body *b, struct Body **cur)
Definition: crypt_mod.h:100
void crypt_smime_void_passphrase(void)
Wrapper for CryptModuleSpecs::void_passphrase()
Definition: cryptglue.c:419
void crypt_pgp_extract_key_from_attachment(FILE *fp, struct Body *top)
Wrapper for CryptModuleSpecs::pgp_extract_key_from_attachment()
Definition: cryptglue.c:401
struct CryptModuleSpecs CryptModPgpGpgme
GPGME PGP - Implements CryptModuleSpecs.
int mutt_autocrypt_set_sign_as_default_key(struct Mailbox *m, struct Email *e)
Set the Autocrypt default key for signing.
Definition: autocrypt.c:712
void crypt_invoke_message(SecurityFlags type)
Display an informative message.
Definition: cryptglue.c:158
#define CRYPT_MOD_CALL_CHECK(identifier, func)
Definition: cryptglue.c:80
#define APPLICATION_SMIME
Use SMIME to encrypt/sign.
Definition: lib.h:88
bool crypt_pgp_check_traditional(FILE *fp, struct Body *b, bool just_one)
Wrapper for CryptModuleSpecs::pgp_check_traditional()
Definition: cryptglue.c:288
#define APPLICATION_PGP
Use PGP to encrypt/sign.
Definition: lib.h:87
SecurityFlags crypt_smime_send_menu(struct Mailbox *m, struct Email *e)
Wrapper for CryptModuleSpecs::send_menu()
Definition: cryptglue.c:536
A local copy of an email.
Definition: mxapi.h:41
void crypt_pgp_invoke_import(const char *fname)
Wrapper for CryptModuleSpecs::pgp_invoke_import()
Definition: cryptglue.c:370
A mailbox.
Definition: mailbox.h:81
void crypt_smime_getkeys(struct Envelope *env)
Wrapper for CryptModuleSpecs::smime_getkeys()
Definition: cryptglue.c:463
void(* cleanup)(void)
Definition: crypt_mod.h:65
void crypt_pgp_invoke_getkeys(struct Address *addr)
Wrapper for CryptModuleSpecs::pgp_invoke_getkeys()
Definition: cryptglue.c:279
struct Body * pgp_gpgme_encrypt_message(struct Body *a, char *keylist, bool sign, const struct AddressList *from)
Implements CryptModuleSpecs::pgp_encrypt_message() -.
Definition: crypt_gpgme.c:1395
int crypt_smime_decrypt_mime(FILE *fp_in, FILE **fp_out, struct Body *b, struct Body **cur)
Wrapper for CryptModuleSpecs::decrypt_mime()
Definition: cryptglue.c:439
void crypt_init(void)
Initialise the crypto backends.
Definition: cryptglue.c:94
SecurityFlags security
bit 0-10: flags, bit 11,12: application, bit 13: traditional pgp See: ncrypt/lib.h pgplib...
Definition: email.h:39
bool(* valid_passphrase)(void)
Definition: crypt_mod.h:86
struct CryptModuleSpecs * crypto_module_lookup(int identifier)
Lookup a crypto module by name.
Definition: crypt_mod.c:65
static int verify_one(struct Body *sigbdy, struct State *s, const char *tempfile, bool is_smime)
Do the actual verification step.
Definition: crypt_gpgme.c:1902
bool crypt_has_module_backend(SecurityFlags type)
Is there a crypto backend for a given type?
Definition: cryptglue.c:172
bool(* pgp_check_traditional)(FILE *fp, struct Body *b, bool just_one)
Definition: crypt_mod.h:223
struct Body * crypt_smime_build_smime_entity(struct Body *a, char *certlist)
Wrapper for CryptModuleSpecs::smime_build_smime_entity()
Definition: cryptglue.c:505
struct Body * crypt_pgp_make_key_attachment(void)
Wrapper for CryptModuleSpecs::pgp_make_key_attachment()
Definition: cryptglue.c:310
char * crypt_pgp_find_keys(struct AddressList *addrlist, bool oppenc_mode)
Wrapper for CryptModuleSpecs::find_keys()
Definition: cryptglue.c:321
void crypt_smime_invoke_import(const char *infile, const char *mailbox)
Wrapper for CryptModuleSpecs::smime_invoke_import()
Definition: cryptglue.c:516
int crypt_pgp_decrypt_mime(FILE *fp_in, FILE **fp_out, struct Body *b, struct Body **cur)
Wrapper for CryptModuleSpecs::decrypt_mime()
Definition: cryptglue.c:212
static struct Body * sign_message(struct Body *a, const struct AddressList *from, bool use_smime)
Sign a message.
Definition: crypt_gpgme.c:1257
struct Body * crypt_pgp_encrypt_message(struct Mailbox *m, struct Email *e, struct Body *a, char *keylist, int sign, const struct AddressList *from)
Wrapper for CryptModuleSpecs::pgp_encrypt_message()
Definition: cryptglue.c:343
struct Body * crypt_pgp_sign_message(struct Body *a, const struct AddressList *from)
Wrapper for CryptModuleSpecs::sign_message()
Definition: cryptglue.c:332
#define mutt_message(...)
Definition: logging.h:87
int crypt_smime_verify_one(struct Body *sigbdy, struct State *s, const char *tempf)
Wrapper for CryptModuleSpecs::verify_one()
Definition: cryptglue.c:525
Keep track when processing files.
Definition: state.h:44
struct CryptModuleSpecs CryptModSmimeGpgme
GPGME SMIME - Implements CryptModuleSpecs.
Handling of global boolean variables.
struct ConfigSubset * sub
Inherited config items.
Definition: neomutt.h:39
Convenience wrapper for the library headers.
int crypt_pgp_encrypted_handler(struct Body *b, struct State *s)
Wrapper for CryptModuleSpecs::encrypted_handler()
Definition: cryptglue.c:253
void(* pgp_invoke_getkeys)(struct Address *addr)
Definition: crypt_mod.h:245
void(* init)(void)
Definition: crypt_mod.h:57
bool crypt_pgp_valid_passphrase(void)
Wrapper for CryptModuleSpecs::valid_passphrase()
Definition: cryptglue.c:201
Register crypto modules.
The header of an Email.
Definition: envelope.h:54
struct Body * crypt_pgp_traditional_encryptsign(struct Body *a, SecurityFlags flags, char *keylist)
Wrapper for CryptModuleSpecs::pgp_traditional_encryptsign()
Definition: cryptglue.c:299
int crypt_pgp_verify_one(struct Body *sigbdy, struct State *s, const char *tempf)
Wrapper for CryptModuleSpecs::verify_one()
Definition: cryptglue.c:379