* keyserver.c (keyserver_spawn): Don't print "searching for key 00000000"
[gnupg.git] / g10 / keyserver.c
1 /* keyserver.c - generic keyserver code
2  * Copyright (C) 2001, 2002, 2003, 2004, 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 <ctype.h>
24 #include <stdio.h>
25 #include <string.h>
26 #include <stdlib.h>
27 #include <assert.h>
28 #ifdef HAVE_LIBCURL
29 #include <curl/curl.h>
30 #endif
31 #include "filter.h"
32 #include "keydb.h"
33 #include "status.h"
34 #include "exec.h"
35 #include "main.h"
36 #include "i18n.h"
37 #include "iobuf.h"
38 #include "memory.h"
39 #include "ttyio.h"
40 #include "options.h"
41 #include "packet.h"
42 #include "trustdb.h"
43 #include "keyserver-internal.h"
44 #include "util.h"
45
46 #define GET    0
47 #define SEND   1
48 #define SEARCH 2
49
50 #define GPGKEYS_PREFIX "gpgkeys_"
51
52 #if defined(HAVE_LIBCURL) || defined(FAKE_CURL)
53 #define GPGKEYS_CURL "gpgkeys_curl"
54 #endif
55
56 #ifdef GPGKEYS_CURL
57 #define GPGKEYS_PREFIX_LEN (strlen(GPGKEYS_PREFIX)+strlen(GPGKEYS_CURL))
58 #else
59 #define GPGKEYS_PREFIX_LEN (strlen(GPGKEYS_PREFIX))
60 #endif
61
62 struct keyrec
63 {
64   KEYDB_SEARCH_DESC desc;
65   u32 createtime,expiretime;
66   int size,flags;
67   byte type;
68   IOBUF uidbuf;
69   unsigned int lines;
70 };
71
72 /* Tell remote processes about these options */
73 #define REMOTE_TELL (KEYSERVER_INCLUDE_REVOKED|KEYSERVER_INCLUDE_SUBKEYS|KEYSERVER_TRY_DNS_SRV)
74
75 static struct parse_options keyserver_opts[]=
76   {
77     {"include-revoked",KEYSERVER_INCLUDE_REVOKED,NULL,
78      N_("include revoked keys in search results")},
79     {"include-subkeys",KEYSERVER_INCLUDE_SUBKEYS,NULL,
80      N_("include subkeys when searching by key ID")},
81     /* not a real option - just for the help message */
82     {"use-temp-files",0,NULL,
83      N_("use temporary files to pass data to keyserver helpers")},
84     {"keep-temp-files",KEYSERVER_KEEP_TEMP_FILES,NULL,
85      N_("do not delete temporary files after using them")},
86     {"refresh-add-fake-v3-keyids",KEYSERVER_ADD_FAKE_V3,NULL,
87      NULL},
88     {"auto-key-retrieve",KEYSERVER_AUTO_KEY_RETRIEVE,NULL,
89      N_("automatically retrieve keys when verifying signatures")},
90     {"auto-pka-retrieve",KEYSERVER_AUTO_PKA_RETRIEVE,NULL,
91      NULL},
92     {"try-dns-srv",KEYSERVER_TRY_DNS_SRV,NULL,
93      NULL},
94     {"honor-keyserver-url",KEYSERVER_HONOR_KEYSERVER_URL,NULL,
95      N_("honor the preferred keyserver URL set on the key")},
96     {NULL,0,NULL,NULL}
97   };
98
99 static int keyserver_work(int action,STRLIST list,KEYDB_SEARCH_DESC *desc,
100                           int count,struct keyserver_spec *keyserver);
101
102 int
103 parse_keyserver_options(char *options)
104 {
105   int ret=1;
106   char *tok;
107
108   while((tok=optsep(&options)))
109     {
110       if(tok[0]=='\0')
111         continue;
112
113       /* For backwards compatibility.  1.2.x used honor-http-proxy and
114          there are a good number of documents published that recommend
115          it. */
116       if(ascii_strcasecmp(tok,"honor-http-proxy")==0)
117         tok="http-proxy";
118       else if(ascii_strcasecmp(tok,"no-honor-http-proxy")==0)
119         tok="no-http-proxy";
120
121       /* We accept quite a few possible options here - some options to
122          handle specially, the keyserver_options list, and import and
123          export options that pertain to keyserver operations.  Note
124          that you must use strncasecmp here as there might be an
125          =argument attached which will foil the use of strcasecmp. */
126
127 #ifdef EXEC_TEMPFILE_ONLY
128       if(ascii_strncasecmp(tok,"use-temp-files",14)==0 ||
129               ascii_strncasecmp(tok,"no-use-temp-files",17)==0)
130         log_info(_("WARNING: keyserver option `%s' is not used"
131                    " on this platform\n"),tok);
132 #else
133       if(ascii_strncasecmp(tok,"use-temp-files",14)==0)
134         opt.keyserver_options.options|=KEYSERVER_USE_TEMP_FILES;
135       else if(ascii_strncasecmp(tok,"no-use-temp-files",17)==0)
136         opt.keyserver_options.options&=~KEYSERVER_USE_TEMP_FILES;
137 #endif
138       else if(!parse_options(tok,&opt.keyserver_options.options,
139                              keyserver_opts,0)
140          && !parse_import_options(tok,
141                                   &opt.keyserver_options.import_options,0)
142          && !parse_export_options(tok,
143                                   &opt.keyserver_options.export_options,0))
144         {
145           /* All of the standard options have failed, so the option is
146              destined for a keyserver plugin. */
147           char *arg=argsplit(tok);
148
149           if(arg)
150             {
151               char *joined;
152
153               joined=xmalloc(strlen(tok)+1+strlen(arg)+1);
154               /* Make a canonical name=value form with no
155                  spaces */
156               strcpy(joined,tok);
157               strcat(joined,"=");
158               strcat(joined,arg);
159               add_to_strlist(&opt.keyserver_options.other,joined);
160               xfree(joined);
161             }
162           else
163             add_to_strlist(&opt.keyserver_options.other,tok);
164         }
165     }
166
167   return ret;
168 }
169
170 void
171 free_keyserver_spec(struct keyserver_spec *keyserver)
172 {
173   xfree(keyserver->uri);
174   xfree(keyserver->scheme);
175   xfree(keyserver->auth);
176   xfree(keyserver->host);
177   xfree(keyserver->port);
178   xfree(keyserver->path);
179   xfree(keyserver->opaque);
180   xfree(keyserver);
181 }
182
183 /* TODO: once we cut over to an all-curl world, we don't need this
184    parser any longer so it can be removed, or at least moved to
185    keyserver/ksutil.c for limited use in gpgkeys_ldap or the like. */
186
187 struct keyserver_spec *
188 parse_keyserver_uri(const char *uri,int require_scheme,
189                     const char *configname,unsigned int configlineno)
190 {
191   int assume_hkp=0;
192   struct keyserver_spec *keyserver;
193   const char *idx;
194   int count;
195
196   assert(uri!=NULL);
197
198   keyserver=xmalloc_clear(sizeof(struct keyserver_spec));
199
200   keyserver->uri=xstrdup(uri);
201
202   /* Get the scheme */
203
204   for(idx=uri,count=0;*idx && *idx!=':';idx++)
205     {
206       count++;
207
208       /* Do we see the start of an RFC-2732 ipv6 address here?  If so,
209          there clearly isn't a scheme so get out early. */
210       if(*idx=='[')
211         {
212           /* Was the '[' the first thing in the string?  If not, we
213              have a mangled scheme with a [ in it so fail. */
214           if(count==1)
215             break;
216           else
217             goto fail;
218         }
219     }
220
221   if(count==0)
222     goto fail;
223
224   if(*idx=='\0' || *idx=='[')
225     {
226       if(require_scheme)
227         return NULL;
228
229       /* Assume HKP if there is no scheme */
230       assume_hkp=1;
231       keyserver->scheme=xstrdup("hkp");
232     }
233   else
234     {
235       int i;
236
237       keyserver->scheme=xmalloc(count+1);
238
239       /* Force to lowercase */
240       for(i=0;i<count;i++)
241         keyserver->scheme[i]=ascii_tolower(uri[i]);
242
243       keyserver->scheme[i]='\0';
244
245       /* Skip past the scheme and colon */
246       uri+=count+1;
247     }
248
249   if(ascii_strcasecmp(keyserver->scheme,"x-broken-hkp")==0)
250     {
251       deprecated_warning(configname,configlineno,"x-broken-hkp",
252                          "--keyserver-options ","broken-http-proxy");
253       xfree(keyserver->scheme);
254       keyserver->scheme=xstrdup("hkp");
255       add_to_strlist(&opt.keyserver_options.other,"broken-http-proxy");
256     }
257   else if(ascii_strcasecmp(keyserver->scheme,"x-hkp")==0)
258     {
259       /* Canonicalize this to "hkp" so it works with both the internal
260          and external keyserver interface. */
261       xfree(keyserver->scheme);
262       keyserver->scheme=xstrdup("hkp");
263     }
264
265   if(assume_hkp || (uri[0]=='/' && uri[1]=='/'))
266     {
267       /* Two slashes means network path. */
268
269       /* Skip over the "//", if any */
270       if(!assume_hkp)
271         uri+=2;
272
273       /* Do we have userinfo auth data present? */
274       for(idx=uri,count=0;*idx && *idx!='@' && *idx!='/';idx++)
275         count++;
276
277       /* We found a @ before the slash, so that means everything
278          before the @ is auth data. */
279       if(*idx=='@')
280         {
281           if(count==0)
282             goto fail;
283
284           keyserver->auth=xmalloc(count+1);
285           strncpy(keyserver->auth,uri,count);
286           keyserver->auth[count]='\0';
287           uri+=count+1;
288         }
289
290       /* Is it an RFC-2732 ipv6 [literal address] ? */
291       if(*uri=='[')
292         {
293           for(idx=uri+1,count=1;*idx
294                 && ((isascii (*idx) && isxdigit(*idx))
295                     || *idx==':' || *idx=='.');idx++)
296             count++;
297
298           /* Is the ipv6 literal address terminated? */
299           if(*idx==']')
300             count++;
301           else
302             goto fail;
303         }
304       else
305         for(idx=uri,count=0;*idx && *idx!=':' && *idx!='/';idx++)
306           count++;
307
308       if(count==0)
309         goto fail;
310
311       keyserver->host=xmalloc(count+1);
312       strncpy(keyserver->host,uri,count);
313       keyserver->host[count]='\0';
314
315       /* Skip past the host */
316       uri+=count;
317
318       if(*uri==':')
319         {
320           /* It would seem to be reasonable to limit the range of the
321              ports to values between 1-65535, but RFC 1738 and 1808
322              imply there is no limit.  Of course, the real world has
323              limits. */
324
325           for(idx=uri+1,count=0;*idx && *idx!='/';idx++)
326             {
327               count++;
328
329               /* Ports are digits only */
330               if(!digitp(idx))
331                 goto fail;
332             }
333
334           keyserver->port=xmalloc(count+1);
335           strncpy(keyserver->port,uri+1,count);
336           keyserver->port[count]='\0';
337
338           /* Skip past the colon and port number */
339           uri+=1+count;
340         }
341
342       /* Everything else is the path */
343       if(*uri)
344         keyserver->path=xstrdup(uri);
345       else
346         keyserver->path=xstrdup("/");
347     }
348   else if(uri[0]!='/')
349     {
350       /* No slash means opaque.  Just record the opaque blob and get
351          out. */
352       keyserver->opaque=xstrdup(uri);
353     }
354   else
355     {
356       /* One slash means absolute path.  We don't need to support that
357          yet. */
358       goto fail;
359     }
360
361   return keyserver;
362
363  fail:
364   free_keyserver_spec(keyserver);
365
366   return NULL;
367 }
368
369 struct keyserver_spec *
370 parse_preferred_keyserver(PKT_signature *sig)
371 {
372   struct keyserver_spec *spec=NULL;
373   const byte *p;
374   size_t plen;
375
376   p=parse_sig_subpkt(sig->hashed,SIGSUBPKT_PREF_KS,&plen);
377   if(p && plen)
378     {
379       byte *dupe=xmalloc(plen+1);
380
381       memcpy(dupe,p,plen);
382       dupe[plen]='\0';
383       spec=parse_keyserver_uri(dupe,1,NULL,0);
384       xfree(dupe);
385     }
386
387   return spec;
388 }
389
390 static void
391 print_keyrec(int number,struct keyrec *keyrec)
392 {
393   int i;
394
395   iobuf_writebyte(keyrec->uidbuf,0);
396   iobuf_flush_temp(keyrec->uidbuf);
397   printf("(%d)\t%s  ",number,iobuf_get_temp_buffer(keyrec->uidbuf));
398
399   if(keyrec->size>0)
400     printf("%d bit ",keyrec->size);
401
402   if(keyrec->type)
403     {
404       const char *str=pubkey_algo_to_string(keyrec->type);
405
406       if(str)
407         printf("%s ",str);
408       else
409         printf("unknown ");
410     }
411
412   switch(keyrec->desc.mode)
413     {
414       /* If the keyserver helper gave us a short keyid, we have no
415          choice but to use it.  Do check --keyid-format to add a 0x if
416          needed. */
417     case KEYDB_SEARCH_MODE_SHORT_KID:
418       printf("key %s%08lX",
419              (opt.keyid_format==KF_0xSHORT
420               || opt.keyid_format==KF_0xLONG)?"0x":"",
421              (ulong)keyrec->desc.u.kid[1]);
422       break;
423
424       /* However, if it gave us a long keyid, we can honor
425          --keyid-format */
426     case KEYDB_SEARCH_MODE_LONG_KID:
427       printf("key %s",keystr(keyrec->desc.u.kid));
428       break;
429
430     case KEYDB_SEARCH_MODE_FPR16:
431       printf("key ");
432       for(i=0;i<16;i++)
433         printf("%02X",keyrec->desc.u.fpr[i]);
434       break;
435
436     case KEYDB_SEARCH_MODE_FPR20:
437       printf("key ");
438       for(i=0;i<20;i++)
439         printf("%02X",keyrec->desc.u.fpr[i]);
440       break;
441
442     default:
443       BUG();
444       break;
445     }
446
447   if(keyrec->createtime>0)
448     {
449       printf(", ");
450       printf(_("created: %s"),strtimestamp(keyrec->createtime));
451     }
452
453   if(keyrec->expiretime>0)
454     {
455       printf(", ");
456       printf(_("expires: %s"),strtimestamp(keyrec->expiretime));
457     }
458
459   if(keyrec->flags&1)
460     printf(" (%s)",_("revoked"));
461   if(keyrec->flags&2)
462     printf(" (%s)",_("disabled"));
463   if(keyrec->flags&4)
464     printf(" (%s)",_("expired"));
465
466   printf("\n");
467 }
468
469 /* Returns a keyrec (which must be freed) once a key is complete, and
470    NULL otherwise.  Call with a NULL keystring once key parsing is
471    complete to return any unfinished keys. */
472 static struct keyrec *
473 parse_keyrec(char *keystring)
474 {
475   static struct keyrec *work=NULL;
476   struct keyrec *ret=NULL;
477   char *record;
478   int i;
479
480   if(keystring==NULL)
481     {
482       if(work==NULL)
483         return NULL;
484       else if(work->desc.mode==KEYDB_SEARCH_MODE_NONE)
485         {
486           xfree(work);
487           return NULL;
488         }
489       else
490         {
491           ret=work;
492           work=NULL;
493           return ret;
494         }
495     }
496
497   if(work==NULL)
498     {
499       work=xmalloc_clear(sizeof(struct keyrec));
500       work->uidbuf=iobuf_temp();
501     }
502
503   /* Remove trailing whitespace */
504   for(i=strlen(keystring);i>0;i--)
505     if(ascii_isspace(keystring[i-1]))
506       keystring[i-1]='\0';
507     else
508       break;
509
510   if((record=strsep(&keystring,":"))==NULL)
511     return ret;
512
513   if(ascii_strcasecmp("pub",record)==0)
514     {
515       char *tok;
516
517       if(work->desc.mode)
518         {
519           ret=work;
520           work=xmalloc_clear(sizeof(struct keyrec));
521           work->uidbuf=iobuf_temp();
522         }
523
524       if((tok=strsep(&keystring,":"))==NULL)
525         return ret;
526
527       classify_user_id(tok,&work->desc);
528       if(work->desc.mode!=KEYDB_SEARCH_MODE_SHORT_KID
529          && work->desc.mode!=KEYDB_SEARCH_MODE_LONG_KID
530          && work->desc.mode!=KEYDB_SEARCH_MODE_FPR16
531          && work->desc.mode!=KEYDB_SEARCH_MODE_FPR20)
532         {
533           work->desc.mode=KEYDB_SEARCH_MODE_NONE;
534           return ret;
535         }
536
537       /* Note all items after this are optional.  This allows us to
538          have a pub line as simple as pub:keyid and nothing else. */
539
540       work->lines++;
541
542       if((tok=strsep(&keystring,":"))==NULL)
543         return ret;
544
545       work->type=atoi(tok);
546
547       if((tok=strsep(&keystring,":"))==NULL)
548         return ret;
549
550       work->size=atoi(tok);
551
552       if((tok=strsep(&keystring,":"))==NULL)
553         return ret;
554
555       if(atoi(tok)<=0)
556         work->createtime=0;
557       else
558         work->createtime=atoi(tok);
559
560       if((tok=strsep(&keystring,":"))==NULL)
561         return ret;
562
563       if(atoi(tok)<=0)
564         work->expiretime=0;
565       else
566         {
567           work->expiretime=atoi(tok);
568           /* Force the 'e' flag on if this key is expired. */
569           if(work->expiretime<=make_timestamp())
570             work->flags|=4;
571         }
572
573       if((tok=strsep(&keystring,":"))==NULL)
574         return ret;
575
576       while(*tok)
577         switch(*tok++)
578           {
579           case 'r':
580           case 'R':
581             work->flags|=1;
582             break;
583             
584           case 'd':
585           case 'D':
586             work->flags|=2;
587             break;
588
589           case 'e':
590           case 'E':
591             work->flags|=4;
592             break;
593           }
594     }
595   else if(ascii_strcasecmp("uid",record)==0 && work->desc.mode)
596     {
597       char *userid,*tok,*decoded;
598
599       if((tok=strsep(&keystring,":"))==NULL)
600         return ret;
601
602       if(strlen(tok)==0)
603         return ret;
604
605       userid=tok;
606
607       /* By definition, de-%-encoding is always smaller than the
608          original string so we can decode in place. */
609
610       i=0;
611
612       while(*tok)
613         if(tok[0]=='%' && tok[1] && tok[2])
614           {
615             if((userid[i]=hextobyte(&tok[1]))==-1)
616               userid[i]='?';
617
618             i++;
619             tok+=3;
620           }
621         else
622           userid[i++]=*tok++;
623
624       /* We don't care about the other info provided in the uid: line
625          since no keyserver supports marking userids with timestamps
626          or revoked/expired/disabled yet. */
627
628       /* No need to check for control characters, as utf8_to_native
629          does this for us. */
630
631       decoded=utf8_to_native(userid,i,0);
632       if(strlen(decoded)>opt.screen_columns-10)
633         decoded[opt.screen_columns-10]='\0';
634       iobuf_writestr(work->uidbuf,decoded);
635       xfree(decoded);
636       iobuf_writestr(work->uidbuf,"\n\t");
637       work->lines++;
638     }
639
640   /* Ignore any records other than "pri" and "uid" for easy future
641      growth. */
642
643   return ret;
644 }
645
646 /* TODO: do this as a list sent to keyserver_work rather than calling
647    it once for each key to get the correct counts after the import
648    (cosmetics, really) and to better take advantage of the keyservers
649    that can do multiple fetches in one go (LDAP). */
650 static int
651 show_prompt(KEYDB_SEARCH_DESC *desc,int numdesc,int count,const char *search)
652 {
653   char *answer;
654
655   if(count && opt.command_fd==-1)
656     {
657       static int from=1;
658       tty_printf("Keys %d-%d of %d for \"%s\".  ",from,numdesc,count,search);
659       from=numdesc+1;
660     }
661
662   answer=cpr_get_no_help("keysearch.prompt",
663                          _("Enter number(s), N)ext, or Q)uit > "));
664   /* control-d */
665   if(answer[0]=='\x04')
666     {
667       printf("Q\n");
668       answer[0]='q';
669     }
670
671   if(answer[0]=='q' || answer[0]=='Q')
672     {
673       xfree(answer);
674       return 1;
675     }
676   else if(atoi(answer)>=1 && atoi(answer)<=numdesc)
677     {
678       char *split=answer,*num;
679
680       while((num=strsep(&split," ,"))!=NULL)
681         if(atoi(num)>=1 && atoi(num)<=numdesc)
682           keyserver_work(GET,NULL,&desc[atoi(num)-1],1,opt.keyserver);
683
684       xfree(answer);
685       return 1;
686     }
687
688   return 0;
689 }
690
691 /* Count and searchstr are just for cosmetics.  If the count is too
692    small, it will grow safely.  If negative it disables the "Key x-y
693    of z" messages.  searchstr should be UTF-8 (rather than native). */
694 static void
695 keyserver_search_prompt(IOBUF buffer,const char *searchstr)
696 {
697   int i=0,validcount=0,started=0,header=0,count=1;
698   unsigned int maxlen,buflen,numlines=0;
699   KEYDB_SEARCH_DESC *desc;
700   byte *line=NULL;
701   char *localstr=NULL;
702
703   if(searchstr)
704     localstr=utf8_to_native(searchstr,strlen(searchstr),0);
705
706   desc=xmalloc(count*sizeof(KEYDB_SEARCH_DESC));
707
708   for(;;)
709     {
710       struct keyrec *keyrec;
711       int rl;
712
713       maxlen=1024;
714       rl=iobuf_read_line(buffer,&line,&buflen,&maxlen);
715
716       if(opt.with_colons)
717         {
718           if(!header && ascii_strncasecmp("SEARCH ",line,7)==0
719              && ascii_strncasecmp(" BEGIN",&line[strlen(line)-7],6)==0)
720             {
721               header=1;
722               continue;
723             }
724           else if(ascii_strncasecmp("SEARCH ",line,7)==0
725                   && ascii_strncasecmp(" END",&line[strlen(line)-5],4)==0)
726             continue;
727
728           printf("%s",line);
729         }
730
731       /* Look for an info: line.  The only current info: values
732          defined are the version and key count. */
733       if(!started && rl>0 && ascii_strncasecmp("info:",line,5)==0)
734         {
735           char *tok,*str=&line[5];
736
737           if((tok=strsep(&str,":"))!=NULL)
738             {
739               int version;
740
741               if(sscanf(tok,"%d",&version)!=1)
742                 version=1;
743
744               if(version!=1)
745                 {
746                   log_error(_("invalid keyserver protocol "
747                               "(us %d!=handler %d)\n"),1,version);
748                   break;
749                 }
750             }
751
752           if((tok=strsep(&str,":"))!=NULL && sscanf(tok,"%d",&count)==1)
753             {
754               if(count==0)
755                 goto notfound;
756               else if(count<0)
757                 count=10;
758               else
759                 validcount=1;
760
761               desc=xrealloc(desc,count*sizeof(KEYDB_SEARCH_DESC));
762             }
763
764           started=1;
765           continue;
766         }
767
768       if(rl==0)
769         {
770           keyrec=parse_keyrec(NULL);
771
772           if(keyrec==NULL)
773             {
774               if(i==0)
775                 {
776                   count=0;
777                   break;
778                 }
779
780               if(i!=count)
781                 validcount=0;
782
783               for(;;)
784                 {
785                   if(show_prompt(desc,i,validcount?count:0,localstr))
786                     break;
787                   validcount=0;
788                 }
789
790               break;
791             }
792         }
793       else
794         keyrec=parse_keyrec(line);
795
796       if(i==count)
797         {
798           /* keyserver helper sent more keys than they claimed in the
799              info: line. */
800           count+=10;
801           desc=xrealloc(desc,count*sizeof(KEYDB_SEARCH_DESC));
802           validcount=0;
803         }
804
805       if(keyrec)
806         {
807           desc[i]=keyrec->desc;
808
809           if(!opt.with_colons)
810             {
811               /* screen_lines - 1 for the prompt. */
812               if(numlines+keyrec->lines>opt.screen_lines-1)
813                 {
814                   if(show_prompt(desc,i,validcount?count:0,localstr))
815                     break;
816                   else
817                     numlines=0;
818                 }
819
820               print_keyrec(i+1,keyrec);
821             }
822
823           numlines+=keyrec->lines;
824           iobuf_close(keyrec->uidbuf);
825           xfree(keyrec);
826
827           started=1;
828           i++;
829         }
830     }
831
832  notfound:
833   /* Leave this commented out or now, and perhaps for a very long
834      time.  All HKPish servers return HTML error messages for
835      no-key-found. */
836   /* 
837      if(!started)
838      log_info(_("keyserver does not support searching\n"));
839      else
840   */
841   if(count==0)
842     {
843       if(localstr)
844         log_info(_("key \"%s\" not found on keyserver\n"),localstr);
845       else
846         log_info(_("key not found on keyserver\n"));
847     }
848
849   xfree(localstr);
850   xfree(desc);
851   xfree(line);
852 }
853
854 /* We sometimes want to use a different gpgkeys_xxx for a given
855    protocol (for example, ldaps is handled by gpgkeys_ldap).  Map
856    these here. */
857 static const char *
858 keyserver_typemap(const char *type)
859 {
860   if(strcmp(type,"ldaps")==0)
861     return "ldap";
862   else
863     return type;
864 }
865
866 #ifdef GPGKEYS_CURL
867 /* The PGP LDAP and the curl fetch-a-LDAP-object methodologies are
868    sufficiently different that we can't use curl to do LDAP. */
869 static int
870 curl_cant_handle(const char *scheme)
871 {
872   if(strcmp(scheme,"ldap")==0 || strcmp(scheme,"ldaps")==0)
873     return 1;
874
875   return 0;
876 }
877 #endif
878
879 #define KEYSERVER_ARGS_KEEP " -o \"%O\" \"%I\""
880 #define KEYSERVER_ARGS_NOKEEP " -o \"%o\" \"%i\""
881
882 static int 
883 keyserver_spawn(int action,STRLIST list,KEYDB_SEARCH_DESC *desc,
884                 int count,int *prog,struct keyserver_spec *keyserver)
885 {
886   int ret=0,i,gotversion=0,outofband=0,quiet=0;
887   STRLIST temp;
888   unsigned int maxlen,buflen;
889   char *command,*end,*searchstr=NULL;
890   byte *line=NULL;
891   struct parse_options *kopts;
892   struct exec_info *spawn;
893   const char *scheme;
894   const char *libexecdir = get_libexecdir ();
895
896   assert(keyserver);
897
898 #ifdef EXEC_TEMPFILE_ONLY
899   opt.keyserver_options.options|=KEYSERVER_USE_TEMP_FILES;
900 #endif
901
902   /* Build the filename for the helper to execute */
903   scheme=keyserver_typemap(keyserver->scheme);
904
905 #ifdef DISABLE_KEYSERVER_PATH
906   /* Destroy any path we might have.  This is a little tricky,
907      portability-wise.  It's not correct to delete the PATH
908      environment variable, as that may fall back to a system built-in
909      PATH.  Similarly, it is not correct to set PATH to the null
910      string (PATH="") since this actually deletes the PATH environment
911      variable under MinGW.  The safest thing to do here is to force
912      PATH to be GNUPG_LIBEXECDIR.  All this is not that meaningful on
913      Unix-like systems (since we're going to give a full path to
914      gpgkeys_foo), but on W32 it prevents loading any DLLs from
915      directories in %PATH%.
916
917      After some more thinking about this we came to the conclusion
918      that it is better to load the helpers from the directory where
919      the program of this process lives.  Fortunately Windows provides
920      a way to retrieve this and our get_libexecdir function has been
921      modified to return just this.  Setting the exec-path is not
922      anymore required.  
923        set_exec_path(libexecdir);
924  */
925 #else
926   if(opt.exec_path_set)
927     {
928       /* If exec-path was set, and DISABLE_KEYSERVER_PATH is
929          undefined, then don't specify a full path to gpgkeys_foo, so
930          that the PATH can work. */
931       command=xmalloc(GPGKEYS_PREFIX_LEN+strlen(scheme)+1);
932       command[0]='\0';
933     }
934   else
935 #endif
936     {
937       /* Specify a full path to gpgkeys_foo. */
938       command=xmalloc(strlen(libexecdir)+strlen(DIRSEP_S)+
939                       GPGKEYS_PREFIX_LEN+strlen(scheme)+1);
940       strcpy(command,libexecdir);
941       strcat(command,DIRSEP_S);
942     }
943
944   end=command+strlen(command);
945
946   strcat(command,GPGKEYS_PREFIX); 
947   strcat(command,scheme);
948
949 #ifdef GPGKEYS_CURL
950   if(!curl_cant_handle(scheme) && path_access(command,X_OK)!=0)
951     strcpy(end,GPGKEYS_CURL);
952 #endif
953
954   if(opt.keyserver_options.options&KEYSERVER_USE_TEMP_FILES)
955     {
956       if(opt.keyserver_options.options&KEYSERVER_KEEP_TEMP_FILES)
957         {
958           command=xrealloc(command,strlen(command)+
959                             strlen(KEYSERVER_ARGS_KEEP)+1);
960           strcat(command,KEYSERVER_ARGS_KEEP);
961         }
962       else
963         {
964           command=xrealloc(command,strlen(command)+
965                             strlen(KEYSERVER_ARGS_NOKEEP)+1);
966           strcat(command,KEYSERVER_ARGS_NOKEEP);  
967         }
968
969       ret=exec_write(&spawn,NULL,command,NULL,0,0);
970     }
971   else
972     ret=exec_write(&spawn,command,NULL,NULL,0,0);
973
974   xfree(command);
975
976   if(ret)
977     return ret;
978
979   fprintf(spawn->tochild,
980           "# This is a GnuPG %s keyserver communications file\n",VERSION);
981   fprintf(spawn->tochild,"VERSION %d\n",KEYSERVER_PROTO_VERSION);
982   fprintf(spawn->tochild,"PROGRAM %s\n",VERSION);
983   fprintf(spawn->tochild,"SCHEME %s\n",keyserver->scheme);
984
985   if(keyserver->opaque)
986     fprintf(spawn->tochild,"OPAQUE %s\n",keyserver->opaque);
987   else
988     {
989       if(keyserver->auth)
990         fprintf(spawn->tochild,"AUTH %s\n",keyserver->auth);
991
992       if(keyserver->host)
993         fprintf(spawn->tochild,"HOST %s\n",keyserver->host);
994
995       if(keyserver->port)
996         fprintf(spawn->tochild,"PORT %s\n",keyserver->port);
997
998       if(keyserver->path)
999         fprintf(spawn->tochild,"PATH %s\n",keyserver->path);
1000     }
1001
1002   /* Write options */
1003
1004   for(i=0,kopts=keyserver_opts;kopts[i].name;i++)
1005     if(opt.keyserver_options.options & kopts[i].bit & REMOTE_TELL)
1006       fprintf(spawn->tochild,"OPTION %s\n",kopts[i].name);
1007
1008   for(temp=opt.keyserver_options.other;temp;temp=temp->next)
1009     fprintf(spawn->tochild,"OPTION %s\n",temp->d);
1010
1011   switch(action)
1012     {
1013     case GET:
1014       {
1015         fprintf(spawn->tochild,"COMMAND GET\n\n");
1016
1017         /* Which keys do we want? */
1018
1019         for(i=0;i<count;i++)
1020           {
1021             if(desc[i].mode==KEYDB_SEARCH_MODE_FPR20)
1022               {
1023                 int f;
1024
1025                 fprintf(spawn->tochild,"0x");
1026
1027                 for(f=0;f<MAX_FINGERPRINT_LEN;f++)
1028                   fprintf(spawn->tochild,"%02X",desc[i].u.fpr[f]);
1029
1030                 fprintf(spawn->tochild,"\n");
1031               }
1032             else if(desc[i].mode==KEYDB_SEARCH_MODE_FPR16)
1033               {
1034                 int f;
1035
1036                 fprintf(spawn->tochild,"0x");
1037
1038                 for(f=0;f<16;f++)
1039                   fprintf(spawn->tochild,"%02X",desc[i].u.fpr[f]);
1040
1041                 fprintf(spawn->tochild,"\n");
1042               }
1043             else if(desc[i].mode==KEYDB_SEARCH_MODE_LONG_KID)
1044               fprintf(spawn->tochild,"0x%08lX%08lX\n",
1045                       (ulong)desc[i].u.kid[0],
1046                       (ulong)desc[i].u.kid[1]);
1047             else if(desc[i].mode==KEYDB_SEARCH_MODE_SHORT_KID)
1048               fprintf(spawn->tochild,"0x%08lX\n",
1049                       (ulong)desc[i].u.kid[1]);
1050             else if(desc[i].mode==KEYDB_SEARCH_MODE_EXACT)
1051               {
1052                 fprintf(spawn->tochild,"0x0000000000000000\n");
1053                 quiet=1;
1054               }
1055             else if(desc[i].mode==KEYDB_SEARCH_MODE_NONE)
1056               continue;
1057             else
1058               BUG();
1059
1060             if(!quiet)
1061               {
1062                 if(keyserver->host)
1063                   log_info(_("requesting key %s from %s server %s\n"),
1064                            keystr_from_desc(&desc[i]),
1065                            keyserver->scheme,keyserver->host);
1066                 else
1067                   log_info(_("requesting key %s from %s\n"),
1068                            keystr_from_desc(&desc[i]),keyserver->uri);
1069               }
1070           }
1071
1072         fprintf(spawn->tochild,"\n");
1073
1074         break;
1075       }
1076
1077     case SEND:
1078       {
1079         STRLIST key;
1080
1081         /* Note the extra \n here to send an empty keylist block */
1082         fprintf(spawn->tochild,"COMMAND SEND\n\n\n");
1083
1084         for(key=list;key!=NULL;key=key->next)
1085           {
1086             armor_filter_context_t afx;
1087             IOBUF buffer=iobuf_temp();
1088             KBNODE block;
1089
1090             temp=NULL;
1091             add_to_strlist(&temp,key->d);
1092
1093             memset(&afx,0,sizeof(afx));
1094             afx.what=1;
1095             /* Tell the armor filter to use Unix-style \n line
1096                endings, since we're going to fprintf this to a file
1097                that (on Win32) is open in text mode.  The win32 stdio
1098                will transform the \n to \r\n and we'll end up with the
1099                proper line endings on win32.  This is a no-op on
1100                Unix. */
1101             afx.eol[0]='\n';
1102             iobuf_push_filter(buffer,armor_filter,&afx);
1103
1104             /* TODO: Remove Comment: lines from keys exported this
1105                way? */
1106
1107             if(export_pubkeys_stream(buffer,temp,&block,
1108                                      opt.keyserver_options.export_options)==-1)
1109               iobuf_close(buffer);
1110             else
1111               {
1112                 KBNODE node;
1113
1114                 iobuf_flush_temp(buffer);
1115
1116                 merge_keys_and_selfsig(block);
1117
1118                 fprintf(spawn->tochild,"INFO %08lX%08lX BEGIN\n",
1119                         (ulong)block->pkt->pkt.public_key->keyid[0],
1120                         (ulong)block->pkt->pkt.public_key->keyid[1]);
1121
1122                 for(node=block;node;node=node->next)
1123                   {
1124                     switch(node->pkt->pkttype)
1125                       {
1126                       default:
1127                         continue;
1128
1129                       case PKT_PUBLIC_KEY:
1130                       case PKT_PUBLIC_SUBKEY:
1131                         {
1132                           PKT_public_key *pk=node->pkt->pkt.public_key;
1133
1134                           keyid_from_pk(pk,NULL);
1135
1136                           fprintf(spawn->tochild,"%sb:%08lX%08lX:%u:%u:%u:%u:",
1137                                   node->pkt->pkttype==PKT_PUBLIC_KEY?"pu":"su",
1138                                   (ulong)pk->keyid[0],(ulong)pk->keyid[1],
1139                                   pk->pubkey_algo,
1140                                   nbits_from_pk(pk),
1141                                   pk->timestamp,
1142                                   pk->expiredate);
1143
1144                           if(pk->is_revoked)
1145                             fprintf(spawn->tochild,"r");
1146                           if(pk->has_expired)
1147                             fprintf(spawn->tochild,"e");
1148
1149                           fprintf(spawn->tochild,"\n");
1150                         }
1151                         break;
1152
1153                       case PKT_USER_ID:
1154                         {
1155                           PKT_user_id *uid=node->pkt->pkt.user_id;
1156                           int r;
1157
1158                           if(uid->attrib_data)
1159                             continue;
1160
1161                           fprintf(spawn->tochild,"uid:");
1162
1163                           /* Quote ':', '%', and any 8-bit
1164                              characters */
1165                           for(r=0;r<uid->len;r++)
1166                             {
1167                               if(uid->name[r]==':' || uid->name[r]=='%'
1168                                  || uid->name[r]&0x80)
1169                                 fprintf(spawn->tochild,"%%%02X",
1170                                         (byte)uid->name[r]);
1171                               else
1172                                 fprintf(spawn->tochild,"%c",uid->name[r]);
1173                             }
1174
1175                           fprintf(spawn->tochild,":%u:%u:",
1176                                   uid->created,uid->expiredate);
1177
1178                           if(uid->is_revoked)
1179                             fprintf(spawn->tochild,"r");
1180                           if(uid->is_expired)
1181                             fprintf(spawn->tochild,"e");
1182
1183                           fprintf(spawn->tochild,"\n");
1184                         }
1185                         break;
1186
1187                         /* This bit is really for the benefit of
1188                            people who store their keys in LDAP
1189                            servers.  It makes it easy to do queries
1190                            for things like "all keys signed by
1191                            Isabella". */
1192                       case PKT_SIGNATURE:
1193                         {
1194                           PKT_signature *sig=node->pkt->pkt.signature;
1195
1196                           if(!IS_UID_SIG(sig))
1197                             continue;
1198
1199                           fprintf(spawn->tochild,"sig:%08lX%08lX:%X:%u:%u\n",
1200                                   (ulong)sig->keyid[0],(ulong)sig->keyid[1],
1201                                   sig->sig_class,sig->timestamp,
1202                                   sig->expiredate);
1203                         }
1204                         break;
1205                       }
1206                   }
1207
1208                 fprintf(spawn->tochild,"INFO %08lX%08lX END\n",
1209                         (ulong)block->pkt->pkt.public_key->keyid[0],
1210                         (ulong)block->pkt->pkt.public_key->keyid[1]);
1211
1212                 fprintf(spawn->tochild,"KEY %s BEGIN\n",key->d);
1213                 fwrite(iobuf_get_temp_buffer(buffer),
1214                        iobuf_get_temp_length(buffer),1,spawn->tochild);
1215                 fprintf(spawn->tochild,"KEY %s END\n",key->d);
1216
1217                 iobuf_close(buffer);
1218
1219                 if(keyserver->host)
1220                   log_info(_("sending key %s to %s server %s\n"),
1221                            keystr(block->pkt->pkt.public_key->keyid),
1222                            keyserver->scheme,keyserver->host);
1223                 else
1224                   log_info(_("sending key %s to %s\n"),
1225                            keystr(block->pkt->pkt.public_key->keyid),
1226                            keyserver->uri);
1227
1228                 release_kbnode(block);
1229               }
1230
1231             free_strlist(temp);
1232           }
1233
1234         break;
1235       }
1236
1237     case SEARCH:
1238       {
1239         STRLIST key;
1240
1241         fprintf(spawn->tochild,"COMMAND SEARCH\n\n");
1242
1243         /* Which keys do we want?  Remember that the gpgkeys_ program
1244            is going to lump these together into a search string. */
1245
1246         for(key=list;key!=NULL;key=key->next)
1247           {
1248             fprintf(spawn->tochild,"%s\n",key->d);
1249             if(key!=list)
1250               {
1251                 searchstr=xrealloc(searchstr,
1252                                     strlen(searchstr)+strlen(key->d)+2);
1253                 strcat(searchstr," ");
1254               }
1255             else
1256               {
1257                 searchstr=xmalloc(strlen(key->d)+1);
1258                 searchstr[0]='\0';
1259               }
1260
1261             strcat(searchstr,key->d);
1262           }
1263
1264         fprintf(spawn->tochild,"\n");
1265
1266         if(keyserver->host)
1267           log_info(_("searching for \"%s\" from %s server %s\n"),
1268                    searchstr,keyserver->scheme,keyserver->host);
1269         else
1270           log_info(_("searching for \"%s\" from %s\n"),
1271                    searchstr,keyserver->uri);
1272
1273         break;
1274       }
1275
1276     default:
1277       log_fatal(_("no keyserver action!\n"));
1278       break;
1279     }
1280
1281   /* Done sending, so start reading. */
1282   ret=exec_read(spawn);
1283   if(ret)
1284     goto fail;
1285
1286   /* Now handle the response */
1287
1288   for(;;)
1289     {
1290       int plen;
1291       char *ptr;
1292
1293       maxlen=1024;
1294       if(iobuf_read_line(spawn->fromchild,&line,&buflen,&maxlen)==0)
1295         {
1296           ret=G10ERR_READ_FILE;
1297           goto fail; /* i.e. EOF */
1298         }
1299
1300       ptr=line;
1301
1302       /* remove trailing whitespace */
1303       plen=strlen(ptr);
1304       while(plen>0 && ascii_isspace(ptr[plen-1]))
1305         plen--;
1306       plen[ptr]='\0';
1307
1308       if(*ptr=='\0')
1309         break;
1310
1311       if(ascii_strncasecmp(ptr,"VERSION ",8)==0)
1312         {
1313           gotversion=1;
1314
1315           if(atoi(&ptr[8])!=KEYSERVER_PROTO_VERSION)
1316             {
1317               log_error(_("invalid keyserver protocol (us %d!=handler %d)\n"),
1318                         KEYSERVER_PROTO_VERSION,atoi(&ptr[8]));
1319               goto fail;
1320             }
1321         }
1322       else if(ascii_strncasecmp(ptr,"PROGRAM ",8)==0)
1323         {
1324           if(ascii_strncasecmp(&ptr[8],VERSION,strlen(VERSION))!=0)
1325             log_info(_("WARNING: keyserver handler from a different"
1326                        " version of GnuPG (%s)\n"),&ptr[8]);
1327         }
1328       else if(ascii_strncasecmp(ptr,"OPTION OUTOFBAND",16)==0)
1329         outofband=1; /* Currently the only OPTION */
1330     }
1331
1332   if(!gotversion)
1333     {
1334       log_error(_("keyserver did not send VERSION\n"));
1335       goto fail;
1336     }
1337
1338   if(!outofband)
1339     switch(action)
1340       {
1341       case GET:
1342         {
1343           void *stats_handle;
1344
1345           stats_handle=import_new_stats_handle();
1346
1347           /* Slurp up all the key data.  In the future, it might be
1348              nice to look for KEY foo OUTOFBAND and FAILED indicators.
1349              It's harmless to ignore them, but ignoring them does make
1350              gpg complain about "no valid OpenPGP data found".  One
1351              way to do this could be to continue parsing this
1352              line-by-line and make a temp iobuf for each key. */
1353
1354           import_keys_stream(spawn->fromchild,stats_handle,
1355                              opt.keyserver_options.import_options);
1356
1357           import_print_stats(stats_handle);
1358           import_release_stats_handle(stats_handle);
1359
1360           break;
1361         }
1362
1363         /* Nothing to do here */
1364       case SEND:
1365         break;
1366
1367       case SEARCH:
1368         keyserver_search_prompt(spawn->fromchild,searchstr);
1369         break;
1370
1371       default:
1372         log_fatal(_("no keyserver action!\n"));
1373         break;
1374       }
1375
1376  fail:
1377   xfree(line);
1378   xfree(searchstr);
1379
1380
1381   *prog=exec_finish(spawn);
1382
1383   return ret;
1384 }
1385
1386 static int 
1387 keyserver_work(int action,STRLIST list,KEYDB_SEARCH_DESC *desc,
1388                int count,struct keyserver_spec *keyserver)
1389 {
1390   int rc=0,ret=0;
1391
1392   if(!keyserver)
1393     {
1394       log_error(_("no keyserver known (use option --keyserver)\n"));
1395       return G10ERR_BAD_URI;
1396     }
1397
1398 #ifdef DISABLE_KEYSERVER_HELPERS
1399
1400   log_error(_("external keyserver calls are not supported in this build\n"));
1401   return G10ERR_KEYSERVER;
1402
1403 #else
1404   /* Spawn a handler */
1405
1406   rc=keyserver_spawn(action,list,desc,count,&ret,keyserver);
1407   if(ret)
1408     {
1409       switch(ret)
1410         {
1411         case KEYSERVER_SCHEME_NOT_FOUND:
1412           log_error(_("no handler for keyserver scheme `%s'\n"),
1413                     keyserver->scheme);
1414           break;
1415
1416         case KEYSERVER_NOT_SUPPORTED:
1417           log_error(_("action `%s' not supported with keyserver "
1418                       "scheme `%s'\n"),
1419                     action==GET?"get":action==SEND?"send":
1420                     action==SEARCH?"search":"unknown",
1421                     keyserver->scheme);
1422           break;
1423
1424         case KEYSERVER_VERSION_ERROR:
1425           log_error(_(GPGKEYS_PREFIX "%s does not support"
1426                       " handler version %d\n"),
1427                     keyserver_typemap(keyserver->scheme),
1428                     KEYSERVER_PROTO_VERSION);
1429           break;
1430
1431         case KEYSERVER_TIMEOUT:
1432           log_error(_("keyserver timed out\n"));
1433           break;
1434
1435         case KEYSERVER_INTERNAL_ERROR:
1436         default:
1437           log_error(_("keyserver internal error\n"));
1438           break;
1439         }
1440
1441       return G10ERR_KEYSERVER;
1442     }
1443
1444   if(rc)
1445     {
1446       log_error(_("keyserver communications error: %s\n"),g10_errstr(rc));
1447
1448       return rc;
1449     }
1450
1451   return 0;
1452 #endif /* ! DISABLE_KEYSERVER_HELPERS*/
1453 }
1454
1455 int 
1456 keyserver_export(STRLIST users)
1457 {
1458   STRLIST sl=NULL;
1459   KEYDB_SEARCH_DESC desc;
1460   int rc=0;
1461
1462   /* Weed out descriptors that we don't support sending */
1463   for(;users;users=users->next)
1464     {
1465       classify_user_id (users->d, &desc);
1466       if(desc.mode!=KEYDB_SEARCH_MODE_SHORT_KID &&
1467          desc.mode!=KEYDB_SEARCH_MODE_LONG_KID &&
1468          desc.mode!=KEYDB_SEARCH_MODE_FPR16 &&
1469          desc.mode!=KEYDB_SEARCH_MODE_FPR20)
1470         {
1471           log_error(_("\"%s\" not a key ID: skipping\n"),users->d);
1472           continue;
1473         }
1474       else
1475         append_to_strlist(&sl,users->d);
1476     }
1477
1478   if(sl)
1479     {
1480       rc=keyserver_work(SEND,sl,NULL,0,opt.keyserver);
1481       free_strlist(sl);
1482     }
1483
1484   return rc;
1485 }
1486
1487 int 
1488 keyserver_import(STRLIST users)
1489 {
1490   KEYDB_SEARCH_DESC *desc;
1491   int num=100,count=0;
1492   int rc=0;
1493
1494   /* Build a list of key ids */
1495   desc=xmalloc(sizeof(KEYDB_SEARCH_DESC)*num);
1496
1497   for(;users;users=users->next)
1498     {
1499       classify_user_id (users->d, &desc[count]);
1500       if(desc[count].mode!=KEYDB_SEARCH_MODE_SHORT_KID &&
1501          desc[count].mode!=KEYDB_SEARCH_MODE_LONG_KID &&
1502          desc[count].mode!=KEYDB_SEARCH_MODE_FPR16 &&
1503          desc[count].mode!=KEYDB_SEARCH_MODE_FPR20)
1504         {
1505           log_error(_("\"%s\" not a key ID: skipping\n"),users->d);
1506           continue;
1507         }
1508
1509       count++;
1510       if(count==num)
1511         {
1512           num+=100;
1513           desc=xrealloc(desc,sizeof(KEYDB_SEARCH_DESC)*num);
1514         }
1515     }
1516
1517   if(count>0)
1518     rc=keyserver_work(GET,NULL,desc,count,opt.keyserver);
1519
1520   xfree(desc);
1521
1522   return rc;
1523 }
1524
1525 int
1526 keyserver_import_fprint(const byte *fprint,size_t fprint_len,
1527                         struct keyserver_spec *keyserver)
1528 {
1529   KEYDB_SEARCH_DESC desc;
1530
1531   memset(&desc,0,sizeof(desc));
1532
1533   if(fprint_len==16)
1534     desc.mode=KEYDB_SEARCH_MODE_FPR16;
1535   else if(fprint_len==20)
1536     desc.mode=KEYDB_SEARCH_MODE_FPR20;
1537   else
1538     return -1;
1539
1540   memcpy(desc.u.fpr,fprint,fprint_len);
1541
1542   return keyserver_work(GET,NULL,&desc,1,keyserver);
1543 }
1544
1545 int 
1546 keyserver_import_keyid(u32 *keyid,struct keyserver_spec *keyserver)
1547 {
1548   KEYDB_SEARCH_DESC desc;
1549
1550   memset(&desc,0,sizeof(desc));
1551
1552   desc.mode=KEYDB_SEARCH_MODE_LONG_KID;
1553   desc.u.kid[0]=keyid[0];
1554   desc.u.kid[1]=keyid[1];
1555
1556   return keyserver_work(GET,NULL,&desc,1,keyserver);
1557 }
1558
1559 /* code mostly stolen from do_export_stream */
1560 static int 
1561 keyidlist(STRLIST users,KEYDB_SEARCH_DESC **klist,int *count,int fakev3)
1562 {
1563   int rc=0,ndesc,num=100;
1564   KBNODE keyblock=NULL,node;
1565   KEYDB_HANDLE kdbhd;
1566   KEYDB_SEARCH_DESC *desc;
1567   STRLIST sl;
1568
1569   *count=0;
1570
1571   *klist=xmalloc(sizeof(KEYDB_SEARCH_DESC)*num);
1572
1573   kdbhd=keydb_new(0);
1574
1575   if(!users)
1576     {
1577       ndesc = 1;
1578       desc = xmalloc_clear ( ndesc * sizeof *desc);
1579       desc[0].mode = KEYDB_SEARCH_MODE_FIRST;
1580     }
1581   else
1582     {
1583       for (ndesc=0, sl=users; sl; sl = sl->next, ndesc++) 
1584         ;
1585       desc = xmalloc ( ndesc * sizeof *desc);
1586         
1587       for (ndesc=0, sl=users; sl; sl = sl->next)
1588         {
1589           if(classify_user_id (sl->d, desc+ndesc))
1590             ndesc++;
1591           else
1592             log_error (_("key \"%s\" not found: %s\n"),
1593                        sl->d, g10_errstr (G10ERR_INV_USER_ID));
1594         }
1595     }
1596
1597   while (!(rc = keydb_search (kdbhd, desc, ndesc)))
1598     {
1599       if (!users) 
1600         desc[0].mode = KEYDB_SEARCH_MODE_NEXT;
1601
1602       /* read the keyblock */
1603       rc = keydb_get_keyblock (kdbhd, &keyblock );
1604       if( rc )
1605         {
1606           log_error (_("error reading keyblock: %s\n"), g10_errstr(rc) );
1607           goto leave;
1608         }
1609
1610       if((node=find_kbnode(keyblock,PKT_PUBLIC_KEY)))
1611         {
1612           /* This is to work around a bug in some keyservers (pksd and
1613              OKS) that calculate v4 RSA keyids as if they were v3 RSA.
1614              The answer is to refresh both the correct v4 keyid
1615              (e.g. 99242560) and the fake v3 keyid (e.g. 68FDDBC7).
1616              This only happens for key refresh using the HKP scheme
1617              and if the refresh-add-fake-v3-keyids keyserver option is
1618              set. */
1619           if(fakev3 && is_RSA(node->pkt->pkt.public_key->pubkey_algo) &&
1620              node->pkt->pkt.public_key->version>=4)
1621             {
1622               (*klist)[*count].mode=KEYDB_SEARCH_MODE_LONG_KID;
1623               mpi_get_keyid(node->pkt->pkt.public_key->pkey[0],
1624                             (*klist)[*count].u.kid);
1625               (*count)++;
1626
1627               if(*count==num)
1628                 {
1629                   num+=100;
1630                   *klist=xrealloc(*klist,sizeof(KEYDB_SEARCH_DESC)*num);
1631                 }
1632             }
1633
1634           /* v4 keys get full fingerprints.  v3 keys get long keyids.
1635              This is because it's easy to calculate any sort of keyid
1636              from a v4 fingerprint, but not a v3 fingerprint. */
1637
1638           if(node->pkt->pkt.public_key->version<4)
1639             {
1640               (*klist)[*count].mode=KEYDB_SEARCH_MODE_LONG_KID;
1641               keyid_from_pk(node->pkt->pkt.public_key,
1642                             (*klist)[*count].u.kid);
1643             }
1644           else
1645             {
1646               size_t dummy;
1647
1648               (*klist)[*count].mode=KEYDB_SEARCH_MODE_FPR20;
1649               fingerprint_from_pk(node->pkt->pkt.public_key,
1650                                   (*klist)[*count].u.fpr,&dummy);
1651             }
1652
1653           /* This is a little hackish, using the skipfncvalue as a
1654              void* pointer to the keyserver spec, but we don't need
1655              the skipfnc here, and it saves having an additional field
1656              for this (which would be wasted space most of the
1657              time). */
1658
1659           (*klist)[*count].skipfncvalue=NULL;
1660
1661           /* Are we honoring preferred keyservers? */
1662           if(opt.keyserver_options.options&KEYSERVER_HONOR_KEYSERVER_URL)
1663             {
1664               PKT_user_id *uid=NULL;
1665               PKT_signature *sig=NULL;
1666
1667               merge_keys_and_selfsig(keyblock);
1668
1669               for(node=node->next;node;node=node->next)
1670                 {
1671                   if(node->pkt->pkttype==PKT_USER_ID
1672                      && node->pkt->pkt.user_id->is_primary)
1673                     uid=node->pkt->pkt.user_id;
1674                   else if(node->pkt->pkttype==PKT_SIGNATURE
1675                           && node->pkt->pkt.signature->
1676                           flags.chosen_selfsig && uid)
1677                     {
1678                       sig=node->pkt->pkt.signature;
1679                       break;
1680                     }
1681                 }
1682
1683               /* Try and parse the keyserver URL.  If it doesn't work,
1684                  then we end up writing NULL which indicates we are
1685                  the same as any other key. */
1686               if(uid && sig)
1687                 (*klist)[*count].skipfncvalue=parse_preferred_keyserver(sig);
1688             }
1689
1690           (*count)++;
1691
1692           if(*count==num)
1693             {
1694               num+=100;
1695               *klist=xrealloc(*klist,sizeof(KEYDB_SEARCH_DESC)*num);
1696             }
1697         }
1698     }
1699
1700   if(rc==-1)
1701     rc=0;
1702   
1703  leave:
1704   if(rc)
1705     xfree(*klist);
1706   xfree(desc);
1707   keydb_release(kdbhd);
1708   release_kbnode(keyblock);
1709
1710   return rc;
1711 }
1712
1713 /* Note this is different than the original HKP refresh.  It allows
1714    usernames to refresh only part of the keyring. */
1715
1716 int
1717 keyserver_refresh(STRLIST users)
1718 {
1719   int rc,count,numdesc,fakev3=0;
1720   KEYDB_SEARCH_DESC *desc;
1721   unsigned int options=opt.keyserver_options.import_options;
1722
1723   /* We switch merge-only on during a refresh, as 'refresh' should
1724      never import new keys, even if their keyids match. */
1725   opt.keyserver_options.import_options|=IMPORT_MERGE_ONLY;
1726
1727   /* Similarly, we switch on fast-import, since refresh may make
1728      multiple import sets (due to preferred keyserver URLs).  We don't
1729      want each set to rebuild the trustdb.  Instead we do it once at
1730      the end here. */
1731   opt.keyserver_options.import_options|=IMPORT_FAST;
1732
1733   /* If refresh_add_fake_v3_keyids is on and it's a HKP or MAILTO
1734      scheme, then enable fake v3 keyid generation. */
1735   if((opt.keyserver_options.options&KEYSERVER_ADD_FAKE_V3) && opt.keyserver
1736      && (ascii_strcasecmp(opt.keyserver->scheme,"hkp")==0 ||
1737          ascii_strcasecmp(opt.keyserver->scheme,"mailto")==0))
1738     fakev3=1;
1739
1740   rc=keyidlist(users,&desc,&numdesc,fakev3);
1741   if(rc)
1742     return rc;
1743
1744   count=numdesc;
1745   if(count>0)
1746     {
1747       int i;
1748
1749       /* Try to handle preferred keyserver keys first */
1750       for(i=0;i<count;i++)
1751         {
1752           if(desc[i].skipfncvalue)
1753             {
1754               struct keyserver_spec *keyserver=desc[i].skipfncvalue;
1755
1756               /* We use the keyserver structure we parsed out before.
1757                  Note that a preferred keyserver without a scheme://
1758                  will be interpreted as hkp:// */
1759
1760               rc=keyserver_work(GET,NULL,&desc[i],1,keyserver);
1761               if(rc)
1762                 log_info(_("WARNING: unable to refresh key %s"
1763                            " via %s: %s\n"),keystr_from_desc(&desc[i]),
1764                          keyserver->uri,g10_errstr(rc));
1765               else
1766                 {
1767                   /* We got it, so mark it as NONE so we don't try and
1768                      get it again from the regular keyserver. */
1769
1770                   desc[i].mode=KEYDB_SEARCH_MODE_NONE;
1771                   count--;
1772                 }
1773
1774               free_keyserver_spec(keyserver);
1775             }
1776         }
1777     }
1778
1779   if(count>0)
1780     {
1781       if(opt.keyserver)
1782         {
1783           if(count==1)
1784             log_info(_("refreshing 1 key from %s\n"),opt.keyserver->uri);
1785           else
1786             log_info(_("refreshing %d keys from %s\n"),
1787                      count,opt.keyserver->uri);
1788         }
1789
1790       rc=keyserver_work(GET,NULL,desc,numdesc,opt.keyserver);
1791     }
1792
1793   xfree(desc);
1794
1795   opt.keyserver_options.import_options=options;
1796
1797   /* If the original options didn't have fast import, and the trustdb
1798      is dirty, rebuild. */
1799   if(!(opt.keyserver_options.import_options&IMPORT_FAST))
1800     trustdb_check_or_update();
1801
1802   return rc;
1803 }
1804
1805 int
1806 keyserver_search(STRLIST tokens)
1807 {
1808   if(tokens)
1809     return keyserver_work(SEARCH,tokens,NULL,0,opt.keyserver);
1810   else
1811     return 0;
1812 }
1813
1814 int
1815 keyserver_fetch(STRLIST urilist)
1816 {
1817   KEYDB_SEARCH_DESC desc;
1818   STRLIST sl;
1819
1820   /* A dummy desc since we're not actually fetching a particular key
1821      ID */
1822   memset(&desc,0,sizeof(desc));
1823   desc.mode=KEYDB_SEARCH_MODE_EXACT;
1824
1825   for(sl=urilist;sl;sl=sl->next)
1826     {
1827       struct keyserver_spec *spec;
1828
1829       spec=parse_keyserver_uri(sl->d,1,NULL,0);
1830       if(spec)
1831         {
1832           int rc=keyserver_work(GET,NULL,&desc,1,spec);
1833           if(rc)
1834             log_info("WARNING: unable to fetch URI %s: %s\n",
1835                      sl->d,g10_errstr(rc));
1836           free_keyserver_spec(spec);
1837         }
1838       else
1839         log_info("WARNING: unable to parse URI %s\n",sl->d);
1840     }
1841
1842   return 0;
1843 }