Various changes
[gnupg.git] / agent / call-scd.c
1 /* call-scd.c - fork of the scdaemon to do SC operations
2  *      Copyright (C) 2001, 2002, 2005 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 2 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, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
19  * USA.
20  */
21
22 #include <config.h>
23 #include <errno.h>
24 #include <stdio.h>
25 #include <stdlib.h>
26 #include <string.h>
27 #include <ctype.h>
28 #include <assert.h>
29 #include <unistd.h>
30 #include <signal.h>
31 #include <sys/stat.h>
32 #include <sys/types.h>
33 #ifndef HAVE_W32_SYSTEM
34 #include <sys/wait.h>
35 #endif
36 #include <pth.h>
37
38 #include "agent.h"
39 #include <assuan.h>
40
41 #ifdef _POSIX_OPEN_MAX
42 #define MAX_OPEN_FDS _POSIX_OPEN_MAX
43 #else
44 #define MAX_OPEN_FDS 20
45 #endif
46
47 /* Definition of module local data of the CTRL structure.  */
48 struct scd_local_s
49 {
50   /* We keep a list of all allocated context with a an achnor at
51      SCD_LOCAL_LIST (see below). */
52   struct scd_local_s *next_local;
53
54   /* We need to get back to the ctrl object actually referencing this
55      structure.  This is really an awkward way of enumerint the lcoal
56      contects.  A much cleaner way would be to keep a global list of
57      ctrl objects to enumerate them.  */
58   ctrl_t ctrl_backlink;
59
60   assuan_context_t ctx; /* NULL or session context for the SCdaemon
61                            used with this connection. */
62   int locked;           /* This flag is used to assert proper use of
63                            start_scd and unlock_scd. */
64
65 };
66
67
68 /* Callback parameter for learn card */
69 struct learn_parm_s
70 {
71   void (*kpinfo_cb)(void*, const char *);
72   void *kpinfo_cb_arg;
73   void (*certinfo_cb)(void*, const char *);
74   void *certinfo_cb_arg;
75   void (*sinfo_cb)(void*, const char *, size_t, const char *);
76   void *sinfo_cb_arg;
77 };
78
79 struct inq_needpin_s 
80 {
81   assuan_context_t ctx;
82   int (*getpin_cb)(void *, const char *, char*, size_t);
83   void *getpin_cb_arg;
84 };
85
86
87 /* To keep track of all active SCD contexts, we keep a linked list
88    anchored at this variable. */
89 static struct scd_local_s *scd_local_list;
90
91 /* A Mutex used inside the start_scd function. */
92 static pth_mutex_t start_scd_lock;
93
94 /* A malloced string with the name of the socket to be used for
95    additional connections.  May be NULL if not provided by
96    SCdaemon. */
97 static char *socket_name;
98
99 /* The context of the primary connection.  This is also used as a flag
100    to indicate whether the scdaemon has been started. */
101 static assuan_context_t primary_scd_ctx;
102
103 /* To allow reuse of the primary connection, the following flag is set
104    to true if the primary context has been reset and is not in use by
105    any connection. */
106 static int primary_scd_ctx_reusable;
107
108
109
110 /* Local prototypes.  */
111 static assuan_error_t membuf_data_cb (void *opaque,
112                                       const void *buffer, size_t length);
113
114
115
116 \f
117 /* This function must be called once to initialize this module.  This
118    has to be done before a second thread is spawned.  We can't do the
119    static initialization because Pth emulation code might not be able
120    to do a static init; in particular, it is not possible for W32. */
121 void
122 initialize_module_call_scd (void)
123 {
124   static int initialized;
125
126   if (!initialized)
127     {
128       if (!pth_mutex_init (&start_scd_lock))
129         log_fatal ("error initializing mutex: %s\n", strerror (errno));
130       initialized = 1;
131     }
132 }
133
134
135 static void
136 dump_mutex_state (pth_mutex_t *m)
137 {
138   if (!(m->mx_state & PTH_MUTEX_INITIALIZED))
139     log_printf ("not_initialized");
140   else if (!(m->mx_state & PTH_MUTEX_LOCKED))
141     log_printf ("not_locked");
142   else
143     log_printf ("locked tid=0x%lx count=%lu", (long)m->mx_owner, m->mx_count);
144 }
145
146
147 /* This function may be called to print infromation pertaining to the
148    current state of this module to the log. */
149 void
150 agent_scd_dump_state (void)
151 {
152   log_info ("agent_scd_dump_state: scd_lock=");
153   dump_mutex_state (&start_scd_lock);
154   log_printf ("\n");
155   log_info ("agent_scd_dump_state: primary_scd_ctx=%p pid=%ld reusable=%d\n",
156             primary_scd_ctx, 
157             (long)assuan_get_pid (primary_scd_ctx),
158             primary_scd_ctx_reusable);
159   if (socket_name)
160     log_info ("agent_scd_dump_state: socket=`%s'\n", socket_name);
161 }
162
163
164 /* The unlock_scd function shall be called after having accessed the
165    SCD.  It is currently not very useful but gives an opportunity to
166    keep track of connections currently calling SCD.  Note that the
167    "lock" operation is done by the start_scd() function which must be
168    called and error checked before any SCD operation.  CTRL is the
169    usual connection context and RC the error code to be passed trhough
170    the function. */
171 static int 
172 unlock_scd (ctrl_t ctrl, int rc)
173 {
174   if (ctrl->scd_local->locked != 1)
175     {
176       log_error ("unlock_scd: invalid lock count (%d)\n",
177                  ctrl->scd_local->locked);
178       if (!rc)
179         rc = gpg_error (GPG_ERR_INTERNAL);
180     }
181   ctrl->scd_local->locked = 0;
182   return rc;
183 }
184
185 /* To make sure we leave no secrets in our image after forking of the
186    scdaemon, we use this callback. */
187 static void
188 atfork_cb (void *opaque, int where)
189 {
190   if (!where)
191     gcry_control (GCRYCTL_TERM_SECMEM);
192 }
193
194
195 /* Fork off the SCdaemon if this has not already been done.  Lock the
196    daemon and make sure that a proper context has been setup in CTRL.
197    This function might also lock the daemon, which means that the
198    caller must call unlock_scd after this fucntion has returned
199    success and the actual Assuan transaction been done. */
200 static int
201 start_scd (ctrl_t ctrl)
202 {
203   gpg_error_t err = 0;
204   const char *pgmname;
205   assuan_context_t ctx;
206   const char *argv[3];
207   int no_close_list[3];
208   int i;
209   int rc;
210
211   if (opt.disable_scdaemon)
212     return gpg_error (GPG_ERR_NOT_SUPPORTED);
213
214   /* If this is the first call for this session, setup the local data
215      structure. */
216   if (!ctrl->scd_local)
217     {
218       ctrl->scd_local = xtrycalloc (1, sizeof *ctrl->scd_local);
219       if (!ctrl->scd_local)
220         return gpg_error_from_syserror ();
221       ctrl->scd_local->ctrl_backlink = ctrl;
222       ctrl->scd_local->next_local = scd_local_list;
223       scd_local_list = ctrl->scd_local;
224     }
225
226
227   /* Assert that the lock count is as expected. */
228   if (ctrl->scd_local->locked)
229     {
230       log_error ("start_scd: invalid lock count (%d)\n",
231                  ctrl->scd_local->locked);
232       return gpg_error (GPG_ERR_INTERNAL);
233     }
234   ctrl->scd_local->locked++;
235
236   if (ctrl->scd_local->ctx)
237     return 0; /* Okay, the context is fine.  We used to test for an
238                  alive context here and do an disconnect.  Now that we
239                  have a ticker function to check for it, it is easier
240                  not to check here but to let the connection run on an
241                  error instead. */
242
243
244   /* We need to protect the following code. */
245   if (!pth_mutex_acquire (&start_scd_lock, 0, NULL))
246     {
247       log_error ("failed to acquire the start_scd lock: %s\n",
248                  strerror (errno));
249       return gpg_error (GPG_ERR_INTERNAL);
250     }
251
252   /* Check whether the pipe server has already been started and in
253      this case either reuse a lingering pipe connection or establish a
254      new socket based one. */
255   if (primary_scd_ctx && primary_scd_ctx_reusable)
256     {
257       ctx = primary_scd_ctx;
258       primary_scd_ctx_reusable = 0;
259       if (opt.verbose)
260         log_info ("new connection to SCdaemon established (reusing)\n");
261       goto leave;
262     }
263
264   if (socket_name)
265     {
266       rc = assuan_socket_connect (&ctx, socket_name, 0);
267       if (rc)
268         {
269           log_error ("can't connect to socket `%s': %s\n",
270                      socket_name, gpg_strerror (rc));
271           err = gpg_error (GPG_ERR_NO_SCDAEMON);
272           goto leave;
273         }
274
275       if (opt.verbose)
276         log_info ("new connection to SCdaemon established\n");
277       goto leave;
278     }
279
280   if (primary_scd_ctx)
281     {
282       log_info ("SCdaemon is running but won't accept further connections\n");
283       err = gpg_error (GPG_ERR_NO_SCDAEMON);
284       goto leave;
285     }
286
287   /* Nope, it has not been started.  Fire it up now. */
288   if (opt.verbose)
289     log_info ("no running SCdaemon - starting it\n");
290       
291   if (fflush (NULL))
292     {
293       err = gpg_error (gpg_err_code_from_errno (errno));
294       log_error ("error flushing pending output: %s\n", strerror (errno));
295       goto leave;
296     }
297
298   if (!opt.scdaemon_program || !*opt.scdaemon_program)
299     opt.scdaemon_program = GNUPG_DEFAULT_SCDAEMON;
300   if ( !(pgmname = strrchr (opt.scdaemon_program, '/')))
301     pgmname = opt.scdaemon_program;
302   else
303     pgmname++;
304
305   argv[0] = pgmname;
306   argv[1] = "--multi-server";
307   argv[2] = NULL;
308
309   i=0;
310   if (!opt.running_detached)
311     {
312       if (log_get_fd () != -1)
313         no_close_list[i++] = log_get_fd ();
314       no_close_list[i++] = fileno (stderr);
315     }
316   no_close_list[i] = -1;
317
318   /* Connect to the pinentry and perform initial handshaking */
319   rc = assuan_pipe_connect_ext (&ctx, opt.scdaemon_program, argv,
320                                 no_close_list, atfork_cb, NULL, 0);
321   if (rc)
322     {
323       log_error ("can't connect to the SCdaemon: %s\n",
324                  gpg_strerror (rc));
325       err = gpg_error (GPG_ERR_NO_SCDAEMON);
326       goto leave;
327     }
328
329   if (opt.verbose)
330     log_debug ("first connection to SCdaemon established\n");
331
332   /* Get the name of the additional socket opened by scdaemon. */
333   {
334     membuf_t data;
335     unsigned char *databuf;
336     size_t datalen;
337
338     xfree (socket_name);
339     socket_name = NULL;
340     init_membuf (&data, 256);
341     assuan_transact (ctx, "GETINFO socket_name",
342                      membuf_data_cb, &data, NULL, NULL, NULL, NULL);
343
344     databuf = get_membuf (&data, &datalen);
345     if (databuf && datalen)
346       {
347         socket_name = xtrymalloc (datalen + 1);
348         if (!socket_name)
349           log_error ("warning: can't store socket name: %s\n",
350                      strerror (errno));
351         else
352           {
353             memcpy (socket_name, databuf, datalen);
354             socket_name[datalen] = 0;
355             if (DBG_ASSUAN)
356               log_debug ("additional connections at `%s'\n", socket_name);
357           }
358       }
359     xfree (databuf);
360   }
361
362   /* Tell the scdaemon we want him to send us an event signal. */
363 #ifndef HAVE_W32_SYSTEM
364   {
365     char buf[100];
366
367     sprintf (buf, "OPTION event-signal=%d", SIGUSR2);
368     assuan_transact (ctx, buf, NULL, NULL, NULL, NULL, NULL, NULL);
369   }
370 #endif
371
372   primary_scd_ctx = ctx;
373   primary_scd_ctx_reusable = 0;
374
375  leave:
376   if (err)
377     {
378       unlock_scd (ctrl, err);
379     } 
380   else
381     {
382       ctrl->scd_local->ctx = ctx;
383     }
384   if (!pth_mutex_release (&start_scd_lock))
385     log_error ("failed to release the start_scd lock: %s\n", strerror (errno));
386   return err;
387 }
388
389
390 /* Check whether the Scdaemon is still alive and clean it up if not. */
391 void
392 agent_scd_check_aliveness (void)
393 {
394   pth_event_t evt;
395   pid_t pid;
396   int rc;
397
398   if (!primary_scd_ctx)
399     return; /* No scdaemon running. */
400
401   /* This is not a critical function so we use a short timeout while
402      acquiring the lock.  */
403   evt = pth_event (PTH_EVENT_TIME, pth_timeout (1, 0));
404   if (!pth_mutex_acquire (&start_scd_lock, 0, evt))
405     {
406       if (pth_event_occurred (evt))
407         {
408           if (opt.verbose > 1)
409             log_info ("failed to acquire the start_scd lock while"
410                       " doing an aliveness check: %s\n", "timeout");
411         }
412       else
413         log_error ("failed to acquire the start_scd lock while"
414                    " doing an aliveness check: %s\n", strerror (errno));
415       pth_event_free (evt, PTH_FREE_THIS);
416       return;
417     }
418   pth_event_free (evt, PTH_FREE_THIS);
419
420   if (primary_scd_ctx)
421     {
422       pid = assuan_get_pid (primary_scd_ctx);
423       if (pid != (pid_t)(-1) && pid
424           && ((rc=waitpid (pid, NULL, WNOHANG))==-1 || (rc == pid)) )
425         {
426           /* Okay, scdaemon died.  Disconnect the primary connection
427              now but take care that it won't do another wait. Also
428              cleanup all other connections and release their
429              resources.  The next use will start a new daemon then.
430              Due to the use of the START_SCD_LOCAL we are sure that
431              none of these context are actually in use. */
432           struct scd_local_s *sl;
433
434           assuan_set_flag (primary_scd_ctx, ASSUAN_NO_WAITPID, 1);
435           assuan_disconnect (primary_scd_ctx);
436
437           for (sl=scd_local_list; sl; sl = sl->next_local)
438             {
439               if (sl->ctx)
440                 {
441                   if (sl->ctx != primary_scd_ctx)
442                     assuan_disconnect (sl->ctx);
443                   sl->ctx = NULL;
444                 }
445             }
446           
447           primary_scd_ctx = NULL;
448           primary_scd_ctx_reusable = 0;
449
450           xfree (socket_name);
451           socket_name = NULL;
452         }
453     }
454
455   if (!pth_mutex_release (&start_scd_lock))
456     log_error ("failed to release the start_scd lock while"
457                " doing the aliveness check: %s\n", strerror (errno));
458 }
459
460
461
462 /* Reset the SCD if it has been used.  Actually it is not a reset but
463    a cleanup of resources used by the current connection. */
464 int
465 agent_reset_scd (ctrl_t ctrl)
466 {
467   if (ctrl->scd_local)
468     {
469       if (ctrl->scd_local->ctx)
470         {
471           /* We can't disconnect the primary context because libassuan
472              does a waitpid on it and thus the system would hang.
473              Instead we send a reset and keep that connection for
474              reuse. */
475           if (ctrl->scd_local->ctx == primary_scd_ctx)
476             {
477               /* Send a RESTART to the SCD.  This is required for the
478                  primary connection as a kind of virtual EOF; we don't
479                  have another way to tell it that the next command
480                  should be viewed as if a new connection has been
481                  made.  For the non-primary connections this is not
482                  needed as we simply close the socket.  We don't check
483                  for an error here because the RESTART may fail for
484                  example if the scdaemon has already been terminated.
485                  Anyway, we need to set the reusable flag to make sure
486                  that the aliveness check can clean it up. */
487               assuan_transact (primary_scd_ctx, "RESTART",
488                                NULL, NULL, NULL, NULL, NULL, NULL);
489               primary_scd_ctx_reusable = 1;
490             }
491           else
492             assuan_disconnect (ctrl->scd_local->ctx);
493           ctrl->scd_local->ctx = NULL;
494         }
495       
496       /* Remove the local context from our list and release it. */
497       if (!scd_local_list)
498         BUG ();
499       else if (scd_local_list == ctrl->scd_local)
500         scd_local_list = ctrl->scd_local->next_local;
501       else
502         {
503           struct scd_local_s *sl;
504       
505           for (sl=scd_local_list; sl->next_local; sl = sl->next_local)
506             if (sl->next_local == ctrl->scd_local)
507               break;
508           if (!sl->next_local)
509             BUG ();
510           sl->next_local = ctrl->scd_local->next_local;
511         }
512       xfree (ctrl->scd_local);
513       ctrl->scd_local = NULL;
514     }
515
516   return 0;
517 }
518
519
520 \f
521 /* Return a new malloced string by unescaping the string S.  Escaping
522    is percent escaping and '+'/space mapping.  A binary Nul will
523    silently be replaced by a 0xFF.  Function returns NULL to indicate
524    an out of memory status. */
525 static char *
526 unescape_status_string (const unsigned char *s)
527 {
528   char *buffer, *d;
529
530   buffer = d = xtrymalloc (strlen ((const char*)s)+1);
531   if (!buffer)
532     return NULL;
533   while (*s)
534     {
535       if (*s == '%' && s[1] && s[2])
536         { 
537           s++;
538           *d = xtoi_2 (s);
539           if (!*d)
540             *d = '\xff';
541           d++;
542           s += 2;
543         }
544       else if (*s == '+')
545         {
546           *d++ = ' ';
547           s++;
548         }
549       else
550         *d++ = *s++;
551     }
552   *d = 0; 
553   return buffer;
554 }
555
556
557 \f
558 static int
559 learn_status_cb (void *opaque, const char *line)
560 {
561   struct learn_parm_s *parm = opaque;
562   const char *keyword = line;
563   int keywordlen;
564
565   for (keywordlen=0; *line && !spacep (line); line++, keywordlen++)
566     ;
567   while (spacep (line))
568     line++;
569   if (keywordlen == 8 && !memcmp (keyword, "CERTINFO", keywordlen))
570     {
571       parm->certinfo_cb (parm->certinfo_cb_arg, line);
572     }
573   else if (keywordlen == 11 && !memcmp (keyword, "KEYPAIRINFO", keywordlen))
574     {
575       parm->kpinfo_cb (parm->kpinfo_cb_arg, line);
576     }
577   else if (keywordlen && *line)
578     {
579       parm->sinfo_cb (parm->sinfo_cb_arg, keyword, keywordlen, line);
580     }
581   
582   return 0;
583 }
584
585 /* Perform the LEARN command and return a list of all private keys
586    stored on the card. */
587 int
588 agent_card_learn (ctrl_t ctrl,
589                   void (*kpinfo_cb)(void*, const char *),
590                   void *kpinfo_cb_arg,
591                   void (*certinfo_cb)(void*, const char *),
592                   void *certinfo_cb_arg,
593                   void (*sinfo_cb)(void*, const char *, size_t, const char *),
594                   void *sinfo_cb_arg)
595 {
596   int rc;
597   struct learn_parm_s parm;
598
599   rc = start_scd (ctrl);
600   if (rc)
601     return rc;
602
603   memset (&parm, 0, sizeof parm);
604   parm.kpinfo_cb = kpinfo_cb;
605   parm.kpinfo_cb_arg = kpinfo_cb_arg;
606   parm.certinfo_cb = certinfo_cb;
607   parm.certinfo_cb_arg = certinfo_cb_arg;
608   parm.sinfo_cb = sinfo_cb;
609   parm.sinfo_cb_arg = sinfo_cb_arg;
610   rc = assuan_transact (ctrl->scd_local->ctx, "LEARN --force",
611                         NULL, NULL, NULL, NULL,
612                         learn_status_cb, &parm);
613   if (rc)
614     return unlock_scd (ctrl, rc);
615
616   return unlock_scd (ctrl, 0);
617 }
618
619
620 \f
621 static int
622 get_serialno_cb (void *opaque, const char *line)
623 {
624   char **serialno = opaque;
625   const char *keyword = line;
626   const char *s;
627   int keywordlen, n;
628
629   for (keywordlen=0; *line && !spacep (line); line++, keywordlen++)
630     ;
631   while (spacep (line))
632     line++;
633
634   if (keywordlen == 8 && !memcmp (keyword, "SERIALNO", keywordlen))
635     {
636       if (*serialno)
637         return gpg_error (GPG_ERR_CONFLICT); /* Unexpected status line. */
638       for (n=0,s=line; hexdigitp (s); s++, n++)
639         ;
640       if (!n || (n&1)|| !(spacep (s) || !*s) )
641         return gpg_error (GPG_ERR_ASS_PARAMETER);
642       *serialno = xtrymalloc (n+1);
643       if (!*serialno)
644         return out_of_core ();
645       memcpy (*serialno, line, n);
646       (*serialno)[n] = 0;
647     }
648   
649   return 0;
650 }
651
652 /* Return the serial number of the card or an appropriate error.  The
653    serial number is returned as a hexstring. */
654 int
655 agent_card_serialno (ctrl_t ctrl, char **r_serialno)
656 {
657   int rc;
658   char *serialno = NULL;
659
660   rc = start_scd (ctrl);
661   if (rc)
662     return rc;
663
664   rc = assuan_transact (ctrl->scd_local->ctx, "SERIALNO",
665                         NULL, NULL, NULL, NULL,
666                         get_serialno_cb, &serialno);
667   if (rc)
668     {
669       xfree (serialno);
670       return unlock_scd (ctrl, rc);
671     }
672   *r_serialno = serialno;
673   return unlock_scd (ctrl, 0);
674 }
675
676
677
678 \f
679 static int
680 membuf_data_cb (void *opaque, const void *buffer, size_t length)
681 {
682   membuf_t *data = opaque;
683
684   if (buffer)
685     put_membuf (data, buffer, length);
686   return 0;
687 }
688   
689 /* Handle the NEEDPIN inquiry. */
690 static int
691 inq_needpin (void *opaque, const char *line)
692 {
693   struct inq_needpin_s *parm = opaque;
694   char *pin;
695   size_t pinlen;
696   int rc;
697
698   if (!strncmp (line, "NEEDPIN", 7) && (line[7] == ' ' || !line[7]))
699     {
700       line += 7;
701       while (*line == ' ')
702         line++;
703       
704       pinlen = 90;
705       pin = gcry_malloc_secure (pinlen);
706       if (!pin)
707         return out_of_core ();
708
709       rc = parm->getpin_cb (parm->getpin_cb_arg, line, pin, pinlen);
710       if (!rc)
711         rc = assuan_send_data (parm->ctx, pin, pinlen);
712       xfree (pin);
713     }
714   else if (!strncmp (line, "KEYPADINFO", 10) && (line[10] == ' ' || !line[10]))
715     {
716       size_t code;
717       char *endp;
718
719       code = strtoul (line+10, &endp, 10);
720       line = endp;
721       while (*line == ' ')
722         line++;
723       
724       rc = parm->getpin_cb (parm->getpin_cb_arg, line, NULL, code);
725     }
726   else
727     {
728       log_error ("unsupported inquiry `%s'\n", line);
729       rc = gpg_error (GPG_ERR_ASS_UNKNOWN_INQUIRE);
730     }
731
732   return rc;
733 }
734
735
736
737 /* Create a signature using the current card */
738 int
739 agent_card_pksign (ctrl_t ctrl,
740                    const char *keyid,
741                    int (*getpin_cb)(void *, const char *, char*, size_t),
742                    void *getpin_cb_arg,
743                    const unsigned char *indata, size_t indatalen,
744                    unsigned char **r_buf, size_t *r_buflen)
745 {
746   int rc, i;
747   char *p, line[ASSUAN_LINELENGTH];
748   membuf_t data;
749   struct inq_needpin_s inqparm;
750   size_t len;
751   unsigned char *sigbuf;
752   size_t sigbuflen;
753
754   *r_buf = NULL;
755   rc = start_scd (ctrl);
756   if (rc)
757     return rc;
758
759   if (indatalen*2 + 50 > DIM(line))
760     return unlock_scd (ctrl, gpg_error (GPG_ERR_GENERAL));
761
762   sprintf (line, "SETDATA ");
763   p = line + strlen (line);
764   for (i=0; i < indatalen ; i++, p += 2 )
765     sprintf (p, "%02X", indata[i]);
766   rc = assuan_transact (ctrl->scd_local->ctx, line,
767                         NULL, NULL, NULL, NULL, NULL, NULL);
768   if (rc)
769     return unlock_scd (ctrl, rc);
770
771   init_membuf (&data, 1024);
772   inqparm.ctx = ctrl->scd_local->ctx;
773   inqparm.getpin_cb = getpin_cb;
774   inqparm.getpin_cb_arg = getpin_cb_arg;
775   snprintf (line, DIM(line)-1, 
776             ctrl->use_auth_call? "PKAUTH %s":"PKSIGN %s", keyid);
777   line[DIM(line)-1] = 0;
778   rc = assuan_transact (ctrl->scd_local->ctx, line,
779                         membuf_data_cb, &data,
780                         inq_needpin, &inqparm,
781                         NULL, NULL);
782   if (rc)
783     {
784       xfree (get_membuf (&data, &len));
785       return unlock_scd (ctrl, rc);
786     }
787   sigbuf = get_membuf (&data, &sigbuflen);
788
789   /* Create an S-expression from it which is formatted like this:
790      "(7:sig-val(3:rsa(1:sSIGBUFLEN:SIGBUF)))" */
791   *r_buflen = 21 + 11 + sigbuflen + 4;
792   p = xtrymalloc (*r_buflen);
793   *r_buf = (unsigned char*)p;
794   if (!p)
795     return unlock_scd (ctrl, out_of_core ());
796   p = stpcpy (p, "(7:sig-val(3:rsa(1:s" );
797   sprintf (p, "%u:", (unsigned int)sigbuflen);
798   p += strlen (p);
799   memcpy (p, sigbuf, sigbuflen);
800   p += sigbuflen;
801   strcpy (p, ")))");
802   xfree (sigbuf);
803
804   assert (gcry_sexp_canon_len (*r_buf, *r_buflen, NULL, NULL));
805   return unlock_scd (ctrl, 0);
806 }
807
808 /* Decipher INDATA using the current card. Note that the returned value is */
809 int
810 agent_card_pkdecrypt (ctrl_t ctrl,
811                       const char *keyid,
812                       int (*getpin_cb)(void *, const char *, char*, size_t),
813                       void *getpin_cb_arg,
814                       const unsigned char *indata, size_t indatalen,
815                       char **r_buf, size_t *r_buflen)
816 {
817   int rc, i;
818   char *p, line[ASSUAN_LINELENGTH];
819   membuf_t data;
820   struct inq_needpin_s inqparm;
821   size_t len;
822
823   *r_buf = NULL;
824   rc = start_scd (ctrl);
825   if (rc)
826     return rc;
827
828   /* FIXME: use secure memory where appropriate */
829   if (indatalen*2 + 50 > DIM(line))
830     return unlock_scd (ctrl, gpg_error (GPG_ERR_GENERAL));
831
832   sprintf (line, "SETDATA ");
833   p = line + strlen (line);
834   for (i=0; i < indatalen ; i++, p += 2 )
835     sprintf (p, "%02X", indata[i]);
836   rc = assuan_transact (ctrl->scd_local->ctx, line,
837                         NULL, NULL, NULL, NULL, NULL, NULL);
838   if (rc)
839     return unlock_scd (ctrl, rc);
840
841   init_membuf (&data, 1024);
842   inqparm.ctx = ctrl->scd_local->ctx;
843   inqparm.getpin_cb = getpin_cb;
844   inqparm.getpin_cb_arg = getpin_cb_arg;
845   snprintf (line, DIM(line)-1, "PKDECRYPT %s", keyid);
846   line[DIM(line)-1] = 0;
847   rc = assuan_transact (ctrl->scd_local->ctx, line,
848                         membuf_data_cb, &data,
849                         inq_needpin, &inqparm,
850                         NULL, NULL);
851   if (rc)
852     {
853       xfree (get_membuf (&data, &len));
854       return unlock_scd (ctrl, rc);
855     }
856   *r_buf = get_membuf (&data, r_buflen);
857   if (!*r_buf)
858     return unlock_scd (ctrl, gpg_error (GPG_ERR_ENOMEM));
859
860   return unlock_scd (ctrl, 0);
861 }
862
863
864 \f
865 /* Read a certificate with ID into R_BUF and R_BUFLEN. */
866 int
867 agent_card_readcert (ctrl_t ctrl,
868                      const char *id, char **r_buf, size_t *r_buflen)
869 {
870   int rc;
871   char line[ASSUAN_LINELENGTH];
872   membuf_t data;
873   size_t len;
874
875   *r_buf = NULL;
876   rc = start_scd (ctrl);
877   if (rc)
878     return rc;
879
880   init_membuf (&data, 1024);
881   snprintf (line, DIM(line)-1, "READCERT %s", id);
882   line[DIM(line)-1] = 0;
883   rc = assuan_transact (ctrl->scd_local->ctx, line,
884                         membuf_data_cb, &data,
885                         NULL, NULL,
886                         NULL, NULL);
887   if (rc)
888     {
889       xfree (get_membuf (&data, &len));
890       return unlock_scd (ctrl, rc);
891     }
892   *r_buf = get_membuf (&data, r_buflen);
893   if (!*r_buf)
894     return unlock_scd (ctrl, gpg_error (GPG_ERR_ENOMEM));
895
896   return unlock_scd (ctrl, 0);
897 }
898
899
900 \f
901 /* Read a key with ID and return it in an allocate buffer pointed to
902    by r_BUF as a valid S-expression. */
903 int
904 agent_card_readkey (ctrl_t ctrl, const char *id, unsigned char **r_buf)
905 {
906   int rc;
907   char line[ASSUAN_LINELENGTH];
908   membuf_t data;
909   size_t len, buflen;
910
911   *r_buf = NULL;
912   rc = start_scd (ctrl);
913   if (rc)
914     return rc;
915
916   init_membuf (&data, 1024);
917   snprintf (line, DIM(line)-1, "READKEY %s", id);
918   line[DIM(line)-1] = 0;
919   rc = assuan_transact (ctrl->scd_local->ctx, line,
920                         membuf_data_cb, &data,
921                         NULL, NULL,
922                         NULL, NULL);
923   if (rc)
924     {
925       xfree (get_membuf (&data, &len));
926       return unlock_scd (ctrl, rc);
927     }
928   *r_buf = get_membuf (&data, &buflen);
929   if (!*r_buf)
930     return unlock_scd (ctrl, gpg_error (GPG_ERR_ENOMEM));
931
932   if (!gcry_sexp_canon_len (*r_buf, buflen, NULL, NULL))
933     {
934       xfree (*r_buf); *r_buf = NULL;
935       return unlock_scd (ctrl, gpg_error (GPG_ERR_INV_VALUE));
936     }
937
938   return unlock_scd (ctrl, 0);
939 }
940
941
942 \f
943 /* Type used with the card_getattr_cb.  */
944 struct card_getattr_parm_s {
945   const char *keyword;  /* Keyword to look for.  */
946   size_t keywordlen;    /* strlen of KEYWORD.  */
947   char *data;           /* Malloced and unescaped data.  */
948   int error;            /* ERRNO value or 0 on success. */
949 };
950
951 /* Callback function for agent_card_getattr.  */
952 static assuan_error_t
953 card_getattr_cb (void *opaque, const char *line)
954 {
955   struct card_getattr_parm_s *parm = opaque;
956   const char *keyword = line;
957   int keywordlen;
958
959   if (parm->data)
960     return 0; /* We want only the first occurrence.  */
961
962   for (keywordlen=0; *line && !spacep (line); line++, keywordlen++)
963     ;
964   while (spacep (line))
965     line++;
966
967   if (keywordlen == parm->keywordlen
968       && !memcmp (keyword, parm->keyword, keywordlen))
969     {
970       parm->data = unescape_status_string ((const unsigned char*)line);
971       if (!parm->data)
972         parm->error = errno;
973     }
974   
975   return 0;
976 }
977
978
979 /* Call the agent to retrieve a single line data object. On success
980    the object is malloced and stored at RESULT; it is guaranteed that
981    NULL is never stored in this case.  On error an error code is
982    returned and NULL stored at RESULT. */
983 gpg_error_t
984 agent_card_getattr (ctrl_t ctrl, const char *name, char **result)
985 {
986   int err;
987   struct card_getattr_parm_s parm;
988   char line[ASSUAN_LINELENGTH];
989
990   *result = NULL;
991
992   if (!*name)
993     return gpg_error (GPG_ERR_INV_VALUE);
994
995   memset (&parm, 0, sizeof parm);
996   parm.keyword = name;
997   parm.keywordlen = strlen (name);
998
999   /* We assume that NAME does not need escaping. */
1000   if (8 + strlen (name) > DIM(line)-1)
1001     return gpg_error (GPG_ERR_TOO_LARGE);
1002   stpcpy (stpcpy (line, "GETATTR "), name); 
1003
1004   err = start_scd (ctrl);
1005   if (err)
1006     return err;
1007
1008   err = assuan_transact (ctrl->scd_local->ctx, line,
1009                          NULL, NULL, NULL, NULL,
1010                          card_getattr_cb, &parm);
1011   if (!err && parm.error)
1012     err = gpg_error_from_errno (parm.error);
1013   
1014   if (!err && !parm.data)
1015     err = gpg_error (GPG_ERR_NO_DATA);
1016   
1017   if (!err)
1018     *result = parm.data;
1019   else
1020     xfree (parm.data);
1021
1022   return unlock_scd (ctrl, err);
1023 }
1024
1025
1026
1027 \f
1028 static int
1029 pass_status_thru (void *opaque, const char *line)
1030 {
1031   assuan_context_t ctx = opaque;
1032   char keyword[200];
1033   int i;
1034
1035   for (i=0; *line && !spacep (line) && i < DIM(keyword)-1; line++, i++)
1036     keyword[i] = *line;
1037   keyword[i] = 0;
1038   /* truncate any remaining keyword stuff. */
1039   for (; *line && !spacep (line); line++)
1040     ;
1041   while (spacep (line))
1042     line++;
1043
1044   assuan_write_status (ctx, keyword, line);
1045   return 0;
1046 }
1047
1048 static int
1049 pass_data_thru (void *opaque, const void *buffer, size_t length)
1050 {
1051   assuan_context_t ctx = opaque;
1052
1053   assuan_send_data (ctx, buffer, length);
1054   return 0;
1055 }
1056
1057
1058 /* Send the line CMDLINE with command for the SCDdaemon to it and send
1059    all status messages back.  This command is used as a general quoting
1060    mechanism to pass everything verbatim to SCDAEMOPN.  The PIN
1061    inquirey is handled inside gpg-agent. */
1062 int
1063 agent_card_scd (ctrl_t ctrl, const char *cmdline,
1064                 int (*getpin_cb)(void *, const char *, char*, size_t),
1065                 void *getpin_cb_arg, void *assuan_context)
1066 {
1067   int rc;
1068   struct inq_needpin_s inqparm;
1069
1070   rc = start_scd (ctrl);
1071   if (rc)
1072     return rc;
1073
1074   inqparm.ctx = ctrl->scd_local->ctx;
1075   inqparm.getpin_cb = getpin_cb;
1076   inqparm.getpin_cb_arg = getpin_cb_arg;
1077   rc = assuan_transact (ctrl->scd_local->ctx, cmdline,
1078                         pass_data_thru, assuan_context,
1079                         inq_needpin, &inqparm,
1080                         pass_status_thru, assuan_context);
1081   if (rc)
1082     {
1083       return unlock_scd (ctrl, rc);
1084     }
1085
1086   return unlock_scd (ctrl, 0);
1087 }
1088
1089