chiark / gitweb /
gpg agent threading bugs: Add some `xxx' comments.
[gnupg2.git] / agent / cache.c
1 /* cache.c - keep a cache of passphrases
2  * Copyright (C) 2002, 2010 Free Software Foundation, Inc.
3  *
4  * This file is part of GnuPG.
5  *
6  * GnuPG is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * GnuPG is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, see <https://www.gnu.org/licenses/>.
18  */
19
20 #include <config.h>
21
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25 #include <time.h>
26 #include <assert.h>
27 #include <npth.h>
28
29 #include "agent.h"
30
31 /* The size of the encryption key in bytes.  */
32 #define ENCRYPTION_KEYSIZE (128/8)
33
34 /* A mutex used to protect the encryption.  This is required because
35    we use one context to do all encryption and decryption.  */
36 static npth_mutex_t encryption_lock;
37 /* The encryption context.  This is the only place where the
38    encryption key for all cached entries is available.  It would be nice
39    to keep this (or just the key) in some hardware device, for example
40    a TPM.  Libgcrypt could be extended to provide such a service.
41    With the current scheme it is easy to retrieve the cached entries
42    if access to Libgcrypt's memory is available.  The encryption
43    merely avoids grepping for clear texts in the memory.  Nevertheless
44    the encryption provides the necessary infrastructure to make it
45    more secure.  */
46 static gcry_cipher_hd_t encryption_handle;
47
48
49 struct secret_data_s {
50   int  totallen; /* This includes the padding and space for AESWRAP. */
51   char data[1];  /* A string.  */
52 };
53
54 typedef struct cache_item_s *ITEM;
55 struct cache_item_s {
56   ITEM next;
57   time_t created;
58   time_t accessed;
59   int ttl;  /* max. lifetime given in seconds, -1 one means infinite */
60   struct secret_data_s *pw;
61   cache_mode_t cache_mode;
62   char key[1];
63 };
64
65 /* The cache himself.  */
66 static ITEM thecache;
67
68 /* NULL or the last cache key stored by agent_store_cache_hit.  */
69 static char *last_stored_cache_key;
70
71
72 /* This function must be called once to initialize this module. It
73    has to be done before a second thread is spawned.  */
74 void
75 initialize_module_cache (void)
76 {
77   int err;
78
79   err = npth_mutex_init (&encryption_lock, NULL);
80
81   if (err)
82     log_fatal ("error initializing cache module: %s\n", strerror (err));
83 }
84
85
86 void
87 deinitialize_module_cache (void)
88 {
89   gcry_cipher_close (encryption_handle);
90   encryption_handle = NULL;
91 }
92
93
94 /* We do the encryption init on the fly.  We can't do it in the module
95    init code because that is run before we listen for connections and
96    in case we are started on demand by gpg etc. it will only wait for
97    a few seconds to decide whether the agent may now accept
98    connections.  Thus we should get into listen state as soon as
99    possible.  */
100 static gpg_error_t
101 init_encryption (void)
102 {
103   gpg_error_t err;
104   void *key;
105   int res;
106
107   if (encryption_handle)
108     return 0; /* Shortcut - Already initialized.  */
109
110   res = npth_mutex_lock (&encryption_lock);
111   if (res)
112     log_fatal ("failed to acquire cache encryption mutex: %s\n", strerror (res));
113
114   err = gcry_cipher_open (&encryption_handle, GCRY_CIPHER_AES128,
115                           GCRY_CIPHER_MODE_AESWRAP, GCRY_CIPHER_SECURE);
116   if (!err)
117     {
118       key = gcry_random_bytes (ENCRYPTION_KEYSIZE, GCRY_STRONG_RANDOM);
119       if (!key)
120         err = gpg_error_from_syserror ();
121       else
122         {
123           err = gcry_cipher_setkey (encryption_handle, key, ENCRYPTION_KEYSIZE);
124           xfree (key);
125         }
126       if (err)
127         {
128           gcry_cipher_close (encryption_handle);
129           encryption_handle = NULL;
130         }
131     }
132   if (err)
133     log_error ("error initializing cache encryption context: %s\n",
134                gpg_strerror (err));
135
136   res = npth_mutex_unlock (&encryption_lock);
137   if (res)
138     log_fatal ("failed to release cache encryption mutex: %s\n", strerror (res));
139
140   return err? gpg_error (GPG_ERR_NOT_INITIALIZED) : 0;
141 }
142
143
144
145 static void
146 release_data (struct secret_data_s *data)
147 {
148    xfree (data);
149 }
150
151 static gpg_error_t
152 new_data (const char *string, struct secret_data_s **r_data)
153 {
154   gpg_error_t err;
155   struct secret_data_s *d, *d_enc;
156   size_t length;
157   int total;
158   int res;
159
160   *r_data = NULL;
161
162   err = init_encryption ();
163   if (err)
164     return err;
165
166   length = strlen (string) + 1;
167
168   /* We pad the data to 32 bytes so that it get more complicated
169      finding something out by watching allocation patterns.  This is
170      usually not possible but we better assume nothing about our secure
171      storage provider.  To support the AESWRAP mode we need to add 8
172      extra bytes as well. */
173   total = (length + 8) + 32 - ((length+8) % 32);
174
175   d = xtrymalloc_secure (sizeof *d + total - 1);
176   if (!d)
177     return gpg_error_from_syserror ();
178   memcpy (d->data, string, length);
179
180   d_enc = xtrymalloc (sizeof *d_enc + total - 1);
181   if (!d_enc)
182     {
183       err = gpg_error_from_syserror ();
184       xfree (d);
185       return err;
186     }
187
188   d_enc->totallen = total;
189   res = npth_mutex_lock (&encryption_lock);
190   if (res)
191     log_fatal ("failed to acquire cache encryption mutex: %s\n",
192                strerror (res));
193
194   err = gcry_cipher_encrypt (encryption_handle, d_enc->data, total,
195                              d->data, total - 8);
196   xfree (d);
197   res = npth_mutex_unlock (&encryption_lock);
198   if (res)
199     log_fatal ("failed to release cache encryption mutex: %s\n", strerror (res));
200   if (err)
201     {
202       xfree (d_enc);
203       return err;
204     }
205   *r_data = d_enc;
206   return 0;
207 }
208
209
210
211 /* Check whether there are items to expire.  */
212 static void
213 housekeeping (void)
214 {
215   ITEM r, rprev;
216   time_t current = gnupg_get_time ();
217
218   /* First expire the actual data */
219   for (r=thecache; r; r = r->next)
220     {
221       if (r->pw && r->ttl >= 0 && r->accessed + r->ttl < current)
222         {
223           if (DBG_CACHE)
224             log_debug ("  expired '%s' (%ds after last access)\n",
225                        r->key, r->ttl);
226           release_data (r->pw);
227           r->pw = NULL;
228           r->accessed = current;
229         }
230     }
231
232   /* Second, make sure that we also remove them based on the created stamp so
233      that the user has to enter it from time to time. */
234   for (r=thecache; r; r = r->next)
235     {
236       unsigned long maxttl;
237
238       switch (r->cache_mode)
239         {
240         case CACHE_MODE_SSH: maxttl = opt.max_cache_ttl_ssh; break;
241         default: maxttl = opt.max_cache_ttl; break;
242         }
243       if (r->pw && r->created + maxttl < current)
244         {
245           if (DBG_CACHE)
246             log_debug ("  expired '%s' (%lus after creation)\n",
247                        r->key, opt.max_cache_ttl);
248           release_data (r->pw);
249           r->pw = NULL;
250           r->accessed = current;
251         }
252     }
253
254   /* Third, make sure that we don't have too many items in the list.
255      Expire old and unused entries after 30 minutes */
256   for (rprev=NULL, r=thecache; r; )
257     {
258       if (!r->pw && r->ttl >= 0 && r->accessed + 60*30 < current)
259         {
260           ITEM r2 = r->next;
261           if (DBG_CACHE)
262             log_debug ("  removed '%s' (mode %d) (slot not used for 30m)\n",
263                        r->key, r->cache_mode);
264           xfree (r);
265           if (!rprev)
266             thecache = r2;
267           else
268             rprev->next = r2;
269           r = r2;
270         }
271       else
272         {
273           rprev = r;
274           r = r->next;
275         }
276     }
277 }
278
279
280 void
281 agent_flush_cache (void)
282 {
283   ITEM r;
284
285   if (DBG_CACHE)
286     log_debug ("agent_flush_cache\n");
287
288   for (r=thecache; r; r = r->next)
289     {
290       if (r->pw)
291         {
292           if (DBG_CACHE)
293             log_debug ("  flushing '%s'\n", r->key);
294           release_data (r->pw);
295           r->pw = NULL;
296           r->accessed = 0;
297         }
298     }
299 }
300
301
302 /* Compare two cache modes.  */
303 static int
304 cache_mode_equal (cache_mode_t a, cache_mode_t b)
305 {
306   /* CACHE_MODE_ANY matches any mode other than CACHE_MODE_IGNORE.  */
307   return ((a == CACHE_MODE_ANY && b != CACHE_MODE_IGNORE)
308           || (b == CACHE_MODE_ANY && a != CACHE_MODE_IGNORE) || a == b);
309 }
310
311
312 /* Store the string DATA in the cache under KEY and mark it with a
313    maximum lifetime of TTL seconds.  If there is already data under
314    this key, it will be replaced.  Using a DATA of NULL deletes the
315    entry.  A TTL of 0 is replaced by the default TTL and a TTL of -1
316    set infinite timeout.  CACHE_MODE is stored with the cache entry
317    and used to select different timeouts.  */
318 int
319 agent_put_cache (const char *key, cache_mode_t cache_mode,
320                  const char *data, int ttl)
321 {
322   gpg_error_t err = 0;
323   ITEM r;
324
325   if (DBG_CACHE)
326     log_debug ("agent_put_cache '%s' (mode %d) requested ttl=%d\n",
327                key, cache_mode, ttl);
328   housekeeping ();
329
330   if (!ttl)
331     {
332       switch(cache_mode)
333         {
334         case CACHE_MODE_SSH: ttl = opt.def_cache_ttl_ssh; break;
335         default: ttl = opt.def_cache_ttl; break;
336         }
337     }
338   if ((!ttl && data) || cache_mode == CACHE_MODE_IGNORE)
339     return 0;
340
341   for (r=thecache; r; r = r->next)
342     {
343       if (((cache_mode != CACHE_MODE_USER
344             && cache_mode != CACHE_MODE_NONCE)
345            || cache_mode_equal (r->cache_mode, cache_mode))
346           && !strcmp (r->key, key))
347         break;
348     }
349   if (r) /* Replace.  */
350     {
351       if (r->pw)
352         {
353           release_data (r->pw);
354           r->pw = NULL;
355         }
356       if (data)
357         {
358           r->created = r->accessed = gnupg_get_time ();
359           r->ttl = ttl;
360           r->cache_mode = cache_mode;
361           err = new_data (data, &r->pw);
362           if (err)
363             log_error ("error replacing cache item: %s\n", gpg_strerror (err));
364         }
365     }
366   else if (data) /* Insert.  */
367     {
368       r = xtrycalloc (1, sizeof *r + strlen (key));
369       if (!r)
370         err = gpg_error_from_syserror ();
371       else
372         {
373           strcpy (r->key, key);
374           r->created = r->accessed = gnupg_get_time ();
375           r->ttl = ttl;
376           r->cache_mode = cache_mode;
377           err = new_data (data, &r->pw);
378           if (err)
379             xfree (r);
380           else
381             {
382               r->next = thecache;
383               thecache = r;
384             }
385         }
386       if (err)
387         log_error ("error inserting cache item: %s\n", gpg_strerror (err));
388     }
389   return err;
390 }
391
392
393 /* Try to find an item in the cache.  Note that we currently don't
394    make use of CACHE_MODE except for CACHE_MODE_NONCE and
395    CACHE_MODE_USER.  */
396 char *
397 agent_get_cache (const char *key, cache_mode_t cache_mode)
398 {
399   gpg_error_t err;
400   ITEM r;
401   char *value = NULL;
402   int res;
403   int last_stored = 0;
404
405   if (cache_mode == CACHE_MODE_IGNORE)
406     return NULL;
407
408   if (!key)
409     {
410       key = last_stored_cache_key;
411       if (!key)
412         return NULL;
413       last_stored = 1;
414     }
415
416
417   if (DBG_CACHE)
418     log_debug ("agent_get_cache '%s' (mode %d)%s ...\n",
419                key, cache_mode,
420                last_stored? " (stored cache key)":"");
421   housekeeping ();
422
423   for (r=thecache; r; r = r->next)
424     {
425       if (r->pw
426           && ((cache_mode != CACHE_MODE_USER
427                && cache_mode != CACHE_MODE_NONCE)
428               || cache_mode_equal (r->cache_mode, cache_mode))
429           && !strcmp (r->key, key))
430         {
431           /* Note: To avoid races KEY may not be accessed anymore below.  */
432           r->accessed = gnupg_get_time ();
433           if (DBG_CACHE)
434             log_debug ("... hit\n");
435           if (r->pw->totallen < 32)
436             err = gpg_error (GPG_ERR_INV_LENGTH);
437           else if ((err = init_encryption ()))
438             ;
439           else if (!(value = xtrymalloc_secure (r->pw->totallen - 8)))
440             err = gpg_error_from_syserror ();
441           else
442             {
443               res = npth_mutex_lock (&encryption_lock);
444               if (res)
445                 log_fatal ("failed to acquire cache encryption mutex: %s\n",
446                            strerror (res));
447               err = gcry_cipher_decrypt (encryption_handle,
448                                          value, r->pw->totallen - 8,
449                                          r->pw->data, r->pw->totallen);
450               res = npth_mutex_unlock (&encryption_lock);
451               if (res)
452                 log_fatal ("failed to release cache encryption mutex: %s\n",
453                            strerror (res));
454             }
455           if (err)
456             {
457               xfree (value);
458               value = NULL;
459               log_error ("retrieving cache entry '%s' failed: %s\n",
460                          key, gpg_strerror (err));
461             }
462           return value;
463         }
464     }
465   if (DBG_CACHE)
466     log_debug ("... miss\n");
467
468   return NULL;
469 }
470
471
472 /* Store the key for the last successful cache hit.  That value is
473    used by agent_get_cache if the requested KEY is given as NULL.
474    NULL may be used to remove that key. */
475 void
476 agent_store_cache_hit (const char *key)
477 {
478   xfree (last_stored_cache_key);
479   last_stored_cache_key = key? xtrystrdup (key) : NULL;
480 }