Implement the server comamnd DECRYPT.
authorWerner Koch <wk@gnupg.org>
Fri, 2 Oct 2009 14:57:55 +0000 (14:57 +0000)
committerWerner Koch <wk@gnupg.org>
Fri, 2 Oct 2009 14:57:55 +0000 (14:57 +0000)
Use int instead of gnupg_fd_t in the server.
Comment fixes.
Rename encr-data.c -> decrypt-data.c

12 files changed:
g10/ChangeLog
g10/Makefile.am
g10/decrypt-data.c [moved from g10/encr-data.c with 99% similarity]
g10/decrypt.c
g10/encrypt.c
g10/gpg.c
g10/main.h
g10/openfile.c
g10/options.h
g10/packet.h
g10/plaintext.c
g10/server.c

index 5d96460..11e13fb 100644 (file)
@@ -1,5 +1,15 @@
 2009-10-02  Werner Koch  <wk@g10code.com>
 
+       * server.c (cmd_encrypt, cmd_decrypt): Implement.
+       * decrypt.c (decrypt_message_fd): New.
+       * options.h (struct opt): Add field OUTFP.
+       * plaintext.c (handle_plaintext): Support opt.outfp.
+
+       * encr-data.c: Rename to decrypt-data.c to reflect the action and
+       not the processed packet type.
+
+2009-10-02  Werner Koch  <wk@g10code.com>
+
        * encr-data.c (decode_filter_context_s): Add fields PARTIAL and
        LENGTH.
        (decrypt_data): Set them.  Simplify premature EOF detection.
index 8b505e7..3a05292 100644 (file)
@@ -79,13 +79,13 @@ gpg2_SOURCES  = gpg.c               \
              pubkey-enc.c      \
              passphrase.c      \
              seckey-cert.c     \
-             encr-data.c       \
+             decrypt.c         \
+             decrypt-data.c    \
              cipher.c          \
              encrypt.c         \
              sign.c            \
              verify.c          \
              revoke.c          \
-             decrypt.c         \
              keyedit.c         \
              dearmor.c         \
              import.c          \
similarity index 99%
rename from g10/encr-data.c
rename to g10/decrypt-data.c
index de26d0a..c9da9be 100644 (file)
@@ -1,4 +1,4 @@
-/* encr-data.c -  process an encrypted data packet
+/* decrypt-data.c - Decrypt an encrypted data packet
  * Copyright (C) 1998, 1999, 2000, 2001, 2005,
  *               2006, 2009 Free Software Foundation, Inc.
  *
index c76c295..68b6688 100644 (file)
@@ -97,6 +97,73 @@ decrypt_message (const char *filename)
 }
 
 
+/* Same as decrypt_message but takes a file descriptor for input and
+   output.  */
+gpg_error_t
+decrypt_message_fd (int input_fd, int output_fd)
+{
+  gpg_error_t err;
+  IOBUF fp;
+  armor_filter_context_t *afx = NULL;
+  progress_filter_context_t *pfx;
+
+  if (opt.outfp)
+    return gpg_error (GPG_ERR_BUG);
+
+  pfx = new_progress_context ();
+  
+  /* Open the message file.  */
+  fp = iobuf_open_fd_or_name (input_fd, NULL, "rb");
+  if (fp && is_secured_file (iobuf_get_fd (fp)))
+    {
+      iobuf_close (fp);
+      fp = NULL;
+      errno = EPERM;
+    }
+  if (!fp)
+    {
+      char xname[64];
+      
+      err = gpg_error_from_syserror ();
+      snprintf (xname, sizeof xname, "[fd %d]", input_fd);
+      log_error (_("can't open `%s': %s\n"), xname, gpg_strerror (err));
+      release_progress_context (pfx);
+      return err;
+    }
+
+  opt.outfp = fdopen (dup (output_fd), "wb");
+  if (!opt.outfp)
+    {
+      char xname[64];
+
+      err = gpg_error_from_syserror ();
+      snprintf (xname, sizeof xname, "[fd %d]", output_fd);
+      log_error (_("can't open `%s': %s\n"), xname, gpg_strerror (err));
+      iobuf_close (fp);
+      release_progress_context (pfx);
+      return err;
+    }
+
+  if (!opt.no_armor)
+    {
+      if (use_armor_filter (fp))
+        {
+          afx = new_armor_context ();
+          push_armor_filter ( afx, fp );
+       }
+    }
+
+  err = proc_encryption_packets ( NULL, fp );
+
+  iobuf_close (fp);
+  fclose (opt.outfp);
+  opt.outfp = NULL;
+  release_armor_context (afx);
+  release_progress_context (pfx);
+  return err;
+}
+
+
 void
 decrypt_messages (int nfiles, char *files[])
 {
index bb3f243..649ea33 100644 (file)
@@ -264,8 +264,7 @@ encrypt_simple (const char *filename, int mode, int use_seskey)
       do_compress = 0;        
     }
   
-  if ( rc || (rc = open_outfile (GNUPG_INVALID_FD, filename,
-                                 opt.armor? 1:0, &out )))
+  if ( rc || (rc = open_outfile (-1, filename, opt.armor? 1:0, &out )))
     {
       iobuf_cancel (inp);
       xfree (cfx.dek);
@@ -462,9 +461,9 @@ write_symkey_enc (STRING2KEY *symkey_s2k, DEK *symkey_dek, DEK *dek,
  * PROVIDED_PKS; if not the function builds a list of keys on its own.
  */
 int
-encrypt_crypt (gnupg_fd_t filefd, const char *filename,
+encrypt_crypt (int filefd, const char *filename,
                strlist_t remusr, int use_symkey, pk_list_t provided_keys,
-               gnupg_fd_t outputfd)
+               int outputfd)
 {
   iobuf_t inp = NULL;
   iobuf_t out = NULL;
@@ -482,7 +481,7 @@ encrypt_crypt (gnupg_fd_t filefd, const char *filename,
   PK_LIST pk_list, work_list;
   int do_compress;
 
-  if (filefd != GNUPG_INVALID_FD && filename)
+  if (filefd != -1 && filename)
     return gpg_error (GPG_ERR_INV_ARG);
 
   do_compress = opt.compress_algo && !RFC1991;
@@ -539,7 +538,7 @@ encrypt_crypt (gnupg_fd_t filefd, const char *filename,
       char xname[64];
 
       rc = gpg_error_from_syserror ();
-      if (filefd != GNUPG_INVALID_FD)
+      if (filefd != -1)
         snprintf (xname, sizeof xname, "[fd %d]", filefd);
       else if (!filename)
         strcpy (xname, "[stdin]");
@@ -652,7 +651,7 @@ encrypt_crypt (gnupg_fd_t filefd, const char *filename,
   if (!opt.no_literal)
     pt = setup_plaintext_name (filename, inp);
   
-  if (filefd != GNUPG_INVALID_FD 
+  if (filefd != -1
       && !iobuf_is_pipe_filename (filename) && *filename && !opt.textmode )
     {
       off_t tmpsize;
@@ -964,8 +963,7 @@ encrypt_crypt_files (int nfiles, char **files, strlist_t remusr)
             }
           line[strlen(line)-1] = '\0';
           print_file_status(STATUS_FILE_START, line, 2);
-          rc = encrypt_crypt (GNUPG_INVALID_FD, line, remusr, 0,
-                              NULL, GNUPG_INVALID_FD);
+          rc = encrypt_crypt (-1, line, remusr, 0, NULL, -1);
           if (rc)
             log_error ("encryption of `%s' failed: %s\n",
                        print_fname_stdin(line), g10_errstr(rc) );
@@ -977,8 +975,7 @@ encrypt_crypt_files (int nfiles, char **files, strlist_t remusr)
       while (nfiles--)
         {
           print_file_status(STATUS_FILE_START, *files, 2);
-          if ( (rc = encrypt_crypt (GNUPG_INVALID_FD, *files, remusr, 0,
-                                    NULL, GNUPG_INVALID_FD)) )
+          if ( (rc = encrypt_crypt (-1, *files, remusr, 0, NULL, -1)) )
             log_error("encryption of `%s' failed: %s\n",
                       print_fname_stdin(*files), g10_errstr(rc) );
           write_status( STATUS_FILE_DONE );
index 55ba2cd..5b70e4f 100644 (file)
--- a/g10/gpg.c
+++ b/g10/gpg.c
@@ -3434,8 +3434,7 @@ main (int argc, char **argv)
          {
            if( argc > 1 )
              wrong_args(_("--encrypt [filename]"));
-           if( (rc = encrypt_crypt (GNUPG_INVALID_FD, fname,
-                                     remusr, 0, NULL, GNUPG_INVALID_FD)) )
+           if( (rc = encrypt_crypt (-1, fname, remusr, 0, NULL, -1)) )
              log_error("%s: encryption failed: %s\n",
                        print_fname_stdin(fname), g10_errstr(rc) );
          }
@@ -3456,8 +3455,7 @@ main (int argc, char **argv)
                      " while in %s mode\n"),compliance_option_string());
        else
          {
-           if( (rc = encrypt_crypt (GNUPG_INVALID_FD, fname, 
-                                     remusr, 1, NULL, GNUPG_INVALID_FD)) )
+           if( (rc = encrypt_crypt (-1, fname, remusr, 1, NULL, -1)) )
              log_error("%s: encryption failed: %s\n",
                        print_fname_stdin(fname), g10_errstr(rc) );
          }
index 4971154..9dfeed3 100644 (file)
@@ -185,9 +185,9 @@ void display_online_help( const char *keyword );
 int setup_symkey (STRING2KEY **symkey_s2k,DEK **symkey_dek);
 int encrypt_symmetric (const char *filename );
 int encrypt_store (const char *filename );
-int encrypt_crypt (gnupg_fd_t filefd, const char *filename,
+int encrypt_crypt (int filefd, const char *filename,
                    strlist_t remusr, int use_symkey, pk_list_t provided_keys,
-                   gnupg_fd_t outputfd);
+                   int outputfd);
 void encrypt_crypt_files (int nfiles, char **files, strlist_t remusr);
 int encrypt_filter (void *opaque, int control,
                    iobuf_t a, byte *buf, size_t *ret_len);
@@ -245,7 +245,7 @@ int save_unprotected_key_to_card (PKT_secret_key *sk, int keyno);
 int overwrite_filep( const char *fname );
 char *make_outfile_name( const char *iname );
 char *ask_outfile_name( const char *name, size_t namelen );
-int open_outfile (gnupg_fd_t inp_fd, const char *iname, int mode, iobuf_t *a);
+int open_outfile (int inp_fd, const char *iname, int mode, iobuf_t *a);
 iobuf_t open_sigfile( const char *iname, progress_filter_context_t *pfx );
 void try_make_homedir( const char *fname );
 
@@ -319,6 +319,7 @@ int gpg_verify (ctrl_t ctrl, int sig_fd, int data_fd, FILE *out_fp);
 
 /*-- decrypt.c --*/
 int decrypt_message( const char *filename );
+gpg_error_t decrypt_message_fd (int input_fd, int output_fd);
 void decrypt_messages(int nfiles, char *files[]);
 
 /*-- plaintext.c --*/
index 5908b2e..9f41273 100644 (file)
@@ -178,24 +178,24 @@ ask_outfile_name( const char *name, size_t namelen )
  * Mode 0 = use ".gpg"
  *     1 = use ".asc"
  *     2 = use ".sig"
-
- * If INP_FD is not GNUPG_INVALID_FD the function will simply create
- * an IOBUF for that file descriptor and ignore a INAME and MODE.
- * Note that INP_FD won't be closed if the returned IOBUF is closed.
+ *
+ * If INP_FD is not -1 the function simply creates an IOBUF for that
+ * file descriptor and ignorea INAME and MODE.  Note that INP_FD won't
+ * be closed if the returned IOBUF is closed.
  */
 int
-open_outfile (gnupg_fd_t inp_fd, const char *iname, int mode, iobuf_t *a)
+open_outfile (int inp_fd, const char *iname, int mode, iobuf_t *a)
 {
   int rc = 0;
 
   *a = NULL;
-  if (inp_fd != GNUPG_INVALID_FD)
+  if (inp_fd != -1)
     {
       char xname[64];
-      gnupg_fd_t fd2;
+      int fd2;
       
-      fd2 = INT2FD (dup (FD2INT (inp_fd)));
-      if (fd2 == GNUPG_INVALID_FD)
+      fd2 = dup (inp_fd);
+      if (fd2 == -1)
         *a = NULL;
       else
         *a = iobuf_fdopen (fd2, "wb");
index a99ca22..3a2a68e 100644 (file)
@@ -43,6 +43,7 @@ struct
   unsigned debug;
   int armor;
   char *outfile;
+  FILE *outfp;      /* Hack, sometimes used in place of outfile.  */
   off_t max_output;
   int dry_run;
   int list_only;
index cb2f0c9..395e70a 100644 (file)
@@ -289,8 +289,8 @@ typedef struct {
 } PKT_compressed;
 
 typedef struct {
-    u32  len;            /* length of encrypted data */
-    int  extralen;        /* this is (blocksize+2) */
+    u32  len;            /* Remaining length of encrypted data. */
+    int  extralen;        /* This is (blocksize+2).  Used by build_packet. */
     byte new_ctb;        /* uses a new CTB */
     byte is_partial;      /* partial length encoded */
     byte mdc_method;     /* > 0: integrity protected encrypted data packet */
index 7679626..d1ab923 100644 (file)
@@ -86,10 +86,13 @@ handle_plaintext (PKT_plaintext * pt, md_filter_context_t * mfx,
   /* Create the filename as C string.  */
   if (nooutput)
     ;
+  else if (opt.outfp)
+    {
+      fname = xstrdup ("[FP]");
+    }
   else if (opt.outfile)
     {
-      fname = xmalloc (strlen (opt.outfile) + 1);
-      strcpy (fname, opt.outfile);
+      fname = xstrdup (opt.outfile);
     }
   else if (pt->namelen == 8 && !memcmp (pt->name, "_CONSOLE", 8))
     {
@@ -112,6 +115,13 @@ handle_plaintext (PKT_plaintext * pt, md_filter_context_t * mfx,
 
   if (nooutput)
     ;
+  else if (opt.outfp)
+    {
+      fp = opt.outfp;
+#ifdef HAVE_DOSISH_SYSTEM
+      setmode (fileno (fp), O_BINARY);
+#endif
+    }
   else if (iobuf_is_pipe_filename (fname) || !*fname)
     {
       /* No filename or "-" given; write to stdout. */
@@ -138,7 +148,13 @@ handle_plaintext (PKT_plaintext * pt, md_filter_context_t * mfx,
     }
   
 #ifndef __riscos__
-  if (fp || nooutput)
+  if (opt.outfp && is_secured_file (fileno (opt.outfp)))
+    {
+      rc = gpg_error (GPG_ERR_EPERM);
+      log_error (_("error creating `%s': %s\n"), fname, gpg_strerror (rc));
+      goto leave;
+    }
+  else if (fp || nooutput)
     ;
   else if (is_secured_filename (fname))
     {
@@ -154,9 +170,9 @@ handle_plaintext (PKT_plaintext * pt, md_filter_context_t * mfx,
       goto leave;
     }
 #else /* __riscos__ */
-  /* If no output filename was given, i.e. we constructed it,
-     convert all '.' in fname to '/' but not vice versa as
-     we don't create directories! */
+  /* If no output filename was given, i.e. we constructed it, convert
+     all '.' in fname to '/' but not vice versa as we don't create
+     directories! */
   if (!opt.outfile)
     for (c = 0; fname[c]; ++c)
       if (fname[c] == '.')
@@ -418,7 +434,7 @@ handle_plaintext (PKT_plaintext * pt, md_filter_context_t * mfx,
       pt->buf = NULL;
     }
 
-  if (fp && fp != stdout && fclose (fp))
+  if (fp && fp != stdout && fp != opt.outfp && fclose (fp))
     {
       rc = (errno ? gpg_error_from_syserror ()
            : gpg_error (GPG_ERR_INTERNAL));
@@ -434,7 +450,7 @@ handle_plaintext (PKT_plaintext * pt, md_filter_context_t * mfx,
      before checking the signature.  */
   fflush (stdout);
 
-  if (fp && fp != stdout)
+  if (fp && fp != stdout && fp != opt.outfp)
     fclose (fp);
   xfree (fname);
   return rc;
index 33f9bb6..478c0ec 100644 (file)
@@ -362,7 +362,7 @@ cmd_decrypt (assuan_context_t ctx, char *line)
   if (out_fd == -1)
     return set_error (GPG_ERR_ASS_NO_OUTPUT, NULL);
 
-  err = gpg_error (GPG_ERR_NOT_IMPLEMENTED);
+  err = decrypt_message_fd (inp_fd, out_fd);
 
   /* Close and reset the fds. */
   close_message_fd (ctrl);