diff --git a/sm/ChangeLog b/sm/ChangeLog index 9853bd363..89d3fd3a8 100644 --- a/sm/ChangeLog +++ b/sm/ChangeLog @@ -1,3 +1,21 @@ +2002-08-20 Werner Koch + + * gpgsm.c (main): Use the log file only in server mode. + + * import.c (print_imported_summary): New. + (check_and_store): Update the counters, take new argument. + (import_one): Factored out core of gpgsm_import. + (gpgsm_import): Print counters. + (gpgsm_import_files): New. + * gpgsm.c (main): Use the new function for import. + +2002-08-19 Werner Koch + + * decrypt.c (gpgsm_decrypt): Return a better error status token. + * verify.c (gpgsm_verify): Don't error on messages with no signing + time or no message digest. This is only the case for messages + without any signed attributes. + 2002-08-16 Werner Koch * certpath.c: Renamed to .. diff --git a/sm/decrypt.c b/sm/decrypt.c index 44cb54416..012254e22 100644 --- a/sm/decrypt.c +++ b/sm/decrypt.c @@ -327,12 +327,15 @@ gpgsm_decrypt (CTRL ctrl, int in_fd, FILE *out_fp) mode = gcry_cipher_mode_from_oid (algoid); if (!algo || !mode) { + rc = GNUPG_Unsupported_Algorithm; log_error ("unsupported algorithm `%s'\n", algoid? algoid:"?"); if (algoid && !strcmp (algoid, "1.2.840.113549.3.2")) log_info (_("(this is the RC2 algorithm)\n")); + else if (!algoid) + log_info (_("(this does not seem to be an encrypted" + " message)\n")); gpgsm_status2 (ctrl, STATUS_ERROR, "decrypt.algorithm", - gnupg_error_token (rc), algoid, NULL); - rc = GNUPG_Unsupported_Algorithm; + gnupg_error_token (rc), algoid?algoid:"?", NULL); goto leave; } dfparm.algo = algo; diff --git a/sm/gpgsm.c b/sm/gpgsm.c index 28c4cca16..cffb17f5c 100644 --- a/sm/gpgsm.c +++ b/sm/gpgsm.c @@ -229,7 +229,6 @@ static ARGPARSE_OPTS opts[] = { { aLearnCard, "learn-card", 256 ,N_("register a smartcard")}, { aServer, "server", 256, N_("run in server mode")}, { oLogFile, "log-file" ,2, N_("use a log file for the server")}, - { 301, NULL, 0, N_("@\nOptions:\n ") }, @@ -1000,7 +999,7 @@ main ( int argc, char **argv) if (may_coredump && !opt.quiet) log_info (_("WARNING: program may create a core file!\n")); - if (logfile) + if (logfile && cmd == aServer) { log_set_file (logfile); log_set_prefix (NULL, 1|2|4); @@ -1227,13 +1226,7 @@ main ( int argc, char **argv) break; case aImport: - if (!argc) - gpgsm_import (&ctrl, 0); - else - { - for (; argc; argc--, argv++) - gpgsm_import (&ctrl, open_read (*argv)); - } + gpgsm_import_files (&ctrl, argc, argv, open_read); break; case aExport: diff --git a/sm/gpgsm.h b/sm/gpgsm.h index 93983bf10..50590206e 100644 --- a/sm/gpgsm.h +++ b/sm/gpgsm.h @@ -208,6 +208,8 @@ void gpgsm_list_keys (CTRL ctrl, STRLIST names, FILE *fp, unsigned int mode); /*-- import.c --*/ int gpgsm_import (CTRL ctrl, int in_fd); +int gpgsm_import_files (CTRL ctrl, int nfiles, char **files, + int (*of)(const char *fname)); /*-- export.c --*/ void gpgsm_export (CTRL ctrl, STRLIST names, FILE *fp); diff --git a/sm/import.c b/sm/import.c index 6b3e60f8b..231e4c8b0 100644 --- a/sm/import.c +++ b/sm/import.c @@ -34,6 +34,14 @@ #include "keydb.h" #include "i18n.h" +struct stats_s { + unsigned long count; + unsigned long skipped_new_keys; + unsigned long imported; + unsigned long unchanged; +}; + + static void print_imported_status (CTRL ctrl, KsbaCert cert) @@ -45,9 +53,50 @@ print_imported_status (CTRL ctrl, KsbaCert cert) xfree (fpr); } -static void -check_and_store (CTRL ctrl, KsbaCert cert, int depth) + +void +print_imported_summary (CTRL ctrl, struct stats_s *stats) { + char buf[13*25]; + + if (!opt.quiet) + { + log_info (_("total number processed: %lu\n"), stats->count); + if (stats->skipped_new_keys) + log_info(_(" skipped new keys: %lu\n"), stats->skipped_new_keys ); + if (stats->imported) + { + log_info (_(" imported: %lu"), stats->imported ); + log_printf ("\n"); + } + if (stats->unchanged) + log_info (_(" unchanged: %lu\n"), stats->unchanged); + } + + sprintf (buf, "%lu %lu %lu %lu %lu %lu %lu %lu %lu %lu %lu %lu %lu", + stats->count, + 0l, /*stats->no_user_id*/ + stats->imported, + 0l, /*stats->imported_rsa*/ + stats->unchanged, + 0l, /*stats->n_uids*/ + 0l, /*stats->n_subk*/ + 0l, /*stats->n_sigs*/ + 0l, /*stats->n_revoc*/ + 0l, /*stats->secret_read*/ + 0l, /*stats->secret_imported*/ + 0l, /*stats->secret_dups*/ + stats->skipped_new_keys + ); + gpgsm_status (ctrl, STATUS_IMPORT_RES, buf); +} + + + +static void +check_and_store (CTRL ctrl, struct stats_s *stats, KsbaCert cert, int depth) +{ + stats->count++; if ( !gpgsm_basic_cert_check (cert) ) { int existed; @@ -57,7 +106,13 @@ check_and_store (CTRL ctrl, KsbaCert cert, int depth) KsbaCert next = NULL; if (!existed) - print_imported_status (ctrl, cert); + { + print_imported_status (ctrl, cert); + stats->imported++; + } + else + stats->unchanged++; + if (opt.verbose > 1 && existed) { if (depth) @@ -78,7 +133,7 @@ check_and_store (CTRL ctrl, KsbaCert cert, int depth) log_error (_("certificate chain too long\n")); else if (!gpgsm_walk_cert_chain (cert, &next)) { - check_and_store (ctrl, next, depth+1); + check_and_store (ctrl, stats, next, depth+1); ksba_cert_release (next); } } @@ -91,8 +146,9 @@ check_and_store (CTRL ctrl, KsbaCert cert, int depth) -int -gpgsm_import (CTRL ctrl, int in_fd) + +static int +import_one (CTRL ctrl, struct stats_s *stats, int in_fd) { int rc; Base64Context b64reader = NULL; @@ -157,7 +213,7 @@ gpgsm_import (CTRL ctrl, int in_fd) for (i=0; (cert=ksba_cms_get_cert (cms, i)); i++) { - check_and_store (ctrl, cert, 0); + check_and_store (ctrl, stats, cert, 0); ksba_cert_release (cert); cert = NULL; } @@ -181,7 +237,7 @@ gpgsm_import (CTRL ctrl, int in_fd) goto leave; } - check_and_store (ctrl, cert, 0); + check_and_store (ctrl, stats, cert, 0); } else { @@ -195,6 +251,19 @@ gpgsm_import (CTRL ctrl, int in_fd) gpgsm_destroy_reader (b64reader); if (fp) fclose (fp); + return rc; +} + + +int +gpgsm_import (CTRL ctrl, int in_fd) +{ + int rc; + struct stats_s stats; + + memset (&stats, 0, sizeof stats); + rc = import_one (ctrl, &stats, in_fd); + print_imported_summary (ctrl, &stats); /* If we never printed an error message do it now so that a command line invocation will return with an error (log_error keeps a global errorcount) */ @@ -204,5 +273,35 @@ gpgsm_import (CTRL ctrl, int in_fd) } +int +gpgsm_import_files (CTRL ctrl, int nfiles, char **files, + int (*of)(const char *fname)) +{ + int rc = 0; + struct stats_s stats; + + memset (&stats, 0, sizeof stats); + + if (!nfiles) + rc = import_one (ctrl, &stats, 0); + else + { + for (; nfiles && !rc ; nfiles--, files++) + { + int fd = of (*files); + rc = import_one (ctrl, &stats, fd); + close (fd); + if (rc == -1) + rc = 0; + } + } + print_imported_summary (ctrl, &stats); + /* If we never printed an error message do it now so that a command + line invocation will return with an error (log_error keeps a + global errorcount) */ + if (rc && !log_get_errorcount (0)) + log_error (_("error importing certificate: %s\n"), gnupg_strerror (rc)); + return rc; +} diff --git a/sm/verify.c b/sm/verify.c index ba509f464..df7c8bfe8 100644 --- a/sm/verify.c +++ b/sm/verify.c @@ -281,28 +281,37 @@ gpgsm_verify (CTRL ctrl, int in_fd, int data_fd, FILE *out_fp) } err = ksba_cms_get_signing_time (cms, signer, &sigtime); - if (err) + if (err == KSBA_No_Data) + sigtime = 0; + else if (err) { log_error ("error getting signing time: %s\n", ksba_strerror (err)); sigtime = (time_t)-1; } - - err = ksba_cms_get_message_digest (cms, signer, &msgdigest, &msgdigestlen); - if (err) - break; - - algoid = ksba_cms_get_digest_algo (cms, signer); - algo = gcry_md_map_name (algoid); - if (DBG_X509) - log_debug ("signer %d - digest algo: %d\n", signer, algo); - if ( !gcry_md_info (data_md, GCRYCTL_IS_ALGO_ENABLED, &algo, NULL) ) + if (!err) { - log_error ("digest algo %d has not been enabled\n", algo); - goto next_signer; + algoid = ksba_cms_get_digest_algo (cms, signer); + algo = gcry_md_map_name (algoid); + if (DBG_X509) + log_debug ("signer %d - digest algo: %d\n", signer, algo); + if ( !gcry_md_info (data_md, GCRYCTL_IS_ALGO_ENABLED, &algo, NULL) ) + { + log_error ("digest algo %d has not been enabled\n", algo); + goto next_signer; + } } + else if (err == KSBA_No_Data) + { + assert (!msgdigest); + err = 0; + algoid = NULL; + algo = 0; + } + else /* real error */ + break; sigval = ksba_cms_get_sig_val (cms, signer); if (!sigval)