mount does now work in server and standalone mode.
[gnupg.git] / g13 / g13.c
1 /* g13.c - Disk Key management with GnuPG
2  * Copyright (C) 2009 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 <http://www.gnu.org/licenses/>.
18  */
19
20 #include <config.h>
21 #include <stdio.h>
22 #include <stdlib.h>
23 #include <string.h>
24 #include <errno.h>
25 #include <ctype.h>
26 #include <unistd.h>
27 #include <fcntl.h>
28 #include <pth.h>
29
30 #include "g13.h"
31
32 #include <gcrypt.h>
33 #include <assuan.h>
34
35 #include "i18n.h"
36 #include "sysutils.h"
37 #include "gc-opt-flags.h"
38 #include "keyblob.h"
39 #include "server.h"
40 #include "runner.h"
41 #include "create.h"
42 #include "./mount.h"
43
44
45 enum cmd_and_opt_values {
46   aNull = 0,
47   oQuiet        = 'q',
48   oVerbose      = 'v',
49
50   aGPGConfList  = 500,
51   aGPGConfTest,
52   aCreate,
53   aMount,
54   aUmount,
55   aServer,
56
57   oOptions,
58   oDebug,
59   oDebugLevel,
60   oDebugAll,
61   oDebugNone,
62   oDebugWait,
63   oDebugAllowCoreDump,
64   oLogFile,
65   oNoLogFile,
66   oAuditLog,
67
68   oOutput,
69
70   oAgentProgram,
71   oGpgProgram,
72
73   oDisplay,
74   oTTYname,
75   oTTYtype,
76   oLCctype,
77   oLCmessages,
78   oXauthority,
79
80   oStatusFD,
81   oLoggerFD,
82
83   oNoVerbose,
84   oNoSecmemWarn,
85   oNoGreeting,
86   oNoTTY,
87   oNoOptions,
88   oHomedir,
89   oWithColons,
90   oDryRun,
91   oNoDetach,
92
93   oRecipient,
94
95   oNoRandomSeedFile,
96   oFakedSystemTime
97  };
98
99
100 static ARGPARSE_OPTS opts[] = {
101
102   ARGPARSE_group (300, N_("@Commands:\n ")),
103
104   ARGPARSE_c (aCreate, "create", N_("Create a new file system container")),
105   ARGPARSE_c (aMount,  "mount",  N_("Mount a file system container") ),
106   ARGPARSE_c (aUmount, "umount", N_("Unmount a file system container") ),
107   ARGPARSE_c (aServer, "server", N_("Run in server mode")),
108
109   ARGPARSE_c (aGPGConfList, "gpgconf-list", "@"),
110   ARGPARSE_c (aGPGConfTest, "gpgconf-test", "@"),
111
112   ARGPARSE_group (301, N_("@\nOptions:\n ")),
113
114   ARGPARSE_s_s (oRecipient, "recipient", N_("|USER-ID|encrypt for USER-ID")),
115
116   ARGPARSE_s_s (oOutput, "output", N_("|FILE|write output to FILE")),
117   ARGPARSE_s_n (oVerbose, "verbose", N_("verbose")),
118   ARGPARSE_s_n (oQuiet, "quiet",  N_("be somewhat more quiet")),
119   ARGPARSE_s_n (oNoTTY, "no-tty", N_("don't use the terminal at all")),
120   ARGPARSE_s_n (oNoDetach, "no-detach", N_("do not detach from the console")),
121   ARGPARSE_s_s (oLogFile, "log-file",  N_("|FILE|write log output to FILE")),
122   ARGPARSE_s_n (oNoLogFile, "no-log-file", "@"),
123   ARGPARSE_s_i (oLoggerFD, "logger-fd", "@"),
124
125   ARGPARSE_s_s (oAuditLog, "audit-log",
126                 N_("|FILE|write an audit log to FILE")),
127   ARGPARSE_s_n (oDryRun, "dry-run", N_("do not make any changes")),
128
129   ARGPARSE_s_s (oOptions, "options", N_("|FILE|read options from FILE")),
130
131   ARGPARSE_p_u (oDebug, "debug", "@"),
132   ARGPARSE_s_s (oDebugLevel, "debug-level",
133                 N_("|LEVEL|set the debugging level to LEVEL")),
134   ARGPARSE_s_n (oDebugAll, "debug-all", "@"),
135   ARGPARSE_s_n (oDebugNone, "debug-none", "@"),
136   ARGPARSE_s_i (oDebugWait, "debug-wait", "@"),
137   ARGPARSE_s_n (oDebugAllowCoreDump, "debug-allow-core-dump", "@"),
138
139   ARGPARSE_s_i (oStatusFD, "status-fd",
140                 N_("|FD|write status info to this FD")),
141
142   ARGPARSE_group (302, N_(
143   "@\n(See the man page for a complete listing of all commands and options)\n"
144   )),
145
146   ARGPARSE_group (303, N_("@\nExamples:\n\n"
147     " blurb\n"
148                           " blurb\n")),
149
150   /* Hidden options. */
151   ARGPARSE_s_n (oNoVerbose, "no-verbose", "@"),
152   ARGPARSE_s_n (oNoSecmemWarn, "no-secmem-warning", "@"), 
153   ARGPARSE_s_n (oNoGreeting, "no-greeting", "@"),
154   ARGPARSE_s_n (oNoOptions, "no-options", "@"),
155   ARGPARSE_s_s (oHomedir, "homedir", "@"),   
156   ARGPARSE_s_s (oAgentProgram, "agent-program", "@"),
157   ARGPARSE_s_s (oGpgProgram, "gpg-program", "@"),
158   ARGPARSE_s_s (oDisplay,    "display", "@"),
159   ARGPARSE_s_s (oTTYname,    "ttyname", "@"),
160   ARGPARSE_s_s (oTTYtype,    "ttytype", "@"),
161   ARGPARSE_s_s (oLCctype,    "lc-ctype", "@"),
162   ARGPARSE_s_s (oLCmessages, "lc-messages", "@"),
163   ARGPARSE_s_s (oXauthority, "xauthority", "@"),
164   ARGPARSE_s_s (oFakedSystemTime, "faked-system-time", "@"),
165   ARGPARSE_s_n (oWithColons, "with-colons", "@"),
166   ARGPARSE_s_n (oNoRandomSeedFile,  "no-random-seed-file", "@"),
167
168   /* Command aliases.  */
169
170   ARGPARSE_end ()
171 };
172
173
174 /* The timer tick interval used by the idle task.  */
175 #define TIMERTICK_INTERVAL_SEC     (1)
176
177
178 /* Global variable to keep an error count. */
179 int g13_errors_seen = 0;
180
181 /* It is possible that we are currently running under setuid permissions.  */
182 static int maybe_setuid = 1;
183
184 /* Helper to implement --debug-level and --debug.  */
185 static const char *debug_level;
186 static unsigned int debug_value;
187
188 /* Flag to indicate that a shutdown was requested.  */
189 static int shutdown_pending;
190
191 /* The thread id of the idle task.  */
192 static pth_t idle_task_tid;
193
194
195 \f
196 static void set_cmd (enum cmd_and_opt_values *ret_cmd,
197                      enum cmd_and_opt_values new_cmd );
198
199 static void emergency_cleanup (void);
200 static void start_idle_task (void);
201 static void join_idle_task (void);
202
203
204 \f
205 /* Begin Pth wrapper functions. */
206 GCRY_THREAD_OPTION_PTH_IMPL;
207 static int fixed_gcry_pth_init (void)
208 {
209   return pth_self ()? 0 : (pth_init () == FALSE) ? errno : 0;
210 }
211 /* End Pth wrapper functions. */
212
213
214 static const char *
215 my_strusage( int level )
216 {
217   const char *p;
218
219   switch (level)
220     {
221     case 11: p = "g13 (GnuPG)";
222       break;
223     case 13: p = VERSION; break;
224     case 17: p = PRINTABLE_OS_NAME; break;
225     case 19: p = _("Please report bugs to <" PACKAGE_BUGREPORT ">.\n");
226       break;
227     case 1:
228     case 40: p = _("Usage: g13 [options] [files] (-h for help)");
229       break;
230     case 41:
231       p = _("Syntax: g13 [options] [files]\n"
232             "Create, mount or unmount an encrypted file system container\n");
233       break;
234
235     case 31: p = "\nHome: "; break;
236     case 32: p = opt.homedir; break;
237      
238     default: p = NULL; break;
239     }
240   return p;
241 }
242
243
244 static void
245 wrong_args (const char *text)
246 {
247   fputs (_("usage: g13 [options] "), stderr);
248   fputs (text, stderr);
249   putc ('\n', stderr);
250   g13_exit (2);
251 }
252
253
254 /* Setup the debugging.  With a DEBUG_LEVEL of NULL only the active
255    debug flags are propagated to the subsystems.  With DEBUG_LEVEL
256    set, a specific set of debug flags is set; and individual debugging
257    flags will be added on top.  */
258 static void
259 set_debug (void)
260 {
261   if (!debug_level)
262     ;
263   else if (!strcmp (debug_level, "none"))
264     opt.debug = 0;
265   else if (!strcmp (debug_level, "basic"))
266     opt.debug = DBG_ASSUAN_VALUE|DBG_MOUNT_VALUE;
267   else if (!strcmp (debug_level, "advanced"))
268     opt.debug = DBG_ASSUAN_VALUE|DBG_MOUNT_VALUE;
269   else if (!strcmp (debug_level, "expert"))
270     opt.debug = (DBG_ASSUAN_VALUE|DBG_MOUNT_VALUE|DBG_CRYPTO_VALUE);
271   else if (!strcmp (debug_level, "guru"))
272     opt.debug = ~0;
273   else
274     {
275       log_error (_("invalid debug-level `%s' given\n"), debug_level);
276       g13_exit(2);
277     }
278
279   opt.debug |= debug_value;
280
281   if (opt.debug && !opt.verbose)
282     opt.verbose = 1;
283   if (opt.debug)
284     opt.quiet = 0;
285
286   if (opt.debug & DBG_CRYPTO_VALUE )
287     gcry_control (GCRYCTL_SET_DEBUG_FLAGS, 1);
288   gcry_control (GCRYCTL_SET_VERBOSITY, (int)opt.verbose);
289 }
290  
291
292
293 static void
294 set_cmd (enum cmd_and_opt_values *ret_cmd, enum cmd_and_opt_values new_cmd)
295 {
296   enum cmd_and_opt_values cmd = *ret_cmd;
297
298   if (!cmd || cmd == new_cmd)
299     cmd = new_cmd;
300   else 
301     {
302       log_error (_("conflicting commands\n"));
303       g13_exit (2);
304     }
305
306   *ret_cmd = cmd;
307 }
308
309
310 /* Helper to add recipients to a list. */
311 static int
312 add_encryption_key (ctrl_t ctrl, const char *name,
313                     void /*FIXME*/ *keylist, int is_cms)
314 {
315   /* FIXME: Decide whether to add a CMS or OpenPGP key and then add
316      the key to a list.  */
317   /* int rc = foo_add_to_certlist (ctrl, name, 0, recplist, is_encrypt_to); */
318   /* if (rc) */
319   /*   { */
320   /*     if (recp_required) */
321   /*       { */
322   /*         log_error ("can't encrypt to `%s': %s\n", name, gpg_strerror (rc)); */
323   /*         gpgsm_status2 (ctrl, STATUS_INV_RECP, */
324   /*                        get_inv_recpsgnr_code (rc), name, NULL); */
325   /*       } */
326   /*     else */
327   /*       log_info (_("NOTE: won't be able to encrypt to `%s': %s\n"), */
328   /*                 name, gpg_strerror (rc)); */
329   /*   } */
330   return 0; /* Key is good.  */
331 }
332
333
334 int
335 main ( int argc, char **argv)
336 {
337   ARGPARSE_ARGS pargs;
338   int orig_argc;
339   char **orig_argv;
340   gpg_error_t err;
341   const char *fname;
342   int may_coredump;
343   FILE *configfp = NULL;
344   char *configname = NULL;
345   unsigned configlineno;
346   int parse_debug = 0;
347   int no_more_options = 0;
348   int default_config =1;
349   char *logfile = NULL;
350   char *auditlog = NULL;
351   int greeting = 0;
352   int nogreeting = 0;
353   int debug_wait = 0;
354   int use_random_seed = 1;
355   int nodetach = 0;
356   int nokeysetup = 0;
357   enum cmd_and_opt_values cmd = 0;
358   struct server_control_s ctrl;
359   estream_t auditfp = NULL;
360   strlist_t recipients = NULL;
361
362   /*mtrace();*/
363
364   gnupg_reopen_std ("g13");
365   set_strusage (my_strusage);
366   gcry_control (GCRYCTL_SUSPEND_SECMEM_WARN);
367
368   log_set_prefix ("g13", 1);
369
370   /* Make sure that our subsystems are ready.  */
371   i18n_init ();
372   init_common_subsystems ();
373
374   /* Libgcrypt requires us to register the threading model first.
375      Note that this will also do the pth_init. */
376   gcry_threads_pth.init = fixed_gcry_pth_init;
377   err = gcry_control (GCRYCTL_SET_THREAD_CBS, &gcry_threads_pth);
378   if (err)
379     {
380       log_fatal ("can't register GNU Pth with Libgcrypt: %s\n",
381                  gpg_strerror (err));
382     }
383
384   /* Check that the Libgcrypt is suitable.  */
385   if (!gcry_check_version (NEED_LIBGCRYPT_VERSION) )
386     log_fatal (_("%s is too old (need %s, have %s)\n"), "libgcrypt", 
387                NEED_LIBGCRYPT_VERSION, gcry_check_version (NULL) );
388
389   /* Take extra care of the random pool.  */
390   gcry_control (GCRYCTL_USE_SECURE_RNDPOOL);
391
392   may_coredump = disable_core_dumps ();
393   
394   gnupg_init_signals (0, emergency_cleanup);
395   
396   create_dotlock (NULL); /* Register locking cleanup.  */
397
398   opt.homedir = default_homedir ();
399
400   /* First check whether we have a config file on the commandline.  */
401   orig_argc = argc;
402   orig_argv = argv;
403   pargs.argc = &argc;
404   pargs.argv = &argv;
405   pargs.flags= 1|(1<<6);  /* Do not remove the args, ignore version.  */
406   while (arg_parse( &pargs, opts))
407     {
408       if (pargs.r_opt == oDebug || pargs.r_opt == oDebugAll)
409         parse_debug++;
410       else if (pargs.r_opt == oOptions)
411         { /* Yes, there is one, so we do not try the default one but
412              read the config file when it is encountered at the
413              commandline.  */
414           default_config = 0;
415         }
416       else if (pargs.r_opt == oNoOptions)
417         default_config = 0; /* --no-options */
418       else if (pargs.r_opt == oHomedir)
419         opt.homedir = pargs.r.ret_str;
420     }
421
422   /* Initialize the secure memory. */
423   gcry_control (GCRYCTL_INIT_SECMEM, 16384, 0);
424   maybe_setuid = 0;
425
426   /* 
427      Now we are now working under our real uid 
428   */
429
430   /* Setup malloc hooks. */
431   {
432     struct assuan_malloc_hooks malloc_hooks;
433
434     malloc_hooks.malloc = gcry_malloc;
435     malloc_hooks.realloc = gcry_realloc;
436     malloc_hooks.free = gcry_free;
437     assuan_set_malloc_hooks (&malloc_hooks);
438   }
439   
440   /* Prepare libassuan.  */
441   assuan_set_assuan_log_prefix (log_get_prefix (NULL));
442   assuan_set_gpg_err_source (GPG_ERR_SOURCE_DEFAULT);
443
444
445   /* Setup a default control structure for command line mode.  */
446   memset (&ctrl, 0, sizeof ctrl);
447   g13_init_default_ctrl (&ctrl);
448
449   /* Set the default option file */
450   if (default_config )
451     configname = make_filename (opt.homedir, "g13.conf", NULL);
452   
453   argc        = orig_argc;
454   argv        = orig_argv;
455   pargs.argc  = &argc;
456   pargs.argv  = &argv;
457   pargs.flags =  1;  /* Do not remove the args.  */
458
459  next_pass:
460   if (configname)
461     {
462       configlineno = 0;
463       configfp = fopen (configname, "r");
464       if (!configfp)
465         {
466           if (default_config)
467             {
468               if (parse_debug)
469                 log_info (_("NOTE: no default option file `%s'\n"), configname);
470             }
471           else 
472             {
473               log_error (_("option file `%s': %s\n"), 
474                          configname, strerror(errno));
475               g13_exit(2);
476             }
477           xfree (configname);
478           configname = NULL;
479         }
480       if (parse_debug && configname)
481         log_info (_("reading options from `%s'\n"), configname);
482       default_config = 0;
483     }
484   
485   while (!no_more_options 
486          && optfile_parse (configfp, configname, &configlineno, &pargs, opts))
487     {
488       switch (pargs.r_opt)
489         {
490         case aGPGConfList: 
491         case aGPGConfTest: 
492           set_cmd (&cmd, pargs.r_opt);
493           nogreeting = 1;
494           nokeysetup = 1;
495           break;
496
497         case aServer:
498         case aMount:
499         case aUmount:
500           nokeysetup = 1;
501         case aCreate:
502           set_cmd (&cmd, pargs.r_opt);
503           break;
504
505         case oOutput: opt.outfile = pargs.r.ret_str; break;
506
507         case oQuiet: opt.quiet = 1; break;
508         case oNoGreeting: nogreeting = 1; break;
509         case oNoTTY:  break;
510
511         case oDryRun: opt.dry_run = 1; break;
512
513         case oVerbose:
514           opt.verbose++;
515           gcry_control (GCRYCTL_SET_VERBOSITY, (int)opt.verbose);
516           break;
517         case oNoVerbose:
518           opt.verbose = 0;
519           gcry_control (GCRYCTL_SET_VERBOSITY, (int)opt.verbose);
520           break;
521
522         case oLogFile: logfile = pargs.r.ret_str; break;
523         case oNoLogFile: logfile = NULL; break;          
524
525         case oAuditLog: auditlog = pargs.r.ret_str; break;
526
527         case oNoDetach: nodetach = 1; break;
528
529         case oDebug: debug_value |= pargs.r.ret_ulong; break;
530         case oDebugAll: debug_value = ~0; break;
531         case oDebugNone: debug_value = 0; break;
532         case oDebugLevel: debug_level = pargs.r.ret_str; break;
533         case oDebugWait: debug_wait = pargs.r.ret_int; break;
534         case oDebugAllowCoreDump:
535           may_coredump = enable_core_dumps ();
536           break;
537
538         case oStatusFD: ctrl.status_fd = pargs.r.ret_int; break;
539         case oLoggerFD: log_set_fd (pargs.r.ret_int ); break;
540
541         case oNoOptions: break; /* no-options */
542         case oOptions:
543           /* Config files may not be nested (silently ignore them).  */
544           if (!configfp)
545             {
546               xfree(configname);
547               configname = xstrdup (pargs.r.ret_str);
548               goto next_pass;
549             }
550           break;
551
552         case oHomedir: opt.homedir = pargs.r.ret_str; break;
553
554         case oAgentProgram: opt.agent_program = pargs.r.ret_str;  break;
555         case oGpgProgram: opt.gpg_program = pargs.r.ret_str;  break;
556         case oDisplay: opt.display = xstrdup (pargs.r.ret_str); break;
557         case oTTYname: opt.ttyname = xstrdup (pargs.r.ret_str); break;
558         case oTTYtype: opt.ttytype = xstrdup (pargs.r.ret_str); break;
559         case oLCctype: opt.lc_ctype = xstrdup (pargs.r.ret_str); break;
560         case oLCmessages: opt.lc_messages = xstrdup (pargs.r.ret_str); break;
561         case oXauthority: opt.xauthority = xstrdup (pargs.r.ret_str); break;
562           
563         case oFakedSystemTime:
564           {
565             time_t faked_time = isotime2epoch (pargs.r.ret_str); 
566             if (faked_time == (time_t)(-1))
567               faked_time = (time_t)strtoul (pargs.r.ret_str, NULL, 10);
568             gnupg_set_time (faked_time, 0);
569           }
570           break;
571
572         case oNoSecmemWarn: gcry_control (GCRYCTL_DISABLE_SECMEM_WARN); break;
573
574         case oNoRandomSeedFile: use_random_seed = 0; break;
575
576         case oRecipient: /* Store the encryption key.  */
577           add_to_strlist (&recipients, pargs.r.ret_str);
578           break;
579
580
581         default: 
582           pargs.err = configfp? ARGPARSE_PRINT_WARNING:ARGPARSE_PRINT_ERROR; 
583           break;
584         }
585     }
586
587   if (configfp)
588     {
589       fclose (configfp);
590       configfp = NULL;
591       /* Keep a copy of the config filename. */
592       opt.config_filename = configname;
593       configname = NULL;
594       goto next_pass;
595     }
596   xfree (configname);
597   configname = NULL;
598
599   if (!opt.config_filename)
600     opt.config_filename = make_filename (opt.homedir, "g13.conf", NULL);
601
602   if (log_get_errorcount(0))
603     g13_exit(2);
604
605   /* Now that we have the options parsed we need to update the default
606      control structure.  */
607   g13_init_default_ctrl (&ctrl);
608
609   if (nogreeting)
610     greeting = 0;
611   
612   if (greeting)
613     {
614       fprintf (stderr, "%s %s; %s\n",
615                strusage(11), strusage(13), strusage(14) );
616       fprintf (stderr, "%s\n", strusage(15) );
617     }
618
619   if (may_coredump && !opt.quiet)
620     log_info (_("WARNING: program may create a core file!\n"));
621
622   if (logfile)
623     {
624       log_set_file (logfile);
625       log_set_prefix (NULL, 1|2|4);
626     }
627
628   if (gnupg_faked_time_p ())
629     {
630       gnupg_isotime_t tbuf;
631
632       log_info (_("WARNING: running with faked system time: "));
633       gnupg_get_isotime (tbuf);
634       dump_isotime (tbuf);
635       log_printf ("\n");
636     }
637
638   /* Print any pending secure memory warnings.  */
639   gcry_control (GCRYCTL_RESUME_SECMEM_WARN);
640
641   /* Setup the debug flags for all subsystems.  */
642   set_debug ();
643
644   /* Install a regular exit handler to make real sure that the secure
645      memory gets wiped out.  */
646   if (atexit (emergency_cleanup))
647     {
648       log_error ("atexit failed\n");
649       g13_exit (2);
650     }
651
652   /* Terminate if we found any error until now.  */
653   if (log_get_errorcount(0))
654     g13_exit (2);
655   
656   /* Set the standard GnuPG random seed file.  */
657   if (use_random_seed) 
658     {
659       char *p = make_filename (opt.homedir, "random_seed", NULL);
660       gcry_control (GCRYCTL_SET_RANDOM_SEED_FILE, p);
661       xfree(p);
662     }
663   
664   /* Store given filename into FNAME. */
665   fname = argc? *argv : NULL;
666
667   /* Parse all given encryption keys.  This does a lookup of the keys
668      and stops if any of the given keys was not found. */
669   if (!nokeysetup)
670     {
671       strlist_t sl;
672       int failed = 0;
673       
674       for (sl = recipients; sl; sl = sl->next)
675         if (add_encryption_key (&ctrl, sl->d, NULL /* FIXME*/, 0))
676           failed = 1;
677       if (failed)
678         g13_exit (1);
679     }
680   
681   /* Dispatch command.  */
682   switch (cmd)
683     {
684     case aGPGConfList: 
685       { /* List options and default values in the GPG Conf format.  */
686         char *config_filename_esc = percent_escape (opt.config_filename, NULL);
687
688         printf ("gpgconf-g13.conf:%lu:\"%s\n",
689                 GC_OPT_FLAG_DEFAULT, config_filename_esc);
690         xfree (config_filename_esc);
691
692         printf ("verbose:%lu:\n", GC_OPT_FLAG_NONE);
693         printf ("quiet:%lu:\n", GC_OPT_FLAG_NONE);
694         printf ("debug-level:%lu:\"none:\n", GC_OPT_FLAG_DEFAULT);
695         printf ("log-file:%lu:\n", GC_OPT_FLAG_NONE);
696       }
697       break;
698     case aGPGConfTest:
699       /* This is merely a dummy command to test whether the
700          configuration file is valid.  */
701       break;
702
703     case aServer:
704       {
705         start_idle_task ();
706         err = g13_server (&ctrl);
707         if (err)
708           log_error ("server exited with error: %s <%s>\n",
709                      gpg_strerror (err), gpg_strsource (err));
710       }
711       break;
712
713     case aCreate: /* Create a new container. */
714       {
715         if (argc != 1) 
716           wrong_args ("--create filename");
717         start_idle_task ();
718         err = g13_create_container (&ctrl, argv[0]);
719         if (err)
720           log_error ("error creating a new container: %s <%s>\n",
721                      gpg_strerror (err), gpg_strsource (err));
722       }
723       break;
724
725     case aMount: /* Mount a container. */
726       {
727         if (argc != 1 && argc != 2 ) 
728           wrong_args ("--mount filename [mountpoint]");
729         start_idle_task ();
730         err = g13_mount_container (&ctrl, argv[0], argc == 2?argv[1]:NULL);
731         if (err)
732           log_error ("error mounting container `%s': %s <%s>\n",
733                      *argv, gpg_strerror (err), gpg_strsource (err));
734       }
735       break;
736
737     default:
738       log_error (_("invalid command (there is no implicit command)\n"));
739       break;
740     }
741
742   if (!err)
743     join_idle_task ();
744
745   /* Print the audit result if needed.  */
746   if (auditlog && auditfp)
747     {
748       /* audit_print_result (ctrl.audit, auditfp, 0); */
749       /* audit_release (ctrl.audit); */
750       ctrl.audit = NULL;
751       es_fclose (auditfp);
752     }
753   
754   /* Cleanup.  */
755   g13_exit (0);
756   return 8; /*NOTREACHED*/
757 }
758
759
760 /* Note: This function is used by signal handlers!. */
761 static void
762 emergency_cleanup (void)
763 {
764   gcry_control (GCRYCTL_TERM_SECMEM );
765 }
766
767
768 void
769 g13_exit (int rc)
770 {
771   gcry_control (GCRYCTL_UPDATE_RANDOM_SEED_FILE);
772   if (opt.debug & DBG_MEMSTAT_VALUE)
773     {
774       gcry_control( GCRYCTL_DUMP_MEMORY_STATS );
775       gcry_control( GCRYCTL_DUMP_RANDOM_STATS );
776     }
777   if (opt.debug)
778     gcry_control (GCRYCTL_DUMP_SECMEM_STATS );
779   emergency_cleanup ();
780   rc = rc? rc : log_get_errorcount(0)? 2 : g13_errors_seen? 1 : 0;
781   exit (rc);
782 }
783
784
785 /* Store defaults into the per-connection CTRL object.  */
786 void
787 g13_init_default_ctrl (struct server_control_s *ctrl)
788 {
789   ctrl->conttype = CONTTYPE_ENCFS;
790 }
791
792
793 /* This function is called for each signal we catch.  It is run in the
794    main context or the one of a Pth thread and thus it is not
795    restricted in what it may do.  */
796 static void
797 handle_signal (int signo)
798 {
799   switch (signo)
800     {
801 #ifndef HAVE_W32_SYSTEM
802     case SIGHUP:
803       log_info ("SIGHUP received - re-reading configuration\n");
804       /* Fixme:  Not yet implemented.  */
805       break;
806       
807     case SIGUSR1:
808       log_info ("SIGUSR1 received - printing internal information:\n");
809       pth_ctrl (PTH_CTRL_DUMPSTATE, log_get_stream ());
810       break;
811
812     case SIGUSR2:
813       log_info ("SIGUSR2 received - no action defined\n");
814       break;
815
816     case SIGTERM:
817       if (!shutdown_pending)
818         log_info ("SIGTERM received - shutting down ...\n");
819       else
820         log_info ("SIGTERM received - still %u runners active\n",
821                   runner_get_threads ());
822       shutdown_pending++;
823       if (shutdown_pending > 2)
824         {
825           log_info ("shutdown forced\n");
826           log_info ("%s %s stopped\n", strusage(11), strusage(13) );
827           g13_exit (0);
828         }
829       break;
830       
831     case SIGINT:
832       log_info ("SIGINT received - immediate shutdown\n");
833       log_info( "%s %s stopped\n", strusage(11), strusage(13));
834       g13_exit (0);
835       break;
836 #endif /*!HAVE_W32_SYSTEM*/
837       
838     default:
839       log_info ("signal %d received - no action defined\n", signo);
840     }
841 }
842
843
844 /* This ticker function is called about every TIMERTICK_INTERVAL_SEC
845    seconds. */
846 static void
847 handle_tick (void)
848 {
849   /* log_debug ("TICK\n"); */
850 }
851
852
853 /* The idle task.  We use a separate thread to do idle stuff and to
854    catch signals.  */
855 static void *
856 idle_task (void *dummy_arg)
857 {
858   sigset_t sigs;       /* The set of signals we want to catch.  */
859   pth_event_t ev;      /* The main event to catch signals.  */
860   pth_event_t time_ev; /* The time event.  */
861   int signo;           /* The number of a raised signal is stored here.  */
862
863   (void)dummy_arg;
864
865   /* Create the event to catch the signals. */
866 #ifndef HAVE_W32_SYSTEM
867   sigemptyset (&sigs );
868   sigaddset (&sigs, SIGHUP);
869   sigaddset (&sigs, SIGUSR1);
870   sigaddset (&sigs, SIGUSR2);
871   sigaddset (&sigs, SIGINT);
872   sigaddset (&sigs, SIGTERM);
873   pth_sigmask (SIG_UNBLOCK, &sigs, NULL);
874 #else
875   sigs = 0;
876 #endif
877   ev = pth_event (PTH_EVENT_SIGS, &sigs, &signo);
878
879   /* The time event neds to computed n tghe fly.  */
880   time_ev = NULL;
881
882   for (;;)
883     {
884       /* The shutdown flag allows us to terminate the idle task.  */
885       if (shutdown_pending)
886         {
887           runner_cancel_all ();
888
889           if (!runner_get_threads ())
890             break; /* ready */
891         }
892
893       /* Create a timeout event if needed.  To help with power saving
894          we syncronize the ticks to the next full second.  */
895       if (!time_ev)
896         {
897           pth_time_t nexttick;
898
899           nexttick = pth_timeout (TIMERTICK_INTERVAL_SEC, 0);
900           if (nexttick.tv_usec > 10)  /* Use a 10 usec threshhold.  */
901             {
902               nexttick.tv_sec++;
903               nexttick.tv_usec = 0;
904             }
905           time_ev = pth_event (PTH_EVENT_TIME, nexttick);
906         }
907
908       pth_event_concat (ev, time_ev, NULL);
909       pth_wait (ev);
910       pth_event_isolate (time_ev);
911
912       if (pth_event_occurred (ev))
913         {
914           handle_signal (signo);
915         }
916
917       if (time_ev && pth_event_occurred (time_ev))
918         {
919           pth_event_free (time_ev, PTH_FREE_ALL);
920           time_ev = NULL;
921           handle_tick ();
922         }
923     }
924
925   pth_event_free (ev, PTH_FREE_ALL);
926   if (time_ev)
927     pth_event_free (time_ev, PTH_FREE_ALL);
928   log_info (_("%s %s stopped\n"), strusage(11), strusage(13));
929   return NULL;
930 }
931
932
933 /* Start the idle task.   */
934 static void
935 start_idle_task (void)
936 {
937   pth_attr_t tattr;
938   pth_t tid;
939   
940   tattr = pth_attr_new ();
941   pth_attr_set (tattr, PTH_ATTR_JOINABLE, 1);
942   pth_attr_set (tattr, PTH_ATTR_STACK_SIZE, 64*1024);
943   pth_attr_set (tattr, PTH_ATTR_NAME, "idle-task");
944   
945   tid = pth_spawn (tattr, idle_task, NULL);
946   if (!tid)
947     {
948       log_fatal ("error starting idle task: %s\n", 
949                  gpg_strerror (gpg_error_from_syserror ()));
950       return; /*NOTREACHED*/
951     }
952   idle_task_tid = tid;
953   pth_attr_destroy (tattr);
954 }
955
956
957 /* Wait for the idle task to finish.  */
958 static void
959 join_idle_task (void)
960 {
961   if (idle_task_tid)
962     {
963       if (!pth_join (idle_task_tid, NULL))
964         log_error ("waiting for idle task thread failed: %s\n",
965                    gpg_strerror (gpg_error_from_syserror ()));
966     }
967 }
968