added option export V0-2-6
authorWerner Koch <wk@gnupg.org>
Fri, 13 Feb 1998 20:58:50 +0000 (20:58 +0000)
committerWerner Koch <wk@gnupg.org>
Fri, 13 Feb 1998 20:58:50 +0000 (20:58 +0000)
43 files changed:
ChangeLog
INSTALL
Makefile.am
Makefile.in
NEWS
README
THANKS
TODO
VERSION
checks/checkit
cipher/ChangeLog [new file with mode: 0644]
cipher/Makefile.in
configure.in
g10/ChangeLog [new file with mode: 0644]
g10/Makefile.in
g10/encode.c
g10/export.c
g10/g10.c
g10/import.c
g10/kbnode.c
g10/keydb.h
g10/keygen.c
g10/parse-packet.c
g10/pubkey-enc.c
g10/ringedit.c
g10/sign.c
include/ChangeLog [new file with mode: 0644]
include/distfiles
include/util.h
mpi/ChangeLog [new file with mode: 0644]
mpi/Makefile.in
mpi/mpicoder.c
mpi/mpiutil.c
po/ChangeLog
scripts/mkdiff
tools/ChangeLog [new file with mode: 0644]
tools/Makefile.in
util/ChangeLog [new file with mode: 0644]
util/Makefile.in
util/argparse.c
util/iobuf.c
util/logger.c
zlib/Makefile.am

index 1d25265..ad76449 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,5 @@
-Tue Feb 10 11:57:23 1998  Werner Koch  (wk@frodo)
-
-       * ddd/hhhh:
+Fri Feb 13 19:43:41 1998  Werner Koch  (wk@isil.d.shuttle.de)
 
+       * configure.in : Fixed zlib stuff
+       * Makefile.am: Likewise
 
diff --git a/INSTALL b/INSTALL
index c524222..13ab8a5 100644 (file)
--- a/INSTALL
+++ b/INSTALL
@@ -1,3 +1,50 @@
+
+Please read the Basic Installation section somewhere below.
+
+Configure options for G10
+=========================
+
+--with-zlib        Forces usage of the local zlib sources. Default is
+                   to use the (sahred) library of the system.
+
+--without-nls      Disable NLS support
+
+--enable-m-debug    Compile with the integrated malloc debugging stuff.
+                   This makes the program slower but is checks every
+                   free operation and can be used to create statistics
+                   of memory usage. If this option is used the program
+                   option "--debug 32" displays every call to a a malloc
+                   function (this makes the program *really* slow), the
+                   option "--debug 128" displays a memory statistic after
+                   the program run.
+
+Problems
+========
+
+If you have compile problems, use the configure options "--with-zlib" and
+"--without-nls".
+
+I cant check alls assembles files; so if you have problems assembling them
+(or the program crashes), simply delete the files in the mpi/<cpu> directory.
+The configure scripts may consider several subdirectories to get all
+available assembler files; be sure to delete the correct ones. The
+assembler replacements are in C and in mpi/generic; never delete udiv-qrnnd.S
+in any CPU directory, because there maybe no C substitute.
+Don't forget to delete "config.cache" and run "./config.status --recheck".
+
+
+
+
+Installation
+============
+G10 is not installed as suid:root; if you want to use it, do it manually
+(only g10, not g10maint).
+
+You have to create the ~/.g10 directory manually.  Your first action after
+this should be to create a key pair: "g10 --gen-key".
+
+
+
 Basic Installation
 ==================
 
index c138df3..9c07b76 100644 (file)
@@ -1,10 +1,9 @@
 ## Process this file with automake to produce Makefile.in
 
-SUBDIRS =  intl po util mpi cipher @ZLIB_SUBDIR@ tools g10
+SUBDIRS =  intl po zlib util mpi cipher tools g10
 EXTRA_DIST = VERSION
 
 
-
 tar:   clean
        cd ..; tar czvf  ~/bkup/g10-`date +%d%m`.tar.gz src
 
index 04bcc53..d5dd00b 100644 (file)
@@ -85,9 +85,8 @@ POSUB = @POSUB@
 RANLIB = @RANLIB@
 VERSION = @VERSION@
 ZLIBS = @ZLIBS@
-ZLIB_SUBDIR = @ZLIB_SUBDIR@
 
-SUBDIRS =  intl po util mpi cipher @ZLIB_SUBDIR@ tools g10
+SUBDIRS =  intl po zlib util mpi cipher tools g10
 EXTRA_DIST = VERSION
 ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
 mkinstalldirs = $(SHELL) $(top_srcdir)/scripts/mkinstalldirs
diff --git a/NEWS b/NEWS
index 748d693..a82c08a 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -1,3 +1,9 @@
+Noteworthy changes in version 0.2.6
+-----------------------------------
+
+    * Option "--export" works.
+
+
 Noteworthy changes in version 0.2.5
 -----------------------------------
 
diff --git a/README b/README
index 91d3ac9..f5dc7a8 100644 (file)
--- a/README
+++ b/README
@@ -2,13 +2,24 @@
             G10 - The GNU Encryption and Signing Tool
            ------------------------------------------
 
+    THIS IS ALPHA SOFTWARE, EXPECT BUGS AND UNIMPLEMENTED STUFF.
+    IT MAY HAPPEN THAT SOME DATA FORMATS OR PROGRAMM OPTIONS
+    CHANGE WITH THE NEXT VERSION.
 
-    THIS IS VERSION IS ONLY A TEST VERSION !  YOU SHOULD NOT
-    USE IT FOR OTHER PURPOSES THAN EVALUATING THE CURRENT CODE.
+    On a Linux box (version 2.x.x, alpha or x86 CPU) it should
+    work reliable. You may create your key on such a machine and
+    use it.  Please verify the tar file; there is a PGP and a G10
+    signature available. My PGP key is well known and published in
+    the "Global Trust Register for 1998", ISBN 0-9532397-0-5.
 
-    * The data format may change in the next version!
+    I have included my pubring as "g10/pubring.10", which contains
+    the key used to make G10 signatures:
+    "pub  1312G/FF3EAA0B 1998-02-09 Werner Koch <wk@isil.d.shuttle.de>"
+    "Key fingerprint = 8489 6CD0 1851 0E33 45DA  CD67 036F 11B8 FF3E AA0B"
 
-    * Some features are not yet implemented
+    You may add it to your G10 pubring and use it in the future to
+    verify new releases.  Because you verified the tar file containing
+    this file here, you can be sure that the above fingerprint is correct.
 
 
     Please subscribe to g10@net.lut.ac.uk by sending a mail with
     Installation
     ------------
 
-    1) "./configure"
-
-       to enable the integrated malloc debugging stuff, use:
+    See the file INSTALL.  Here is a quick summary:
 
-       "./configure --enable-m-debug"
+    1) "./configure"
 
     2) "make"
 
 
     4) You end up with a binary "g10" in /usr/local/bin
 
-    5) create a directory ".g10" under your hoem directory ("mkdir ~/.g10")
+    5) Optional, but suggested: install the program "g10" as suid root.
+
+    6) Create a directory ".g10" under your home directory ("mkdir ~/.g10")
+
 
 
 
     you are asked for the passphrase, so that G10 is able to look at the
     inner structure of a encrypted packet.
 
-       --quick-random
+       g10maint --quick-random
 
     Do not use the stroing random generator but a faster one.  This can be
     used to generate keys for tests; those are marked as insecure.
 
-       --list-trustdb
+       g10maint --list-trustdb
 
     List the contents of the trustdb in a human readable format
 
-       --list-trustdb  <usernames>
+       g10maint --list-trustdb  <usernames>
 
     List the tree of certificates for the given usernames
 
-       --list-trust-path  depth  username
+       g10maint --list-trust-path  depth  username
 
     List the possible trust paths for the given username, up to the specified
     depth.  If depth is negative, duplicate introducers are not listed,
      using a negative number). This option may create new entries in the
     trustdb.
 
-       --print-mds  filenames
+       g10maint --print-mds  filenames
 
     List all available message digest values for the fiven filenames
 
-       --gen-prime n
+       g10maint --gen-prime n
 
     Generate and print a simple prime number of size n
 
-       --gen-prime n q
+       g10maint --gen-prime n q
 
     Generate a prime number suitable for ElGamal signatures of size n with
     a q as largest primefactor of n-1.
 
-       --gen-prime n q 1
+       g10maint --gen-prime n q 1
 
     Ditto, but calculate a generator too.
 
 
-    For more options/commands see the file g10/OPTIONS.
+    For more options/commands see the file g10/OPTIONS, or use "g10 --help"
 
 
     Debug Flags
     but for now I stick to my own formatting rules.
 
     The primary FTP site is "ftp://ftp.guug.de/pub/gcrypt/"
-    The primary WWW page is "http://www.d.shuttle.de/isil/g10.html"
+    The primary WWW page is "http://www.d.shuttle.de/isil/crypt/g10.html"
+
+    If you like, send your keys to <g10-keys@isil.d.shuttle.de>; use
+    "g10 --export --armor | mail g10-keys@isil.d.shuttle.de" to do this.
 
     Please direct bug reports to <g10-bugs@isil.d.shuttle.de> or better
     post them to the mailing list <g10@net.lut.ac.uk>.
diff --git a/THANKS b/THANKS
index 4f53c92..315b7c1 100644 (file)
--- a/THANKS
+++ b/THANKS
@@ -9,7 +9,10 @@ Daniel Eisenbud        eisenbud@cs.swarthmore.edu
 Detlef Lannert         lannert@lannert.rz.uni-duesseldorf.de
 Ernst Molitor          ernst.molitor@uni-bonn.de
 Hendrik Buschkamp      buschkamp@rheumanet.org
+Jean-loup Gailly       gzip@prep.ai.mit.edu
 Jens Bachem            bachem@rrz.uni-koeln.de
+Mark Adler             madler@alumni.caltech.edu
+Martin Schulte         schulte@thp.uni-koeln.de
 Peter Gutmann          pgut001@cs.auckland.ac.nz
 Ralph Gillen           gillen@theochem.uni-duesseldorf.de
 Thomas Roessler        roessler@guug.de
diff --git a/TODO b/TODO
index baaa141..7b193c6 100644 (file)
--- a/TODO
+++ b/TODO
       we have a self-signature -> put this stuff into a kind of directory
       record, as it does not belong to the pubkey record?
 
+    * add an option to create a new user id and to reorder the sequence of
+      them, so that the preferred emal address comes first.  We need to
+      add some logic, which guarantees, that only one user-id can be signed by
+      others.  This prevents extensive growing of the public key certificate
+      due to the bad usage of signing every user id.  You get no extra
+      security by key signatures for every user id.  I consider this
+      behaviour of PGP a bug, introduced, becaus PGP does't require a
+      self-signature. New user ids will only have your self signature to bind
+      them to your key and because the user id which is signed by others has
+      also be signed by you, all user-ids are bound together.
+
 
diff --git a/VERSION b/VERSION
index 3a4036f..53a75d6 100644 (file)
--- a/VERSION
+++ b/VERSION
@@ -1 +1 @@
-0.2.5
+0.2.6
index 09cf7ac..4c221ce 100755 (executable)
@@ -44,11 +44,9 @@ cleanup () {
 
 
 run_g10 () {
-    eval HOME=. ../g10/g10 $*
-    if [ $? != 0 ] ; then
-       g10_err=$?
+    if ! eval HOME=. ../g10/g10 $* ; then
        echo "(HOME=. ../g10/g10 $*) failed" >&2
-       error "g10 failed: $g10_err" >&2
+       exit 1
     fi
 }
 
@@ -58,7 +56,7 @@ run_g10 () {
 
 set -e
 pgmname=$(basename $0)
-#trap cleanup EXIT SIGHUP SIGINT SIGQUIT
+trap cleanup SIGHUP SIGINT SIGQUIT
 
 
 # some checks
@@ -79,7 +77,7 @@ EOF
 
 # print the G10 version
 run_g10 --version
-# intialize the trustdb
+
 
 info Checking decryption
 for i in $plain_files ; do
@@ -87,21 +85,21 @@ for i in $plain_files ; do
     cmp $i y || error "$i: mismatch"
 done
 
-#info Checking cleartext signatures
-## There is a minor glitch, which appends a lf to the cleartext.
-## I do not consider that a bug, but I have to use the head .. mimic.
-## It is not clear what should happen to leading LFs, we must
-## change the defintion of cleartext, so that only 1 empty line
-## must follow the headers, but some specs say: any number of empty lines ..
-## clean-sat removes leading LFs
-## I know that this does not work for random data files (due to large lines
-## or what ever) - I hope we can live with it.
-#for i in $plain_files; do
-#    echo "$usrpass1" | run_g10 --passphrase-fd 0 -sat -o x --yes $i
-#    run_g10 -o y --yes x
-#    ../tools/clean-sat < $i > z
-#    head -c $[ $(cat y | wc -c) - 1 ] y | diff - z || error "$i: mismatch"
-#done
+info Checking cleartext signatures
+# There is a minor glitch, which appends a lf to the cleartext.
+# I do not consider that a bug, but I have to use the head .. mimic.
+# It is not clear what should happen to leading LFs, we must
+# change the defintion of cleartext, so that only 1 empty line
+# must follow the headers, but some specs say: any number of empty lines ..
+# clean-sat removes leading LFs
+# I know that this does not work for random data files (due to large lines
+# or what ever) - I hope we can live with it.
+for i in $plain_files; do
+    echo "$usrpass1" | run_g10 --passphrase-fd 0 -sat -o x --yes $i
+    run_g10 -o y --yes x
+    ../tools/clean-sat < $i > z
+    head -c $[ $(cat y | wc -c) - 1 ] y | diff - z || error "$i: mismatch"
+done
 
 info Creating some random data files
 for i in 500 9000 32000 80000; do
@@ -109,26 +107,25 @@ for i in 500 9000 32000 80000; do
     data_files="$data_files data-$i"
 done
 
-#info Checking armored signatures
-#for i in $plain_files $data_files ; do
-#    echo "$usrpass1" | run_g10 --passphrase-fd 0 -sa -o x --yes $i
-#    run_g10 -o y --yes x
-#    cmp $i y || error "$i: mismatch"
-#done
-#
-#info Checking signatures
-#for i in $plain_files $data_files; do
-#    echo "$usrpass1" | run_g10 --passphrase-fd 0 -s -o x --yes $i
-#    run_g10 -o y --yes x
-#    cmp $i y || error "$i: mismatch"
-#done
+info Checking armored signatures
+for i in $plain_files $data_files ; do
+    echo "$usrpass1" | run_g10 --passphrase-fd 0 -sa -o x --yes $i
+    run_g10 -o y --yes x
+    cmp $i y || error "$i: mismatch"
+done
+
+info Checking signatures
+for i in $plain_files $data_files; do
+    echo "$usrpass1" | run_g10 --passphrase-fd 0 -s -o x --yes $i
+    run_g10 -o y --yes x
+    cmp $i y || error "$i: mismatch"
+done
 
 
 info Checking armored encryption
 for i in $plain_files $data_files ; do
-    info "file $i"
-    run_g10 -v -ea -o x --yes -r "$usrname2" $i
-    run_g10 -v -o y --yes x
+    run_g10 -ea -o x --yes -r "$usrname2" $i
+    run_g10 -o y --yes x
     cmp $i y || error "$i: mismatch"
 done
 
diff --git a/cipher/ChangeLog b/cipher/ChangeLog
new file mode 100644 (file)
index 0000000..e69de29
index aba727a..b8fe2a1 100644 (file)
@@ -85,7 +85,6 @@ POSUB = @POSUB@
 RANLIB = @RANLIB@
 VERSION = @VERSION@
 ZLIBS = @ZLIBS@
-ZLIB_SUBDIR = @ZLIB_SUBDIR@
 
 INCLUDES =  -I$(top_srcdir)/include
 EXTRA_DIST = @CIPHER_EXTRA_DIST@
index 33e1f2f..1a29bf7 100644 (file)
@@ -162,26 +162,26 @@ AC_SUBST(MPI_EXTRA_ASM_OBJS)
 
 dnl Do we have zlib? Must do it here because Solaris failed
 dnl when compiling a conftest (due to the "-lz" from LIBS).
-ZLIBS=
-ZLIB_SUBDIR=
 if test "$g10_force_zlib" = "yes"; then
-    ZLIBS="\${top_srcdir}/zlib/libzlib.a"
-    ZLIB_SUBDIR=zlib
+    ZLIBS="-L\${top_srcdir}/zlib -lzlib"
+    AM_CONDITIONAL(ENABLE_LOCAL_ZLIB, true)
     WK_LINK_FILES(zlib/zlib.h, zlib.h )
     WK_LINK_FILES(zlib/zconf.h, zconf.h )
 else
 AC_CHECK_HEADERS(zlib.h)
 if test "$ac_cv_header_zlib_h" = yes ; then
     LIBS="$LIBS -lz"
+    ZLIBS=
+    AM_CONDITIONAL(ENABLE_LOCAL_ZLIB, false)
 else
-    ZLIBS="\${top_srcdir}/zlib/libzlib.a"
-    ZLIB_SUBDIR=zlib
+    ZLIBS="-L\${top_srcdir}/zlib -lzlib"
+    AM_CONDITIONAL(ENABLE_LOCAL_ZLIB, true)
     WK_LINK_FILES(zlib/zlib.h, zlib.h )
     WK_LINK_FILES(zlib/zconf.h, zconf.h )
 fi
 fi
 AC_SUBST(ZLIBS)
-AC_SUBST(ZLIB_SUBDIR)
+
 
 dnl checking whether we have other cipher source files
 CIPHER_EXTRA_OBJS=""
diff --git a/g10/ChangeLog b/g10/ChangeLog
new file mode 100644 (file)
index 0000000..2bfa48b
--- /dev/null
@@ -0,0 +1,27 @@
+Fri Feb 13 20:18:14 1998  Werner Koch  (wk@isil.d.shuttle.de)
+
+       * ringedit.c (enum_keyblocks, keyring_enum): New.
+
+Fri Feb 13 19:33:40 1998  Werner Koch  (wk@isil.d.shuttle.de)
+
+       * export.c: Add functionality.
+
+       * keygen.c (generate_keypair): Moved the leading comment behind the
+       key packet.
+       * kbnode.c (walk_kbnode): Fixed.
+
+       * g10.c (main): listing armored keys now work.
+
+Fri Feb 13 16:17:43 1998  Werner Koch  (wk@isil.d.shuttle.de)
+
+       * parse-packet.c (parse_publickey, parse_signature): Fixed calls
+       to mpi_read used for ELG b.
+
+Fri Feb 13 15:13:23 1998  Werner Koch  (wk@isil.d.shuttle.de)
+
+       * g10.c (main): changed formatting of help output.
+
+Thu Feb 12 22:24:42 1998  Werner Koch  (wk@frodo)
+
+       * pubkey-enc.c (get_session_key): rewritten
+
index 63ffc3e..afbeebf 100644 (file)
@@ -85,7 +85,6 @@ POSUB = @POSUB@
 RANLIB = @RANLIB@
 VERSION = @VERSION@
 ZLIBS = @ZLIBS@
-ZLIB_SUBDIR = @ZLIB_SUBDIR@
 
 INCLUDES = -I$(top_srcdir)/include
 EXTRA_DIST = OPTIONS  pubring.g10
index 04aebef..eea7345 100644 (file)
@@ -182,7 +182,7 @@ encode_crypt( const char *filename, STRLIST remusr )
        goto leave;
     }
     else if( opt.verbose )
-       log_error("reading from '%s'\n", filename? filename: "[stdin]");
+       log_info("reading from '%s'\n", filename? filename: "[stdin]");
 
     if( !(out = open_outfile( filename, opt.armor? 1:0 )) ) {
        rc = G10ERR_CREATE_FILE;  /* or user said: do not overwrite */
index d45c128..619d699 100644 (file)
 #include "keydb.h"
 #include "memory.h"
 #include "util.h"
+#include "main.h"
 
 
 /****************
- * Make a new keyring from all internal keyrings (if no user is given)
- * or for all selected users.
+ * Export the public keys (to standard out or --outout).
+ * Depending on opt.armor the output is armored.
+ * If USERS is NULL, the complete ring wil. be exported.
  */
 int
 export_pubkeys( STRLIST users )
 {
-    log_fatal("Not yet implemented");
-    return 0;
+    int rc = 0;
+    armor_filter_context_t afx;
+    compress_filter_context_t zfx;
+    IOBUF out = NULL;
+    PACKET pkt;
+    KBNODE keyblock = NULL;
+    KBNODE kbctx, node;
+    KBPOS kbpos;
+    STRLIST sl;
+    int all = !users;
+    int any=0;
+
+    memset( &afx, 0, sizeof afx);
+    memset( &zfx, 0, sizeof zfx);
+    init_packet( &pkt );
+
+    if( !(out = open_outfile( NULL, 0 )) ) {
+       rc = G10ERR_CREATE_FILE;
+       goto leave;
+    }
+
+    if( opt.armor ) {
+       afx.what = 1;
+       iobuf_push_filter( out, armor_filter, &afx );
+    }
+    if( opt.compress )
+       iobuf_push_filter( out, compress_filter, &zfx );
+
+    if( all ) {
+       rc = enum_keyblocks( 0, &kbpos, &keyblock );
+       if( rc ) {
+           if( rc != -1 )
+               log_error("enum_keyblocks(open) failed: %s\n", g10_errstr(rc) );
+           goto leave;
+       }
+       all = 2;
+    }
+
+    /* use the correct sequence. strlist_last,prev do work correct with
+     * NULL pointers :-) */
+    for( sl=strlist_last(users); sl || all ; sl=strlist_prev( users, sl )) {
+       if( all ) { /* get the next user */
+           rc = enum_keyblocks( 1, &kbpos, &keyblock );
+           if( rc == -1 )  /* EOF */
+               break;
+           if( rc ) {
+               log_error("enum_keyblocks(read) failed: %s\n", g10_errstr(rc));
+               break;
+           }
+       }
+       else {
+           /* search the userid */
+           rc = find_keyblock_byname( &kbpos, sl->d );
+           if( rc ) {
+               log_error("%s: user not found: %s\n", sl->d, g10_errstr(rc) );
+               rc = 0;
+               continue;
+           }
+           /* read the keyblock */
+           rc = read_keyblock( &kbpos, &keyblock );
+       }
+
+       if( rc ) {
+           log_error("certificate read problem: %s\n", g10_errstr(rc));
+           goto leave;
+       }
+
+       /* and write it */
+       for( kbctx=NULL; (node = walk_kbnode( keyblock, &kbctx, 0 )); ) {
+           if( (rc = build_packet( out, node->pkt )) ) {
+               log_error("build_packet(%d) failed: %s\n",
+                           node->pkt->pkttype, g10_errstr(rc) );
+               rc = G10ERR_WRITE_FILE;
+               goto leave;
+           }
+       }
+       any++;
+    }
+    if( rc == -1 )
+       rc = 0;
+
+  leave:
+    if( all == 2 )
+       enum_keyblocks( 2, &kbpos, &keyblock ); /* close */
+    release_kbnode( keyblock );
+    if( rc || !any )
+       iobuf_cancel(out);
+    else
+       iobuf_close(out);
+    if( !any )
+       log_info("warning: nothing exported\n");
+    return rc;
 }
 
 
index b5ce5f7..4fbc0f7 100644 (file)
--- a/g10/g10.c
+++ b/g10/g10.c
 #include "status.h"
 
 
+static ARGPARSE_OPTS opts[] = {
+
+    { 300, NULL, 0, N_("\vCommands:\n ") },
+
+    { 's', "sign",      0, N_("make a signature")},
+    { 539, "clearsign", 0, N_("make a clear text signature") },
+    { 'b', "detach-sign", 0, N_("make a detached signature")},
+    { 'e', "encrypt",   0, N_("encrypt data")},
+    { 'c', "symmetric", 0, N_("encryption only with symmetric cipher")},
+    { 507, "store",     0, N_("store only")},
+    { 'd', "decrypt",   0, N_("decrypt data (default)")},
+    { 'k', "list-keys", 0, N_("list keys")},
+    { 508, "check-keys",0, N_("check signatures on a key in the keyring")},
+    { 515, "fingerprint", 0, N_("show the fingerprints")},
+    { 521, "list-packets",0,N_("list only the sequence of packets")},
+    { 503, "gen-key",   0, N_("generate a new key pair")},
+    { 506, "sign-key"  ,0, N_("make a signature on a key in the keyring")},
+    { 505, "delete-key",0, N_("remove key from the public keyring")},
+    { 524, "edit-sig"  ,0, N_("edit a key signature")},
+    { 525, "change-passphrase", 0, N_("change the passphrase of your secret keyring")},
+    { 537, "export"          , 0, N_("export keys") },
+    { 530, "import",      0     , N_("import/merge keys")},
+
+    { 301, NULL, 0, N_("\v\nOptions:\n ") },
+
+    { 'a', "armor",     0, N_("create ascii armored output")},
+    { 'o', "output",    2, N_("use as output file")},
+    { 'u', "local-user",2, N_("use this user-id to sign or decrypt")},
+    { 'r', "remote-user", 2, N_("use this user-id for encryption")},
+    { 'v', "verbose",   0, N_("verbose") },
+    { 'z', NULL,        1, N_("set compress level (0 disables)") },
+    { 't', "textmode",  0, N_("use canonical text mode")},
+    { 'n', "dry-run",   0, N_("don't make any changes") },
+    { 500, "batch",     0, N_("batch mode: never ask")},
+    { 501, "yes",       0, N_("assume yes on most questions")},
+    { 502, "no",        0, N_("assume no on most questions")},
+    { 509, "keyring"   ,2, N_("add this keyring to the list of keyrings")},
+    { 517, "secret-keyring" ,2, N_("add this secret keyring to the list")},
+    { 518, "options"   , 2, N_("read options from file")},
+
+    { 510, "debug"     ,4|16, N_("set debugging flags")},
+    { 511, "debug-all" ,0, N_("enable full debugging")},
+    { 512, "status-fd" ,1, N_("write status info to this fd") },
+    { 534, "no-comment", 0,   N_("do not write comment packets")},
+    { 535, "completes-needed", 1, N_("(default is 1)")},
+    { 536, "marginals-needed", 1, N_("(default is 3)")},
+    { 527, "cipher-algo", 2 , N_("select default cipher algorithm")},
+    { 528, "pubkey-algo", 2 , N_("select default puplic key algorithm")},
+    { 529, "digest-algo", 2 , N_("select default message digest algorithm")},
+
+    { 302, NULL, 0, N_("\v\nExamples:\n\n"
+    " -se -r Bob [file]          sign and encrypt for user Bob\n"
+    " -sat [file]                make a clear text signature\n"
+    " -sb  [file]                make a detached signature\n"
+    " -k   [userid]              show keys\n"
+    " -kc  [userid]              show fingerprint\n"  ) },
+
+  /* hidden options */
+    { 532, "quick-random", 0, "\r"},
+    { 526, "no-verbose", 0, "\r"},
+    { 538, "trustdb-name", 2, "\r" },
+    { 540, "no-secmem-warning", 0, "\r" }, /* used only by regression tests */
+    { 519, "no-armor",   0, "\r"},
+    { 520, "no-default-keyring", 0, "\r" },
+    { 522, "no-greeting", 0, "\r" },
+    { 523, "passphrase-fd",1, "\r" },
+    { 541, "no-operation", 0, "\r" },      /* used by regression tests */
+
+
+{0} };
+
+
+
+
 enum cmd_values { aNull = 0,
     aSym, aStore, aEncr, aKeygen, aSign, aSignEncr,
     aSignKey, aClearsign, aListPackets, aEditSig,
     aKMode, aKModeC, aChangePass, aImport,
-    aExport,
+    aExport, aCheckKeys,
 aNOP };
 
 
@@ -59,7 +133,7 @@ strusage( int level )
     switch( level ) {
       case 10:
       case 0:  p = "g10 - v" VERSION "; "
-                   "Copyright 1997 Werner Koch (dd9jn)\n" ; break;
+                   "Copyright 1998 Werner Koch (dd9jn)\n" ; break;
       case 13: p = "g10"; break;
       case 14: p = VERSION; break;
       case 1:
@@ -105,7 +179,7 @@ i18n_init(void)
 static void
 wrong_args( const char *text)
 {
-    fputs(_("Usage: g10 [options] "),stderr);
+    fputs(_("usage: g10 [options] "),stderr);
     fputs(text,stderr);
     putc('\n',stderr);
     g10_exit(2);
@@ -152,63 +226,28 @@ set_cmd( enum cmd_values *ret_cmd, enum cmd_values new_cmd )
 }
 
 
+
+static void
+check_opts(void)
+{
+    if( !opt.def_cipher_algo || check_cipher_algo(opt.def_cipher_algo) )
+       log_error(_("selected cipher algorithm is invalid\n"));
+    if( !opt.def_pubkey_algo || check_pubkey_algo(opt.def_pubkey_algo) )
+       log_error(_("selected pubkey algorithm is invalid\n"));
+    if( !opt.def_digest_algo || check_digest_algo(opt.def_digest_algo) )
+       log_error(_("selected digest algorithm is invalid\n"));
+    if( opt.completes_needed < 1 )
+       log_error(_("completes-needed must be greater than 0\n"));
+    if( opt.marginals_needed < 2 )
+       log_error(_("marginals-needed must be greater than 1\n"));
+}
+
+
+
+
 void
 main( int argc, char **argv )
 {
-    static ARGPARSE_OPTS opts[] = {
-    { 'a', "armor",     0, N_("create ascii armored output")},
-    { 'v', "verbose",   0, N_("verbose") },
-    { 'z', NULL,        1, N_("set compress level (0 disables)") },
-    { 'n', "dry-run",   0, N_("don't make any changes") },
-    { 'c', "symmetric", 0, N_("do only a symmetric encryption")},
-    { 'o', "output",    2, N_("use as output file")},
-    { 500, "batch",     0, N_("batch mode: never ask")},
-    { 501, "yes",       0, N_("assume yes on most questions")},
-    { 502, "no",        0, N_("assume no on most questions")},
-    { 503, "gen-key",   0, N_("generate a new key pair")},
-    { 504, "add-key",   0, N_("add key to the public keyring")},
-    { 505, "delete-key",0, N_("remove key from public keyring")},
-    { 506, "sign-key"  ,0, N_("make a signature on a key in the keyring")},
-    { 507, "store",     0, N_("store only")},
-    { 508, "check-key" ,0, N_("check signatures on a key in the keyring")},
-    { 509, "keyring"   ,2, N_("add this keyring to the list of keyrings")},
-    { 's', "sign",      0, N_("make a signature")},
-    { 't', "textmode",  0, N_("use canonical text mode")},
-    { 'b', "detach-sign", 0, N_("make a detached signature")},
-    { 'e', "encrypt",   0, N_("encrypt data")},
-    { 'd', "decrypt",   0, N_("decrypt data (default)")},
-    { 'u', "local-user",2, N_("use this user-id to sign or decrypt")},
-    { 'r', "remote-user", 2, N_("use this user-id for encryption")},
-    { 'k', NULL      , 0, N_("list keys")},
-    { 510, "debug"     ,4|16, N_("set debugging flags")},
-    { 511, "debug-all" ,0, N_("enable full debugging")},
-    { 512, "status-fd" ,1, N_("write status info to this fd") },
-    { 515, "fingerprint", 0, N_("show the fingerprints")},
-    { 517, "secret-keyring" ,2, N_("add this secret keyring to the list")},
-    { 518, "options"   , 2, N_("read options from file")},
-    { 519, "no-armor",   0, "\r"},
-    { 520, "no-default-keyring", 0, "\r" },
-    { 521, "list-packets",0,N_("list only the sequence of packets")},
-    { 522, "no-greeting", 0, "\r" },
-    { 523, "passphrase-fd",1, "\r" },
-    { 524, "edit-sig"  ,0, N_("edit a key signature")},
-    { 525, "change-passphrase", 0, N_("change the passphrase of your secret keyring")},
-    { 526, "no-verbose", 0, "\r"},
-    { 527, "cipher-algo", 2 , N_("select default cipher algorithm")},
-    { 528, "pubkey-algo", 2 , N_("select default puplic key algorithm")},
-    { 529, "digest-algo", 2 , N_("select default message digest algorithm")},
-    { 530, "import",      0 , N_("put public keys into the trustdb")},
-    { 532, "quick-random", 0, "\r"},
-    { 534, "no-comment", 0,   N_("do not write comment packets")},
-    { 535, "completes-needed", 1, N_("(default is 1)")},
-    { 536, "marginals-needed", 1, N_("(default is 3)")},
-    { 537, "export", 0, N_("export all or the given keys") },
-    { 538, "trustdb-name", 2, "\r" },
-    { 539, "clearsign", 0, N_("make a clear text signature") },
-    { 540, "no-secmem-warning", 0, "\r" }, /* used only by regression tests */
-    { 541, "no-operation", 0, "\r" },      /* used by regression tests */
-
-    {0} };
     ARGPARSE_ARGS pargs;
     IOBUF a;
     int rc=0;
@@ -236,6 +275,7 @@ main( int argc, char **argv )
      * secmem_init()  somewhere after the option parsing
      */
 
+    log_set_name("g10");
     i18n_init();
     opt.compress = -1; /* defaults to standard compress level */
     opt.def_cipher_algo = CIPHER_ALGO_BLOWFISH;
@@ -278,9 +318,11 @@ main( int argc, char **argv )
                if( parse_debug )
                log_info(_("note: no default option file '%s'\n"), configname );
            }
-           else
-               log_fatal(_("option file '%s': %s\n"),
+           else {
+               log_error(_("option file '%s': %s\n"),
                                    configname, strerror(errno) );
+               g10_exit(1);
+           }
            m_free(configname); configname = NULL;
        }
        if( parse_debug && configname )
@@ -291,9 +333,7 @@ main( int argc, char **argv )
     while( optfile_parse( configfp, configname, &configlineno,
                                                &pargs, opts) ) {
        switch( pargs.r_opt ) {
-         case 'v': opt.verbose++;
-                   opt.list_sigs=1;
-                   break;
+         case 'v': opt.verbose++; opt.list_sigs=1; break;
          case 'z': opt.compress = pargs.r.ret_int; break;
          case 'a': opt.armor = 1; opt.no_armor=0; break;
          case 'd': break; /* it is default */
@@ -322,7 +362,8 @@ main( int argc, char **argv )
          case 503: set_cmd( &cmd, aKeygen); break;
          case 506: set_cmd( &cmd, aSignKey); break;
          case 507: set_cmd( &cmd, aStore); break;
-         case 508: opt.check_sigs = 1; opt.list_sigs = 1; break;
+         case 508: set_cmd( &cmd, aCheckKeys);
+                   opt.check_sigs = 1; opt.list_sigs = 1; break;
          case 509: add_keyring(pargs.r.ret_str); nrings++; break;
          case 510: opt.debug |= pargs.r.ret_ulong; break;
          case 511: opt.debug = ~0; break;
@@ -374,27 +415,8 @@ main( int argc, char **argv )
        goto next_pass;
     }
     m_free( configname ); configname = NULL;
-    if( !opt.def_cipher_algo || check_cipher_algo(opt.def_cipher_algo) ) {
-       log_error(_("selected cipher algorithm is invalid\n"));
-       errors++;
-    }
-    if( !opt.def_pubkey_algo || check_pubkey_algo(opt.def_pubkey_algo) ) {
-       log_error(_("selected pubkey algorithm is invalid\n"));
-       errors++;
-    }
-    if( !opt.def_digest_algo || check_digest_algo(opt.def_digest_algo) ) {
-       log_error(_("selected digest algorithm is invalid\n"));
-       errors++;
-    }
-    if( opt.completes_needed < 1 ) {
-       log_error(_("completes-needed must be greater than 0\n"));
-       errors++;
-    }
-    if( opt.marginals_needed < 2 ) {
-       log_error(_("marginals-needed must be greater than 1\n"));
-       errors++;
-    }
-    if( errors )
+    check_opts();
+    if( log_get_errorcount(0) )
        g10_exit(2);
 
     if( greeting ) {
@@ -541,6 +563,7 @@ main( int argc, char **argv )
                                                       g10_errstr(rc) );
        break;
 
+      case aCheckKeys:
       case aKMode: /* list keyring */
        if( !argc ) { /* list the default public keyrings */
            int i, seq=0;
@@ -563,14 +586,23 @@ main( int argc, char **argv )
            }
 
        }
+       else if( cmd == aCheckKeys ) {
+           log_error("will be soon: --check-keys user-ids\n");
+       }
        else if( argc == 1) { /* list the given keyring */
            if( !(a = iobuf_open(fname)) )
-               log_fatal(_("can't open '%s'\n"), fname_print);
-           proc_packets( a );
-           iobuf_close(a);
+               log_error(_("can't open '%s'\n"), fname_print);
+           else {
+               if( !opt.no_armor ) {
+                   memset( &afx, 0, sizeof afx);
+                   iobuf_push_filter( a, armor_filter, &afx );
+               }
+               proc_packets( a );
+               iobuf_close(a);
+           }
        }
        else
-           wrong_args(_("-k[v][v][v][c] [keyring]"));
+           wrong_args(_("-k[v][v][v][c] [keyring]") );
        break;
 
       case aKeygen: /* generate a key (interactive) */
@@ -607,18 +639,20 @@ main( int argc, char **argv )
        if( argc > 1 )
            wrong_args(_("[filename]"));
        if( !(a = iobuf_open(fname)) )
-           log_fatal(_("can't open '%s'\n"), fname_print);
-       if( !opt.no_armor ) {
-           /* push the armor filter, so it can peek at the input data */
-           memset( &afx, 0, sizeof afx);
-           iobuf_push_filter( a, armor_filter, &afx );
-       }
-       if( cmd == aListPackets ) {
-           set_packet_list_mode(1);
-           opt.list_packets=1;
+           log_error(_("can't open '%s'\n"), fname_print);
+       else {
+           if( !opt.no_armor ) {
+               /* push the armor filter, so it can peek at the input data */
+               memset( &afx, 0, sizeof afx);
+               iobuf_push_filter( a, armor_filter, &afx );
+           }
+           if( cmd == aListPackets ) {
+               set_packet_list_mode(1);
+               opt.list_packets=1;
+           }
+           proc_packets( a );
+           iobuf_close(a);
        }
-       proc_packets( a );
-       iobuf_close(a);
        break;
     }
 
index 2cba74a..0474152 100644 (file)
 
 
 /****************
- * Import the public keys from the given filename.
- * Import is a somewhat misleading name, as we (only) add informations
- * about the public keys into aout trustdb.
+ * Import the public keys from the given filename. Input may be armored.
+ * This function rejects alls keys which are not valid self signed on at
+ * least one userid. Only user ids which are self signed will be imported.
+ * Other signatures are not not checked.
+ *
+ * Actually this functtion does a merge, it works like this:
+ *   FIXME: add handling for revocation certs
+ *
+ *  - get the keyblock
+ *  - check self-signatures and remove all userids and their isgnatures
+ *    without/invalid self-signatures.
+ *  - reject the keyblock, if we have no valid userid.
+ *  - See wether we have this key already in one of our pubrings.
+ *    If not, simply add it to the default keyring.
+ *  - Compare the key and the self-signatures of the new and the one in
+ *    our keyring.  If they are differen something weird is going on;
+ *    ask what to do.
+ *  - See wether we have only non-self-signature on one user id; if not
+ *    ask the user what to do.
+ *  - compare the signatures: If we already have this signature, check
+ *    that they compare okay, if not issue a warning and ask the user.
+ *    (consider to look at the timestamp and use the newest?)
+ *  - Simply add the signature.  Can't verify here because we may not have
+ *    the signatures public key yet; verification is done when putting it
+ *    into the trustdb, which is done automagically as soon as this pubkey
+ *    is used.
+ *  - Proceed with next signature.
  *
- * NOTE: this function is not really needed and will be changed to
- *     a function which reads a plain textfile, describing a public
- *     key and its associated ownertrust.  This can be used (together
- *     with the export function) to make a backup of the assigned
- *     ownertrusts.
  */
 int
 import_pubkeys( const char *filename )
index dd4f0ce..83ec507 100644 (file)
@@ -177,11 +177,12 @@ walk_kbnode( KBNODE root, KBNODE *context, int all )
     do {
        if( !*context ) {
            *context = root;
-           return root;
+           n = root;
+       }
+       else {
+           n = (*context)->next;
+           *context = n;
        }
-
-       n = (*context)->next;
-       *context = n;
     } while( !all && n && (n->private_flag & 1) );
 
     return n;
index ff0ecb5..ca54020 100644 (file)
@@ -51,6 +51,8 @@ struct keyblock_pos_struct {
     int   resno;     /* resource number */
     ulong offset;    /* position information */
     unsigned count;  /* length of the keyblock in packets */
+    IOBUF  fp;      /* used by enum_keyblocks */
+    PACKET *pkt;     /* ditto */
 };
 typedef struct keyblock_pos_struct KBPOS;
 
@@ -144,6 +146,7 @@ int find_secret_keyblock_byname( KBPOS *kbpos, const char *username );
 int lock_keyblock( KBPOS *kbpos );
 void unlock_keyblock( KBPOS *kbpos );
 int read_keyblock( KBPOS *kbpos, KBNODE *ret_root );
+int enum_keyblocks( int mode, KBPOS *kbpos, KBNODE *ret_root );
 int insert_keyblock( KBPOS *kbpos, KBNODE root );
 int delete_keyblock( KBPOS *kbpos );
 int update_keyblock( KBPOS *kbpos, KBNODE root );
index f9e68a0..1c9a2ef 100644 (file)
@@ -535,11 +535,11 @@ generate_keypair()
 
     /* we create the packets as a tree of kbnodes. Because the structure
      * we create is known in advance we simply generate a linked list
-     * The first packet is a comment packet, followed by the userid and
-     * the self signature.
+     * The first packet is a dummy comment packet which we flag
+     * as deleted.  The very first packet must always be a CERT packet.
      */
-    pub_root = make_comment_node("#created by G10 pre-release " VERSION );
-    sec_root = make_comment_node("#created by G10 pre-release " VERSION );
+    pub_root = make_comment_node("#"); delete_kbnode(pub_root, pub_root);
+    sec_root = make_comment_node("#"); delete_kbnode(sec_root, sec_root);
 
     tty_printf(_(
 "We need to generate a lot of random bytes. It is a good idea to perform\n"
@@ -557,6 +557,12 @@ generate_keypair()
        rc = gen_dsa(nbits, pub_root, sec_root, dek, &skc );
     else
        BUG();
+    if( !rc ) {
+       add_kbnode( pub_root,
+               make_comment_node("#created by G10 release " VERSION ));
+       add_kbnode( sec_root,
+               make_comment_node("#created by G10 release " VERSION ));
+    }
     if( !rc )
        write_uid(pub_root, uid );
     if( !rc )
index 2e3cf21..0e13f6d 100644 (file)
@@ -437,6 +437,7 @@ parse_publickey( IOBUF inp, int pkttype, unsigned long pktlen, PACKET *packet )
     if( k->pubkey_algo == PUBKEY_ALGO_ELGAMAL ) {
        n = pktlen;
        k->d.elg.a = mpi_read(inp, &n, 0); pktlen -=n;
+       n = pktlen;
        k->d.elg.b = mpi_read(inp, &n, 0 ); pktlen -=n;
        if( list_mode ) {
            printf("\telg a: ");
@@ -502,6 +503,7 @@ parse_signature( IOBUF inp, int pkttype, unsigned long pktlen,
        sig->d.elg.digest_start[1] = iobuf_get_noeof(inp); pktlen--;
        n = pktlen;
        sig->d.elg.a = mpi_read(inp, &n, 0 ); pktlen -=n;
+       n = pktlen;
        sig->d.elg.b = mpi_read(inp, &n, 0 ); pktlen -=n;
        if( list_mode ) {
            printf("\tdigest algo %d, begin of digest %02x %02x\n",
index 2f8fb45..0fcd9c2 100644 (file)
 int
 get_session_key( PKT_pubkey_enc *k, DEK *dek )
 {
-    int i, j, c, rc = 0;
-    MPI dek_frame = mpi_alloc_secure(40);
+    int rc = 0;
+    MPI plain_dek  = NULL;
+    byte *frame = NULL;
+    unsigned n, nframe;
     u16 csum, csum2;
     PKT_secret_cert *skc = m_alloc_clear( sizeof *skc );
 
@@ -58,7 +60,8 @@ get_session_key( PKT_pubkey_enc *k, DEK *dek )
        skey.g = skc->d.elg.g;
        skey.y = skc->d.elg.y;
        skey.x = skc->d.elg.x;
-       elg_decrypt( dek_frame, k->d.elg.a, k->d.elg.b, &skey );
+       plain_dek = mpi_alloc_secure( mpi_get_nlimbs(skey.p) );
+       elg_decrypt( plain_dek, k->d.elg.a, k->d.elg.b, &skey );
        memset( &skey, 0, sizeof skey );
     }
   #ifdef HAVE_RSA_CIPHER
@@ -74,7 +77,8 @@ get_session_key( PKT_pubkey_enc *k, DEK *dek )
        skey.q = skc->d.rsa.rsa_q;
        skey.d = skc->d.rsa.rsa_d;
        skey.u = skc->d.rsa.rsa_u;
-       rsa_secret( dek_frame, k->d.rsa.rsa_integer, &skey );
+       plain_dek = mpi_alloc_secure( mpi_get_nlimbs(skey.n) );
+       rsa_secret( plain_dek, k->d.rsa.rsa_integer, &skey );
        memset( &skey, 0, sizeof skey );
     }
   #endif/*HAVE_RSA_CIPHER*/
@@ -83,9 +87,10 @@ get_session_key( PKT_pubkey_enc *k, DEK *dek )
        goto leave;
     }
     free_secret_cert( skc ); skc = NULL;
+    frame = mpi_get_buffer( plain_dek, &nframe, NULL );
+    mpi_free( plain_dek ); plain_dek = NULL;
 
-
-    /* Now get the DEK (data encryption key) from the dek_frame
+    /* Now get the DEK (data encryption key) from the frame
      *
      * Old versions encode the DEK in in this format (msb is left):
      *
@@ -101,51 +106,53 @@ get_session_key( PKT_pubkey_enc *k, DEK *dek )
      * CSUM
      */
     if( DBG_CIPHER )
-       log_mpidump("DEK frame:", dek_frame );
-    for(i=0; mpi_getbyte(dek_frame, i) != -1; i++ )
+       log_hexdump("DEK frame:", frame, nframe );
+    for(n=0; n < nframe && !frame[n]; n++ ) /* skip leading zeroes */
        ;
-    for(i--; i >= 0 && !(c=mpi_getbyte(dek_frame, i)); i--)
-       ; /* Skip leading zeroes */
-    if( i < 16 )
+    if( n + 7 > nframe )
        { rc = G10ERR_WRONG_SECKEY; goto leave; }
-    if( c == 1 && mpi_getbyte(dek_frame,0) == 2 ) {
+    if( frame[n] == 1 && frame[nframe-1] == 2 ) {
        log_error("old encoding of DEK is not supported\n");
        rc = G10ERR_CIPHER_ALGO;
        goto leave;
     }
-    if( c != 2 )  /* somethink is wrong */
+    if( frame[n] != 2 )  /* somethink is wrong */
        { rc = G10ERR_WRONG_SECKEY; goto leave; }
-    /* look for the zero byte */
-    for(i--; i > 4 ; i-- )
-       if( !mpi_getbyte(dek_frame,i) )
-           break;
-    if( i <= 4 ) /* zero byte not found */
+    for(n++; n < nframe && frame[n]; n++ ) /* skip the random bytes */
+       ;
+    n++; /* and the zero byte */
+    if( n + 4 > nframe )
        { rc = G10ERR_WRONG_SECKEY; goto leave; }
-    /* next byte indicates the used cipher */
-    switch( mpi_getbyte(dek_frame, --i ) ) {
+
+    dek->keylen = nframe - (n+1) - 2;
+    dek->algo = frame[n++];
+    switch( dek->algo ) {
       case CIPHER_ALGO_IDEA:
        rc = G10ERR_NI_CIPHER;
        goto leave;
       case CIPHER_ALGO_BLOWFISH:
-       if( i != 22 ) /* length of blowfish is 20 (+2 bytes checksum) */
+       if( dek->keylen != 20 )
            { rc = G10ERR_WRONG_SECKEY; goto leave; }
-       dek->algo = CIPHER_ALGO_BLOWFISH;
        break;
       case CIPHER_ALGO_BLOWFISH128:
-       if( i != 18 ) /* length of blowfish-128 is 16 (+2 bytes checksum) */
+       if( dek->keylen != 16 )
+           { rc = G10ERR_WRONG_SECKEY; goto leave; }
+       break;
+      case CIPHER_ALGO_CAST:
+       if( dek->keylen < 5 || dek->keylen > 16 )
            { rc = G10ERR_WRONG_SECKEY; goto leave; }
-       dek->algo = CIPHER_ALGO_BLOWFISH128;
        break;
       default:
+       dek->algo = 0;
        rc = G10ERR_CIPHER_ALGO;
        goto leave;
     }
     /* copy the key to DEK and compare the checksum */
-    csum  = mpi_getbyte(dek_frame, 1) << 8;
-    csum |= mpi_getbyte(dek_frame, 0);
-    dek->keylen = i - 2;
-    for( i--, csum2=0, j=0; i > 1; i-- )
-       csum2 += dek->key[j++] = mpi_getbyte(dek_frame, i);
+    csum  = frame[nframe-2] << 8;
+    csum |= frame[nframe-1];
+    memcpy( dek->key, frame+n, dek->keylen );
+    for( csum2=0, n=0; n < dek->keylen; n++ )
+       csum2 += dek->key[n];
     if( csum != csum2 ) {
        rc = G10ERR_WRONG_SECKEY;
        goto leave;
@@ -154,7 +161,8 @@ get_session_key( PKT_pubkey_enc *k, DEK *dek )
        log_hexdump("DEK is:", dek->key, dek->keylen );
 
   leave:
-    mpi_free(dek_frame);
+    mpi_free(plain_dek);
+    m_free(frame);
     if( skc )
        free_secret_cert( skc );
     return rc;
index 141d8cf..adba3db 100644 (file)
@@ -77,6 +77,7 @@ static int keyring_search( PACKET *pkt, KBPOS *kbpos, IOBUF iobuf );
 static int keyring_search2( PUBKEY_FIND_INFO info, KBPOS *kbpos,
                                                   const char *fname);
 static int keyring_read( KBPOS *kbpos, KBNODE *ret_root );
+static int keyring_enum( KBPOS *kbpos, KBNODE *ret_root );
 static int keyring_copy( KBPOS *kbpos, int mode, KBNODE root );
 
 
@@ -297,6 +298,78 @@ read_keyblock( KBPOS *kbpos, KBNODE *ret_root )
     return keyring_read( kbpos, ret_root );
 }
 
+
+/****************
+ * This functions can be used to read trough a complete keyring.
+ * Mode is: 0 = open
+ *         1 = read
+ *         2 = close
+ *         all others are reserved!
+ * Note that you do not need a search prior to call this function,
+ * only handle is needed.
+ * NOTE: It is not alloed to do an insert/update/delte with this
+ *      keyblock, if you want to do this, user search/read!
+ */
+int
+enum_keyblocks( int mode, KBPOS *kbpos, KBNODE *ret_root )
+{
+    int rc = 0;
+    RESTBL *rentry;
+
+    if( !mode || mode == 100 ) {
+       int i;
+       kbpos->fp = NULL;
+       if( !mode )
+           i = 0;
+       else
+           i = kbpos->resno+1;
+       for(; i < MAX_RESOURCES; i++ )
+           if( resource_table[i].used && !resource_table[i].secret )
+               break;
+       if( i == MAX_RESOURCES )
+           return -1; /* no resources */
+       kbpos->resno = i;
+       rentry = check_pos( kbpos );
+       kbpos->fp = iobuf_open( rentry->fname );
+       if( !kbpos->fp ) {
+           log_error("can't open '%s'\n", rentry->fname );
+           return G10ERR_OPEN_FILE;
+       }
+       kbpos->pkt = NULL;
+    }
+    else if( mode == 1 ) {
+       int cont;
+       do {
+           cont = 0;
+           if( !kbpos->fp )
+               return G10ERR_GENERAL;
+           rc = keyring_enum( kbpos, ret_root );
+           if( rc == -1 ) {
+               assert( !kbpos->pkt );
+               rentry = check_pos( kbpos );
+               assert(rentry);
+               /* close */
+               enum_keyblocks(2, kbpos, ret_root );
+               /* and open the next one */
+               rc = enum_keyblocks(100, kbpos, ret_root );
+               if( !rc )
+                   cont = 1;
+           }
+       } while(cont);
+    }
+    else if( kbpos->fp ) {
+       iobuf_close( kbpos->fp );
+       kbpos->fp = NULL;
+       /* release pending packet */
+       free_packet( kbpos->pkt );
+       m_free( kbpos->pkt );
+    }
+    return rc;
+}
+
+
+
+
 /****************
  * Insert the keyblock described by ROOT into the keyring described
  * by KBPOS.  This actually appends the data to the keyfile.
@@ -551,9 +624,8 @@ keyring_read( KBPOS *kbpos, KBNODE *ret_root )
 
     if( rc )
        release_kbnode( root );
-    else {
+    else
        *ret_root = root;
-    }
     free_packet( pkt );
     m_free( pkt );
     iobuf_close(a);
@@ -561,6 +633,69 @@ keyring_read( KBPOS *kbpos, KBNODE *ret_root )
 }
 
 
+static int
+keyring_enum( KBPOS *kbpos, KBNODE *ret_root )
+{
+    PACKET *pkt;
+    int rc;
+    RESTBL *rentry;
+    KBNODE root = NULL;
+    int in_cert = 0;
+
+    if( !(rentry=check_pos(kbpos)) )
+       return G10ERR_GENERAL;
+
+    if( kbpos->pkt ) {
+       root = new_kbnode( kbpos->pkt );
+       kbpos->pkt = NULL;
+    }
+
+    pkt = m_alloc( sizeof *pkt );
+    init_packet(pkt);
+    while( (rc=parse_packet(kbpos->fp, pkt)) != -1 ) {
+       if( rc ) {  /* ignore errors */
+           if( rc != G10ERR_UNKNOWN_PACKET ) {
+               log_error("read_keyblock: read error: %s\n", g10_errstr(rc) );
+               rc = G10ERR_INV_KEYRING;
+               goto ready;
+           }
+           free_packet( pkt );
+           continue;
+       }
+       /* make a linked list of all packets */
+       switch( pkt->pkttype ) {
+         case PKT_PUBLIC_CERT:
+         case PKT_SECRET_CERT:
+           if( in_cert ) { /* store this packet */
+               kbpos->pkt = pkt;
+               pkt = NULL;
+               goto ready;
+           }
+           in_cert = 1;
+         default:
+           if( !root )
+               root = new_kbnode( pkt );
+           else
+               add_kbnode( root, new_kbnode( pkt ) );
+           pkt = m_alloc( sizeof *pkt );
+           init_packet(pkt);
+           break;
+       }
+    }
+  ready:
+    if( rc == -1 && root )
+       rc = 0;
+
+    if( rc )
+       release_kbnode( root );
+    else
+       *ret_root = root;
+    free_packet( pkt );
+    m_free( pkt );
+    return rc;
+}
+
+
 
 /****************
  * Peromf insert/delete/update operation.
@@ -579,6 +714,8 @@ keyring_copy( KBPOS *kbpos, int mode, KBNODE root )
 
     if( !(rentry = check_pos( kbpos )) )
        return G10ERR_GENERAL;
+    if( kbpos->fp )
+       BUG(); /* not allowed with such a handle */
 
     /* open the source file */
     fp = iobuf_open( rentry->fname );
index 52718b3..d677744 100644 (file)
@@ -796,14 +796,14 @@ edit_keysigs( const char *username )
     /* search the userid */
     rc = find_keyblock_byname( &kbpos, username );
     if( rc ) {
-       log_error("user '%s' not found\n", username );
+       log_error("%s: user not found\n", username );
        goto leave;
     }
 
     /* read the keyblock */
     rc = read_keyblock( &kbpos, &keyblock );
     if( rc ) {
-       log_error("error reading the certificate: %s\n", g10_errstr(rc) );
+       log_error("%s: certificate read problem: %s\n", username, g10_errstr(rc) );
        goto leave;
     }
 
diff --git a/include/ChangeLog b/include/ChangeLog
new file mode 100644 (file)
index 0000000..e69de29
index d847316..35ca322 100644 (file)
@@ -8,3 +8,4 @@ types.h
 util.h
 i18n.h
 
+ChangeLog
index 1eca49a..e083c53 100644 (file)
@@ -56,14 +56,14 @@ typedef struct {
 } ARGPARSE_OPTS;
 
 /*-- logger.c --*/
+void log_set_name( const char *name );
+const char *log_get_name(void);
 void log_set_pid( int pid );
 int  log_get_errorcount( int clear );
 void log_hexdump( const char *text, char *buf, size_t len );
 void log_mpidump( const char *text, MPI a );
 
 #if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 5 )
-  void printstr( int level, const char *fmt, ... )
-                           __attribute__ ((format (printf,2,3)));
   void log_bug( const char *fmt, ... )
                            __attribute__ ((noreturn, format (printf,1,2)));
   void log_bug0( const char *, int, const char * ) __attribute__ ((noreturn));
@@ -74,7 +74,6 @@ void log_mpidump( const char *text, MPI a );
   void log_debug( const char *fmt, ... ) __attribute__ ((format (printf,1,2)));
   #define BUG() log_bug0(  __FILE__ , __LINE__, __FUNCTION__ )
 #else
-  void printstr( int level, const char *fmt, ... );
   void log_bug( const char *fmt, ... );
   void log_bug0( const char *, int );
   void log_fatal( const char *fmt, ... );
diff --git a/mpi/ChangeLog b/mpi/ChangeLog
new file mode 100644 (file)
index 0000000..e69de29
index 3b34ede..87976ee 100644 (file)
@@ -85,7 +85,6 @@ POSUB = @POSUB@
 RANLIB = @RANLIB@
 VERSION = @VERSION@
 ZLIBS = @ZLIBS@
-ZLIB_SUBDIR = @ZLIB_SUBDIR@
 
 INCLUDES =  -I$(top_srcdir)/include
 
index bccb51f..3daea76 100644 (file)
@@ -118,7 +118,7 @@ mpi_read(IOBUF inp, unsigned *ret_nread, int secure)
 
   leave:
     if( nread > *ret_nread )
-       log_error("Ooops: mpi crosses packet border");
+       log_bug("mpi crosses packet border");
     else
        *ret_nread = nread;
     return val;
index 09be317..3eb09f0 100644 (file)
   #undef mpi_free
 #endif
 
+/****************
+ * fixme: It was a bad idea to use the number of limbs to allocate
+ *       because on a alpha the limbs are large but we normally need
+ *       integers of n bits - So we should chnage this to bits (or bytes).
+ *
+ *       But mpi_alloc is used in a lot of places :-)
+ */
 MPI
 #ifdef M_DEBUG
 mpi_debug_alloc( unsigned nlimbs, const char *info )
index 1d25265..e69de29 100644 (file)
@@ -1,5 +0,0 @@
-Tue Feb 10 11:57:23 1998  Werner Koch  (wk@frodo)
-
-       * ddd/hhhh:
-
-
index 9db7019..ae74353 100755 (executable)
@@ -3,9 +3,9 @@
 set -e
 
 curr_ver=$(ls g10-*.tar.gz | sort -r -t '.' -n +0.4 -1 +1 -2 +2 \
-           | head -1 | sed -e 's/g10-\(.*\).tar.gz/\1/' )
+          | head -1 | sed -e 's/g10-\(.*\).tar.gz/\1/' )
 prev_ver=$(ls g10-*.tar.gz | sort -r -t '.' -n +0.4 -1 +1 -2 +2 \
-           | head -2 | tail -1 | sed -e 's/g10-\(.*\).tar.gz/\1/' )
+          | head -2 | tail -1 | sed -e 's/g10-\(.*\).tar.gz/\1/' )
 
 echo "Current  is: $curr_ver"
 echo "Previous is: $prev_ver"
@@ -13,11 +13,13 @@ echo "Previous is: $prev_ver"
 echo "Removing old directories"
 [ -d "g10-$curr_ver" ] && rm -rf "g10-$curr_ver"
 [ -d "g10-$prev_ver" ] && rm -rf "g10-$prev_ver"
-echo "Unpacking previous and current tar" 
+
+echo "Unpacking previous and current tar"
 tar xzf "g10-$curr_ver.tar.gz"
 tar xzf "g10-$prev_ver.tar.gz"
 
+read
+
 echo "Diffing"
 tmp_name="g10-$curr_ver.diff.tmp"
 diff_name="g10-$curr_ver.diff"
@@ -44,6 +46,7 @@ Prereq: $prev_ver
 EOF
 
 sed -ne '/^diff.*VERSION/,/^+[0-9][0-9]*/ p' $tmp_name >> $diff_name
+echo  >> $diff_name
 sed -e '/^diff.*VERSION/,/^+[0-9][0-9]*/ d'  $tmp_name >> $diff_name
 
 rm $tmp_name
@@ -53,7 +56,7 @@ gzip -9 $diff_name
 
 echo "Checking patch file"
 cd g10-$prev_ver
-zcat ../$diff_name.gz | patch -s -p1 
+zcat ../$diff_name.gz | patch -s -p1
 rm $(find . -name "*.orig")
 cd ..
 
diff --git a/tools/ChangeLog b/tools/ChangeLog
new file mode 100644 (file)
index 0000000..e69de29
index 21af3c4..d9fa5ce 100644 (file)
@@ -85,7 +85,6 @@ POSUB = @POSUB@
 RANLIB = @RANLIB@
 VERSION = @VERSION@
 ZLIBS = @ZLIBS@
-ZLIB_SUBDIR = @ZLIB_SUBDIR@
 
 INCLUDES = -I$(top_srcdir)/include
 needed_libs = ../cipher/libcipher.a  ../util/libutil.a ../mpi/libmpi.a ../util/libutil.a
diff --git a/util/ChangeLog b/util/ChangeLog
new file mode 100644 (file)
index 0000000..c72c6b8
--- /dev/null
@@ -0,0 +1,18 @@
+Fri Feb 13 19:34:59 1998  Werner Koch  (wk@isil.d.shuttle.de)
+
+       * iobuf.c (iobuf_seek): Set counters to new offset.
+
+Fri Feb 13 17:13:04 1998  Werner Koch  (wk@isil.d.shuttle.de)
+
+       * logger.c (log_set_name, log_get_name): New.
+       (print_prefix, pgm_name): New, changed all function to make use it.
+       (log_mpidump): Removed the "DBG" prefix.
+       (log_hexdump): Ditto.
+
+       * logger.c (printstr): Removed.
+
+Fri Feb 13 15:14:13 1998  Werner Koch  (wk@isil.d.shuttle.de)
+
+       * argparse.c (show_help): New '\v' kludge.
+
+
index 4da6640..1a7cc11 100644 (file)
@@ -85,7 +85,6 @@ POSUB = @POSUB@
 RANLIB = @RANLIB@
 VERSION = @VERSION@
 ZLIBS = @ZLIBS@
-ZLIB_SUBDIR = @ZLIB_SUBDIR@
 
 INCLUDES = -I$(top_srcdir)/include
 
index 0c8ad8f..620211e 100644 (file)
@@ -538,16 +538,31 @@ show_help( ARGPARSE_OPTS *opts, unsigned flags )
        /* get max. length of long options */
        for(i=indent=0; opts[i].short_opt; i++ ) {
            if( opts[i].long_opt )
-               if( (j=strlen(opts[i].long_opt)) > indent && j < 35 )
-                   indent = j;
+               if( !opts[i].description || *opts[i].description != '\v' )
+                   if( (j=strlen(opts[i].long_opt)) > indent && j < 35 )
+                        indent = j;
        }
        /* example: " -v, --verbose   Viele Sachen ausgeben" */
        indent += 10;
-       puts("Options:");
+       if( *opts[0].description != '\v' )
+           puts("Options:");
        for(i=0; opts[i].short_opt; i++ ) {
            s = _( opts[i].description );
            if( s && *s== '\r' ) /* hide this line */
                continue;
+           if( s && *s == '\v' ) { /* unindented comment only line */
+               for(s++; *s; s++ ) {
+                   if( *s == '\n' ) {
+                       if( s[1] )
+                           putchar('\n');
+                   }
+                   else
+                       putchar(*s);
+               }
+               putchar('\n');
+               continue;
+           }
+
            if( opts[i].short_opt < 256 )
                printf(" -%c", opts[i].short_opt );
            else
index 65efc0e..cc3288d 100644 (file)
@@ -867,6 +867,11 @@ iobuf_tell( IOBUF a )
 }
 
 
+
+/****************
+ * This is a very limited implementation. It simply discards all internal
+ * buffering and remove all filters but the first one.
+ */
 int
 iobuf_seek( IOBUF a, ulong newpos )
 {
@@ -885,6 +890,10 @@ iobuf_seek( IOBUF a, ulong newpos )
        log_error("can't seek to %lu: %s\n", newpos, strerror(errno) );
        return -1;
     }
+    a->d.len = 0;   /* discard buffer */
+    a->d.start = 0;
+    a->nbytes = 0;
+    a->nlimit = 0;
     a->ntotal = newpos;
     /* remove filters, but the last */
     while( a->chain )
index 7d101c2..8b53a7b 100644 (file)
 #include "util.h"
 
 static char pidstring[15];
+static char *pgm_name;
 static int errorcount;
 
 void
+log_set_name( const char *name )
+{
+    m_free(pgm_name);
+    if( name )
+       pgm_name = m_strdup(name);
+    else
+       pgm_name = NULL;
+}
+
+const char *
+log_get_name(void)
+{
+    return pgm_name? pgm_name : "";
+}
+
+
+void
 log_set_pid( int pid )
 {
     if( pid )
@@ -46,45 +64,21 @@ log_get_errorcount( int clear)
     return n;
 }
 
-
-/****************
- * General interface for printing a line
- * level 0 := print to /dev/null
- *      1 := print to stdout
- *      2 := print as info to stderr
- *      3 := ditto but as error
- */
-void
-printstr( int level, const char *fmt, ... )
+static void
+print_prefix(const char *text)
 {
-    va_list arg_ptr ;
-
-    if( !level )
-       return;
-
-    if( !fmt ) {
-       putc('\n', level? stderr: stdout);
-       return;
-    }
-
-    va_start( arg_ptr, fmt ) ;
-    if( level < 2 ) {
-       vfprintf(stdout,fmt,arg_ptr) ;
-    }
-    else {
-       fprintf(stderr, level==2? "%s: ": "%s: error: ", strusage(13) ) ;
-       vfprintf(stderr,fmt,arg_ptr) ;
-    }
-    va_end(arg_ptr);
+    if( pgm_name )
+       fprintf(stderr, "%s%s: %s", pgm_name, pidstring, text );
+    else
+       fprintf(stderr, "?%s: %s", pidstring, text );
 }
 
-
 void
 log_info( const char *fmt, ... )
 {
     va_list arg_ptr ;
 
-    fprintf(stderr, "info%s: ", pidstring ) ;
+    print_prefix("");
     va_start( arg_ptr, fmt ) ;
     vfprintf(stderr,fmt,arg_ptr) ;
     va_end(arg_ptr);
@@ -95,7 +89,7 @@ log_error( const char *fmt, ... )
 {
     va_list arg_ptr ;
 
-    fprintf(stderr, "error%s: ", pidstring  ) ;
+    print_prefix("");
     va_start( arg_ptr, fmt ) ;
     vfprintf(stderr,fmt,arg_ptr) ;
     va_end(arg_ptr);
@@ -107,7 +101,7 @@ log_fatal( const char *fmt, ... )
 {
     va_list arg_ptr ;
 
-    fprintf(stderr, "Fatal%s: ", pidstring  ) ;
+    print_prefix("fatal: ");
     va_start( arg_ptr, fmt ) ;
     vfprintf(stderr,fmt,arg_ptr) ;
     va_end(arg_ptr);
@@ -120,7 +114,8 @@ log_bug( const char *fmt, ... )
 {
     va_list arg_ptr ;
 
-    fprintf(stderr, "\nInternal Error%s: ", pidstring  ) ;
+    putc('\n', stderr );
+    print_prefix("Ooops: ");
     va_start( arg_ptr, fmt ) ;
     vfprintf(stderr,fmt,arg_ptr) ;
     va_end(arg_ptr);
@@ -148,7 +143,7 @@ log_debug( const char *fmt, ... )
 {
     va_list arg_ptr ;
 
-    fprintf(stderr, "DBG%s: ", pidstring  ) ;
+    print_prefix("DBG: ");
     va_start( arg_ptr, fmt ) ;
     vfprintf(stderr,fmt,arg_ptr) ;
     va_end(arg_ptr);
@@ -161,7 +156,7 @@ log_hexdump( const char *text, char *buf, size_t len )
 {
     int i;
 
-    fprintf(stderr, "DBG%s: %s", pidstring,  text );
+    print_prefix(text);
     for(i=0; i < len; i++ )
        fprintf(stderr, " %02X", ((byte*)buf)[i] );
     fputc('\n', stderr);
@@ -171,7 +166,7 @@ log_hexdump( const char *text, char *buf, size_t len )
 void
 log_mpidump( const char *text, MPI a )
 {
-    fprintf(stderr, "DBG%s: %s", pidstring, text );
+    print_prefix(text);
     mpi_print(stderr, a, 1 );
     fputc('\n', stderr);
 }
index e75e2e5..2d2d749 100644 (file)
@@ -6,7 +6,13 @@
 CFLAGS = -O -Wall
 
 EXTRA_DIST = README algorithm.doc ChangeLog example.c
+
+# I found no other easy way to use this only if zlib is neede
+# doing this with SUBDIR = @xxx@  in the top Makefile.am does not
+# work because automake doesn't scan this Makefile.am here.
+if ENABLE_LOCAL_ZLIB
 noinst_LIBRARIES = libzlib.a
+endif
 
 
 libzlib_a_SOURCES = adler32.c compress.c crc32.c gzio.c \
@@ -20,3 +26,4 @@ libzlib_a_SOURCES = adler32.c compress.c crc32.c gzio.c \
 CLEANFILES = example foo.gz
 
 
+