Make use of the *_NAME etc macros.
[gnupg.git] / g10 / server.c
index f67a346..8bf7a08 100644 (file)
 
 
 /* Data used to associate an Assuan context with local server data.  */
-struct server_local_s 
+struct server_local_s
 {
   /* Our current Assuan context. */
-  assuan_context_t assuan_ctx;  
+  assuan_context_t assuan_ctx;
   /* File descriptor as set by the MESSAGE command. */
-  gnupg_fd_t message_fd;               
+  gnupg_fd_t message_fd;
 
   /* List of prepared recipients.  */
   pk_list_t recplist;
 
+  /* Set if pinentry notifications should be passed back to the
+     client. */
+  int allow_pinentry_notify;
 };
 
 
 \f
 /* Helper to close the message fd if it is open. */
-static void 
+static void
 close_message_fd (ctrl_t ctrl)
 {
   if (ctrl->server_local->message_fd != GNUPG_INVALID_FD)
     {
       assuan_sock_close (ctrl->server_local->message_fd);
       ctrl->server_local->message_fd = GNUPG_INVALID_FD;
-    } 
+    }
 }
 
 
@@ -89,7 +92,7 @@ has_option (const char *line, const char *name)
 {
   const char *s;
   int n = strlen (name);
-  
+
   s = strstr (line, name);
   if (s && s >= skip_options (line))
     return 0;
@@ -105,9 +108,8 @@ has_option (const char *line, const char *name)
 static gpg_error_t
 option_handler (assuan_context_t ctx, const char *key, const char *value)
 {
-/*   ctrl_t ctrl = assuan_get_pointer (ctx); */
+  ctrl_t ctrl = assuan_get_pointer (ctx);
 
-  (void)ctx;
   (void)value;
 
   /* Fixme: Implement the tty and locale args. */
@@ -136,6 +138,10 @@ option_handler (assuan_context_t ctx, const char *key, const char *value)
     {
       /* This is for now a dummy option. */
     }
+  else if (!strcmp (key, "allow-pinentry-notify"))
+    {
+      ctrl->server_local->allow_pinentry_notify = 1;
+    }
   else
     return gpg_error (GPG_ERR_UNKNOWN_OPTION);
 
@@ -188,7 +194,7 @@ static gpg_error_t
 output_notify (assuan_context_t ctx, char *line)
 {
 /*   ctrl_t ctrl = assuan_get_pointer (ctx); */
-  
+
   (void)ctx;
 
   if (strstr (line, "--armor"))
@@ -231,9 +237,9 @@ cmd_recipient (assuan_context_t ctx, char *line)
     remusr = rcpts;
   */
 
-  err = find_and_check_key (line, PUBKEY_USAGE_ENC, hidden, 
+  err = find_and_check_key (ctrl, line, PUBKEY_USAGE_ENC, hidden,
                             &ctrl->server_local->recplist);
-  
+
   if (err)
     log_error ("command '%s' failed: %s\n", "RECIPIENT", gpg_strerror (err));
   return err;
@@ -266,7 +272,7 @@ cmd_signer (assuan_context_t ctx, char *line)
 
 
 \f
-/*  ENCRYPT 
+/*  ENCRYPT
 
    Do the actual encryption process.  Takes the plaintext from the
    INPUT command, writes the ciphertext to the file descriptor set
@@ -294,7 +300,7 @@ cmd_encrypt (assuan_context_t ctx, char *line)
 
   (void)line; /* LINE is not used.  */
 
-  if ( !ctrl->server_local->recplist ) 
+  if ( !ctrl->server_local->recplist )
     {
       write_status_text (STATUS_NO_RECP, "0");
       err = gpg_error (GPG_ERR_NO_USER_ID);
@@ -318,13 +324,13 @@ cmd_encrypt (assuan_context_t ctx, char *line)
      PGP-2 mode.  Do all the other checks we do in gpg.c for aEncr.
      Maybe we should drop the PGP2 compatibility. */
 
-  
+
   /* FIXME: GPGSM does this here: Add all encrypt-to marked recipients
      from the default list. */
 
   /* fixme: err = ctrl->audit? 0 : start_audit_session (ctrl);*/
-    
-  err = encrypt_crypt (inp_fd, NULL, NULL, 0,
+
+  err = encrypt_crypt (ctrl, inp_fd, NULL, NULL, 0,
                        ctrl->server_local->recplist,
                        out_fd);
 
@@ -368,7 +374,7 @@ cmd_decrypt (assuan_context_t ctx, char *line)
     return set_error (GPG_ERR_ASS_NO_OUTPUT, NULL);
 
   glo_ctrl.lasterr = 0;
-  err = decrypt_message_fd (inp_fd, out_fd);
+  err = decrypt_message_fd (ctrl, inp_fd, out_fd);
   if (!err)
     err = glo_ctrl.lasterr;
 
@@ -389,7 +395,7 @@ cmd_decrypt (assuan_context_t ctx, char *line)
    This does a verify operation on the message send to the input-FD.
    The result is written out using status lines.  If an output FD was
    given, the signed text will be written to that.
-  
+
    If the signature is a detached one, the server will inquire about
    the signed material and the client must provide it.
  */
@@ -404,7 +410,7 @@ cmd_verify (assuan_context_t ctx, char *line)
 
   /* FIXME: Revamp this code it is nearly to 3 years old and was only
      intended as a quick test.  */
-  
+
   (void)line;
 
   if (fd == GNUPG_INVALID_FD)
@@ -620,7 +626,7 @@ cmd_passwd (assuan_context_t ctx, char *line)
 static int
 register_commands (assuan_context_t ctx)
 {
-  static struct 
+  static struct
   {
     const char *name;
     assuan_handler_t handler;
@@ -634,8 +640,8 @@ register_commands (assuan_context_t ctx)
     { "SIGN",          cmd_sign      },
     { "IMPORT",        cmd_import    },
     { "EXPORT",        cmd_export    },
-    { "INPUT",         NULL          }, 
-    { "OUTPUT",        NULL          }, 
+    { "INPUT",         NULL          },
+    { "OUTPUT",        NULL          },
     { "MESSAGE",       cmd_message   },
     { "LISTKEYS",      cmd_listkeys  },
     { "LISTSECRETKEYS",cmd_listsecretkeys },
@@ -653,7 +659,7 @@ register_commands (assuan_context_t ctx)
                                     table[i].handler, table[i].help);
       if (rc)
         return rc;
-    } 
+    }
   return 0;
 }
 
@@ -683,7 +689,7 @@ gpg_server (ctrl_t ctrl)
                 gpg_strerror (rc));
       goto leave;
     }
-  
+
   rc = assuan_init_pipe_server (ctx, filedes);
   if (rc)
     {
@@ -703,7 +709,7 @@ gpg_server (ctrl_t ctrl)
   if (opt.verbose || opt.debug)
     {
       char *tmp = NULL;
-      const char *s1 = getenv ("GPG_AGENT_INFO");
+      const char *s1 = getenv (GPG_AGENT_INFO_NAME);
 
       tmp = xtryasprintf ("Home: %s\n"
                           "Config: %s\n"
@@ -748,7 +754,7 @@ gpg_server (ctrl_t ctrl)
           log_info ("Assuan accept problem: %s\n", gpg_strerror (rc));
           break;
         }
-      
+
       rc = assuan_process (ctx);
       if (rc)
         {
@@ -769,3 +775,28 @@ gpg_server (ctrl_t ctrl)
   return rc;
 }
 
+
+/* Helper to notify the client about Pinentry events.  Because that
+   might disturb some older clients, this is only done when enabled
+   via an option.  If it is not enabled we tell Windows to allow
+   setting the foreground window right here.  Returns an gpg error
+   code. */
+gpg_error_t
+gpg_proxy_pinentry_notify (ctrl_t ctrl, const unsigned char *line)
+{
+  if (!ctrl || !ctrl->server_local
+      || !ctrl->server_local->allow_pinentry_notify)
+    {
+      gnupg_allow_set_foregound_window ((pid_t)strtoul (line+17, NULL, 10));
+      /* Client might be interested in that event - send as status line.  */
+      if (!strncmp (line, "PINENTRY_LAUNCHED", 17)
+          && (line[17]==' '||!line[17]))
+        {
+          for (line += 17; *line && spacep (line); line++)
+            ;
+          write_status_text (STATUS_PINENTRY_LAUNCHED, line);
+        }
+      return 0;
+    }
+  return assuan_inquire (ctrl->server_local->assuan_ctx, line, NULL, NULL, 0);
+}