/[winpt]/trunk/Src/wptKeyEditCB.cpp
ViewVC logotype

Diff of /trunk/Src/wptKeyEditCB.cpp

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 28 by twoaday, Thu Oct 20 12:35:59 2005 UTC revision 160 by twoaday, Thu Jan 19 09:22:09 2006 UTC
# Line 1  Line 1 
1  /* wptKeyEditCB.cpp - Key edit callback handling  /* wptKeyEditCB.cpp - Key edit callback handling
2   *      Copyright (C) 2005 Timo Schulz   *      Copyright (C) 2005 Timo Schulz
3   *      Copyright (C) 2005 g10 Code GmbH   *      Copyright (C) 2005 g10 Code GmbH
4   *   *
5   * This file is part of WinPT.   * This file is part of WinPT.
6   *   *
7   * WinPT is free software; you can redistribute it and/or   * WinPT is free software; you can redistribute it and/or
8   * modify it under the terms of the GNU General Public License   * modify it under the terms of the GNU General Public License
9   * as published by the Free Software Foundation; either version 2   * as published by the Free Software Foundation; either version 2
10   * of the License, or (at your option) any later version.   * of the License, or (at your option) any later version.
11   *     *  
12   * WinPT is distributed in the hope that it will be useful,   * WinPT is distributed in the hope that it will be useful,
13   * but WITHOUT ANY WARRANTY; without even the implied warranty of   * but WITHOUT ANY WARRANTY; without even the implied warranty of
14   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15   * General Public License for more details.   * General Public License for more details.
16   *   *
17   * You should have received a copy of the GNU General Public License   * You should have received a copy of the GNU General Public License
18   * along with WinPT; if not, write to the Free Software Foundation,   * along with WinPT; if not, write to the Free Software Foundation,
19   * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA   * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20   */   */
21  #include <stdio.h>  
22  #include <string.h>  #ifdef HAVE_CONFIG_H
23  #include <stdlib.h>  #include <config.h>
24  #include <assert.h>  #endif
25  #include <windows.h>  
26    #include <stdio.h>
27  #include "gpgme.h"  #include <string.h>
28  #include "wptCommonCtl.h"  #include <stdlib.h>
29  #include "wptContext.h"  #include <assert.h>
30  #include "wptKeyEdit.h"  #include <windows.h>
31  #include "wptErrors.h"  
32    #include "gpgme.h"
33    #include "wptCommonCtl.h"
34  /* 'keyserver' command handler. */  #include "wptContext.h"
35  static const char*  #include "wptKeyEdit.h"
36  cmd_keyserv_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)  #include "wptErrors.h"
37  {  
38      static char buf[32];  /* Possible errors for the edit key operation. */
39    enum editkey_error_t {
40      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {      EDITKEY_ERR_ALREADY_SIGNED = 1,
41          ctx->cmd_sent = 1;      EDITKEY_ERR_BAD_PASSPHRASE = 2
42          sprintf (buf, "uid %d", ctx->uid_index);  };
43          return buf;  
44      }  /* 'keyserver' command handler. */
45      if (!strcmp (key, "keyedit.prompt") && !ctx->cnt) {  static const char*
46          ctx->cnt = 1;  cmd_keyserv_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)
47          return "keyserver";  {
48      }      static char buf[32];
49      if (!strcmp (key, "keyedit.add_keyserver"))  
50          return ctx->url;      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {
51      if ( !strcmp (key, "keyedit.confirm_keyserver"))          ctx->cmd_sent = 1;
52          return "Y";          sprintf (buf, "uid %d", ctx->uid_index);
53      if (!strcmp (key, "passphrase.enter"))          return buf;
54          return ctx->pass;      }
55      if (!strcmp (key, "keyedit.prompt") && ctx->cnt == 1) {      if (!strcmp (key, "keyedit.prompt") && !ctx->cnt) {
56          ctx->reset ();          ctx->cnt = 1;
57          return "save";          return "keyserver";
58      }      }
59        if (!strcmp (key, "keyedit.add_keyserver"))
60      return NULL;          return ctx->url;
61  }      if ( !strcmp (key, "keyedit.confirm_keyserver"))
62            return "Y";
63        if (!strcmp (key, "passphrase.enter"))
64  static const char*          return ctx->pass;
65  cmd_sign_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)      if (!strcmp (key, "keyedit.prompt") && ctx->cnt == 1) {
66  {          ctx->reset ();
67      static char buf[32];          return "save";
68        }
69      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {  
70          ctx->cmd_sent = 1;      return NULL;
71          switch (ctx->getType ()) {  }
72          case GPG_EDITKEY_SIGN: return "sign";  
73          case GPG_EDITKEY_TSIGN: return "tsign";  
74          case GPG_EDITKEY_LSIGN: return "lsign";  /* 'sign' command handler. */
75          case GPG_EDITKEY_NRSIGN: return"nrsign";  static const char*
76          case GPG_EDITKEY_NRLSIGN: return "nrlsign";  cmd_sign_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)
77          }  {
78      }      static char buf[32];
79      if (!strcmp (key, "sign_uid.class")) {  
80          sprintf (buf, "%d", ctx->sig_class);      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {
81          return buf;          ctx->cmd_sent = 1;
82      }          switch (ctx->getType ()) {
83      if (!strcmp (key, "sign_uid.expire"))          case GPG_EDITKEY_SIGN: return "sign";
84          return "Y"; /* the sig expires when the key expires */          case GPG_EDITKEY_TSIGN: return "tsign";
85      if (!strcmp (key, "siggen.valid"))          case GPG_EDITKEY_LSIGN: return "lsign";
86          return ctx->exp_date;          case GPG_EDITKEY_NRSIGN: return"nrsign";
87      if (!strcmp (key, "trustsig_prompt.trust_value")) {          case GPG_EDITKEY_NRLSIGN: return "nrlsign";
88          sprintf (buf, "%d", ctx->trust_id);          }
89          return buf;      }
90      }      if (!strcmp (key, "sign_uid.class")) {
91      if (!strcmp (key, "trustsig_prompt.trust_depth"))          sprintf (buf, "%d", ctx->sig_class);
92          return ""; /* fixme */          return buf;
93      if (!strcmp (key, "trustsig_prompt.trust_regexp"))      }
94          return ""; /* fixme */      if (!strcmp (key, "sign_uid.expire"))
95      if (!strcmp (key, "sign_uid.local_promote_okay" ) )          return "Y"; /* the sig expires when the key expires */
96          return "Y";      if (!strcmp (key, "siggen.valid"))
97      if (!strcmp (key, "sign_uid.okay" ) )          return ctx->exp_date;
98          return "Y";      if (!strcmp (key, "trustsig_prompt.trust_value")) {
99      if (!strcmp (key, "keyedit.sign_all.okay"))          sprintf (buf, "%d", ctx->trust_id);
100          return "Y";          return buf;
101      if (!strcmp ( key, "passphrase.enter"))      }
102          return ctx->pass;      if (!strcmp (key, "trustsig_prompt.trust_depth"))
103      if (!strcmp (key, "keyedit.prompt")) {          return ""; /* fixme */
104          ctx->reset ();      if (!strcmp (key, "trustsig_prompt.trust_regexp"))
105          return "save";          return ""; /* fixme */
106      }      if (!strcmp (key, "sign_uid.local_promote_okay" ) )
107                return "Y";
108      return NULL;      if (!strcmp (key, "sign_uid.okay" ) )
109  }          return "Y";
110        if (!strcmp (key, "keyedit.sign_all.okay"))
111  /* 'trust' command handler. */          return "Y";
112  static const char*      if (!strcmp ( key, "passphrase.enter"))
113  cmd_trust_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)          return ctx->pass;
114  {      if (!strcmp (key, "keyedit.prompt")) {
115      static char buf[4];          ctx->reset ();
116            return "save";
117      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {      }
118          ctx->cmd_sent = 1;      
119          return "trust";      return NULL;
120      }  }
121      if (!strcmp (key, "edit_ownertrust.set_ultimate.okay"))  
122          return "Y";  /* 'trust' command handler. */
123      if (!strcmp (key, "edit_ownertrust.value" )) {  static const char*
124          sprintf (buf, "%d", ctx->trust_id);  cmd_trust_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)
125          return buf;  {
126      }      static char buf[4];
127      if (!strcmp (key, "keyedit.prompt")) {  
128          ctx->reset ();      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {
129          return "save";          ctx->cmd_sent = 1;
130      }          return "trust";
131        }
132      return NULL;      if (!strcmp (key, "edit_ownertrust.set_ultimate.okay"))
133  }          return "Y";
134        if (!strcmp (key, "edit_ownertrust.value" )) {
135            sprintf (buf, "%d", ctx->trust_id);
136  /* 'adduid' command handler. */          return buf;
137  static const char*      }
138  cmd_adduid_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)      if (!strcmp (key, "keyedit.prompt")) {
139  {          ctx->reset ();
140      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {          return "save";
141          ctx->cmd_sent = 1;      }
142          return "adduid";  
143      }      return NULL;
144      if (!strcmp (key, "keygen.name"))  }
145          return ctx->name;  
146      if (!strcmp (key, "keygen.email"))  
147          return ctx->email;  /* 'adduid' command handler. */
148      if (!strcmp (key, "keygen.comment"))  static const char*
149          return ctx->cmt? ctx->cmt : "";  cmd_adduid_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)
150      if (!strcmp (key, "passphrase.enter"))  {
151          return ctx->pass;      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {
152      if( !strcmp (key, "keyedit.prompt")) {          ctx->cmd_sent = 1;
153          ctx->reset ();          return "adduid";
154          return "save";      }
155      }      if (!strcmp (key, "keygen.name"))
156            return ctx->name;
157      return NULL;      if (!strcmp (key, "keygen.email"))
158  }          return ctx->email;
159        if (!strcmp (key, "keygen.comment"))
160            return ctx->cmt? ctx->cmt : "";
161  static const char*      if (!strcmp (key, "passphrase.enter"))
162  cmd_deluid_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key,          return ctx->pass;
163                      int *r_step)      if( !strcmp (key, "keyedit.prompt")) {
164  {          ctx->reset ();
165      static char buf[64];          return "save";
166      int step = *r_step;      }
167    
168      if (step == 0 && !strcmp (key, "keyedit.prompt")) {      return NULL;
169          sprintf (buf, "uid %d", ctx->uid_index);  }
170          *r_step = step = 1;  
171          return buf;  
172      }  static const char*
173      if (step == 1 && !strcmp (key, "keyedit.prompt")) {  cmd_deluid_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key,
174          *r_step = step = 2;                      int *r_step)
175          return "deluid";  {
176      }      static char buf[64];
177      if (step == 2 && !strcmp (key, "keyedit.remove.uid.okay")) {      int step = *r_step;
178          *r_step = step = 3;  
179          return "Y";      if (step == 0 && !strcmp (key, "keyedit.prompt")) {
180      }          sprintf (buf, "uid %d", ctx->uid_index);
181      if (step == 3 && !strcmp (key, "keyedit.prompt" )) {          *r_step = step = 1;
182          *r_step = step = 0;          return buf;
183          ctx->reset ();      }
184          return "save";      if (step == 1 && !strcmp (key, "keyedit.prompt")) {
185      }          *r_step = step = 2;
186                return "deluid";
187      return NULL;      }
188  }      if (step == 2 && !strcmp (key, "keyedit.remove.uid.okay")) {
189            *r_step = step = 3;
190            return "Y";
191  static const char *      }
192  cmd_delsig_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char * key,      if (step == 3 && !strcmp (key, "keyedit.prompt" )) {
193                      int * r_step)          *r_step = step = 0;
194  {          ctx->reset ();
195      static char buf[64];          return "save";
196      int step = *r_step;      }
197        
198      if (step == 0 && !strcmp (key, "keyedit.prompt")) {      return NULL;
199          sprintf (buf, "uid %d", ctx->uid_index);  }
200          *r_step = step = 1;  
201          return buf;  
202      }  static const char *
203      if (step == 1 && !strcmp (key, "keyedit.prompt")) {  cmd_delsig_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char * key,
204          *r_step = step = 2;                      int * r_step)
205          return "delsig";  {
206      }      static char buf[64];
207      if (!strcmp (key, "keyedit.delsig.unknown") ||      int step = *r_step;
208          !strcmp (key, "keyedit.delsig.valid")) {  
209          if (++ctx->cnt == ctx->sig_index)      if (step == 0 && !strcmp (key, "keyedit.prompt")) {
210              return "Y";          sprintf (buf, "uid %d", ctx->uid_index);
211          else          *r_step = step = 1;
212              return "N";          return buf;
213      }      }
214      if (ctx->sig_index == 0 &&      if (step == 1 && !strcmp (key, "keyedit.prompt")) {
215          !strcmp (key, "keyedit.delsig.selfsig"))          *r_step = step = 2;
216          return "Y";          return "delsig";
217      if (step == 2 && !strcmp (key, "keyedit.prompt")) {      }
218          *r_step = step = 0;      if (!strcmp (key, "keyedit.delsig.unknown") ||
219          ctx->reset ();          !strcmp (key, "keyedit.delsig.valid")) {
220          return "save";          if (++ctx->cnt == ctx->sig_index)
221      }              return "Y";
222      return NULL;          else
223  }              return "N";
224        }
225        if (!strcmp (key, "keyedit.delsig.selfsig"))
226  /* 'delkey' command handler. */          return "Y";
227  static const char*      if (step == 2 && !strcmp (key, "keyedit.prompt")) {
228  cmd_delkey_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,          *r_step = step = 0;
229                      const char *key, int *r_step )          ctx->reset ();
230  {          return "save";
231      static char buf[64];      }
232      int step = *r_step;      return NULL;
233    }
234      if (step == 0 && !strcmp (key, "keyedit.prompt")) {  
235          sprintf (buf, "key %d", ctx->key_index);  
236          *r_step = step = 1;  /* 'delkey' command handler. */
237          return buf;  static const char*
238      }  cmd_delkey_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,
239      if (step == 1 && !strcmp (key, "keyedit.prompt")) {                      const char *key, int *r_step )
240          *r_step = step = 2;  {
241          return "delkey";      static char buf[64];
242      }      int step = *r_step;
243      if (step == 2 && !strcmp (key, "keyedit.remove.subkey.okay")) {  
244          *r_step = step = 3;      if (step == 0 && !strcmp (key, "keyedit.prompt")) {
245          return "Y";          sprintf (buf, "key %d", ctx->key_index);
246      }          *r_step = step = 1;
247      if (step == 3 && !strcmp (key, "keyedit.prompt")) {          return buf;
248          *r_step = step = 0;      }
249          ctx->reset ();      if (step == 1 && !strcmp (key, "keyedit.prompt")) {
250          return "save";          *r_step = step = 2;
251      }          return "delkey";
252        }
253      return NULL;      if (step == 2 && !strcmp (key, "keyedit.remove.subkey.okay")) {
254  }          *r_step = step = 3;
255            return "Y";
256        }
257  /* 'addkey' command handler. */      if (step == 3 && !strcmp (key, "keyedit.prompt")) {
258  static const char*          *r_step = step = 0;
259  cmd_addkey_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)          ctx->reset ();
260  {          return "save";
261      static char buf[64];      }
262    
263      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {      return NULL;
264          ctx->cmd_sent = 1;  }
265          return "addkey";  
266      }  
267    /* 'addkey' command handler. */
268      if (!strcmp (key, "passphrase.enter"))  static const char*
269          return ctx->pass;  cmd_addkey_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)
270      if (!strcmp (key, "keygen.algo")) {  {
271          _snprintf (buf, sizeof buf-1, "%d", ctx->pubkey_algo);      static char buf[64];
272          return buf;  
273      }        if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {
274      if (!strcmp (key, "keygen.size")) {          ctx->cmd_sent = 1;
275          _snprintf (buf, sizeof buf-1, "%d", ctx->pubkey_size);          return "addkey";
276          return buf;      }
277      }  
278      if (!strcmp (key, "keygen.valid")) {      if (!strcmp (key, "passphrase.enter"))
279          _snprintf (buf, sizeof buf-1, "%d", ctx->valid);          return ctx->pass;
280          return buf;              if (!strcmp (key, "keygen.algo")) {
281      }          _snprintf (buf, sizeof (buf)-1, "%d", ctx->pubkey_algo);
282      if (!strcmp (key, "keyedit.prompt")) {          return buf;
283          ctx->reset ();      }  
284          return "save";      if (!strcmp (key, "keygen.size")) {
285      }          _snprintf (buf, sizeof (buf)-1, "%d", ctx->pubkey_size);
286      return NULL;          return buf;
287  }      }
288        if (!strcmp (key, "keygen.valid")) {
289  /* 'passwd' command handler. */          _snprintf (buf, sizeof (buf)-1, "%d", ctx->valid);
290  static const char*          return buf;        
291  cmd_passwd_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)      }
292  {      if (!strcmp (key, "keyedit.prompt")) {
293      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {          ctx->reset ();
294          ctx->cmd_sent = 1;          return "save";
295          return "passwd";      }
296      }      return NULL;
297      if( !strcmp (key, "passphrase.enter") && !ctx->cnt) {  }
298          ctx->cnt = 1;  
299          return ctx->pass;  /* 'passwd' command handler. */
300      }  static const char*
301      if( !strcmp (key, "passphrase.enter" ))  cmd_passwd_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)
302          return ctx->new_pass;  {
303      if( !strcmp (key, "change_passwd.empty.okay" ))      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {
304          return ctx->flags?  "Y" : "N";          ctx->cmd_sent = 1;
305      if (!strcmp (key, "keyedit.prompt")) {          return "passwd";
306          ctx->reset ();      }
307          return "save";      if (!ctx->cnt && !strcmp (key, "passphrase.enter")) {
308      }          ctx->cnt = 1;
309      return NULL;          return ctx->pass;
310  }      }
311        if (!strcmp (key, "passphrase.enter" ))
312            return ctx->new_pass;
313  static const char*      if (!strcmp (key, "change_passwd.empty.okay" ))
314  cmd_setpref_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char * key)          return ctx->flags?  "Y" : "N";
315  {      if (!strcmp (key, "keyedit.prompt")) {
316      static char buf[128];          ctx->reset ();
317            return "save";
318      /* XXX: check the code. */      }
319  #if 0  
320      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {      return NULL;
321          ctx->cmd_sent = 1;  }
322          return "";  
323      }  
324      if (!strcmp ( key, "keyedit.prompt") && ctx->u.pref.id == 0) {  static const char*
325          ctx->u.pref.id++;  cmd_setpref_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char * key)
326          _snprintf (buf, sizeof buf-1, "setpref %s", ctx->u.pref.new_prefs);  {
327          return buf;      static char buf[128];
328      }  
329      if (!strcmp ( key, "keyedit.prompt") && ctx->u.pref.id == 1) {      /* XXX: check the code. */
330          ctx->u.pref.id++;  #if 0
331          return "updpref";      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {
332      }          ctx->cmd_sent = 1;
333      if (!strcmp ( key, "keyedit.updpref.okay"))          return "";
334          return "Y";      }
335      if (!strcmp (key, "passphrase.enter"))      if (!strcmp ( key, "keyedit.prompt") && ctx->u.pref.id == 0) {
336          return ctx->u.pref.passwd;          ctx->u.pref.id++;
337      if (!strcmp (key, "keyedit.prompt") && ctx->u.pref.id == 2) {          _snprintf (buf, sizeof buf-1, "setpref %s", ctx->u.pref.new_prefs);
338          ctx->u.pref.id = 0;          return buf;
339          ctx->reset ();      }
340          return "save";      if (!strcmp ( key, "keyedit.prompt") && ctx->u.pref.id == 1) {
341      }          ctx->u.pref.id++;
342  #endif          return "updpref";
343      return NULL;      }
344  }      if (!strcmp ( key, "keyedit.updpref.okay"))
345            return "Y";
346        if (!strcmp (key, "passphrase.enter"))
347  /* 'primary' command handler. */          return ctx->u.pref.passwd;
348  static const char*      if (!strcmp (key, "keyedit.prompt") && ctx->u.pref.id == 2) {
349  cmd_primary_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,          ctx->u.pref.id = 0;
350                       const char *key, int *r_step )          ctx->reset ();
351  {          return "save";
352      static char buf[64];      }
353      int step = *r_step;  #endif
354        return NULL;
355      if (step == 0 && !strcmp (key, "keyedit.prompt")) {  }
356          sprintf (buf, "uid %d", ctx->uid_index);  
357          *r_step = step = 1;  
358          return buf;  /* 'primary' command handler. */
359      }  static const char*
360      if (step == 1 && !strcmp (key, "keyedit.prompt" )) {  cmd_primary_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,
361          *r_step = step = 2;                       const char *key, int *r_step )
362          return "primary";  {
363      }      static char buf[64];
364      if (step == 2 && !strcmp (key, "passphrase.enter")) {      int step = *r_step;
365          *r_step = step = 3;  
366          return ctx->pass;      if (step == 0 && !strcmp (key, "keyedit.prompt")) {
367      }          sprintf (buf, "uid %d", ctx->uid_index);
368      if (step == 3 && !strcmp (key, "keyedit.prompt")) {          *r_step = step = 1;
369          *r_step = step = 0;          return buf;
370          ctx->reset ();      }
371          return "save";      if (step == 1 && !strcmp (key, "keyedit.prompt" )) {
372      }          *r_step = step = 2;
373      return NULL;          return "primary";
374  }      }
375        if (step == 2 && !strcmp (key, "passphrase.enter")) {
376  /* 'expire' command handler. */          *r_step = step = 3;
377  static const char*          return ctx->pass;
378  cmd_expire_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,      }
379                      const char *key, int *r_step )      if (step == 3 && !strcmp (key, "keyedit.prompt")) {
380  {          *r_step = step = 0;
381      static char buf[64];          ctx->reset ();
382      int step = *r_step;          return "save";
383        }
384      if (step == 0 && !strcmp (key, "keyedit.prompt")) {      return NULL;
385          sprintf (buf, "key %d", ctx->key_index);  }
386          *r_step = step = 1;  
387          return buf;  /* 'expire' command handler. */
388      }  static const char*
389      if (step == 1 && !strcmp (key, "keyedit.prompt")) {  cmd_expire_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,
390          *r_step = step = 2;                      const char *key, int *r_step )
391          return "expire";  {
392      }      static char buf[64];
393      if( step == 2 && !strcmp ( key, "keygen.valid" ) ) {      int step = *r_step;
394          *r_step = step = 3;  
395          sprintf (buf, "%d", ctx->valid);      if (step == 0 && !strcmp (key, "keyedit.prompt")) {
396          return buf;          sprintf (buf, "key %d", ctx->key_index);
397      }          *r_step = step = 1;
398      if (step == 3 && !strcmp (key, "passphrase.enter")) {          return buf;
399          *r_step = step = 4;      }
400          return ctx->pass;      if (step == 1 && !strcmp (key, "keyedit.prompt")) {
401      }          *r_step = step = 2;
402      if (step == 4 && !strcmp (key, "keyedit.prompt")) {          return "expire";
403          *r_step = step = 0;      }
404          ctx->reset ();      if( step == 2 && !strcmp ( key, "keygen.valid" ) ) {
405          return "save";          *r_step = step = 3;
406      }          sprintf (buf, "%d", ctx->valid);
407                return buf;
408      return NULL;      }
409  }      if (step == 3 && !strcmp (key, "passphrase.enter")) {
410            *r_step = step = 4;
411            return ctx->pass;
412  /* 'revuid' command handler. */      }
413  const char*      if (step == 4 && !strcmp (key, "keyedit.prompt")) {
414  cmd_revuid_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,          *r_step = step = 0;
415                      const char *key, int *r_step)          ctx->reset ();
416  {          return "save";
417      static char buf[32];      }
418      int step = *r_step;      
419            return NULL;
420      if (step == 0 && !strcmp (key, "keyedit.prompt")) {  }
421          *r_step = step = 1;  
422          sprintf (buf, "uid %d", ctx->uid_index);  
423          return buf;  /* 'revuid' command handler. */
424      }  const char*
425      else if (step == 1 && !strcmp (key, "keyedit.prompt")) {  cmd_revuid_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,
426          *r_step = step = 2;                      const char *key, int *r_step)
427          return "revuid";  {
428      }      static char buf[32];
429      else if (step == 2 && !strcmp (key, "keyedit.revoke.uid.okay")) {      int step = *r_step;
430          *r_step = step = 3;      
431          return "Y";      if (step == 0 && !strcmp (key, "keyedit.prompt")) {
432      }          *r_step = step = 1;
433      else if (step == 3 && !strcmp (key, "ask_revocation_reason.code")) {          sprintf (buf, "uid %d", ctx->uid_index);
434          *r_step = step = 4;          return buf;
435          return "4";      }
436      }      else if (step == 1 && !strcmp (key, "keyedit.prompt")) {
437      else if (step == 4 && !strcmp (key, "ask_revocation_reason.text")) {          *r_step = step = 2;
438          *r_step = step = 5;          return "revuid";
439          return "";      }
440      }      else if (step == 2 && !strcmp (key, "keyedit.revoke.uid.okay")) {
441      else if (step == 5 && !strcmp (key, "ask_revocation_reason.okay")) {          *r_step = step = 3;
442          *r_step = step = 6;          return "Y";
443          return "Y";      }
444      }      else if (step == 3 && !strcmp (key, "ask_revocation_reason.code")) {
445      else if (step == 6 && !strcmp (key, "passphrase.enter")) {          *r_step = step = 4;
446          *r_step = step = 7;          return "4";
447          return ctx->pass;      }
448      }      else if (step == 4 && !strcmp (key, "ask_revocation_reason.text")) {
449      else if (step == 7 && !strcmp (key, "keyedit.prompt")) {          *r_step = step = 5;
450          *r_step = step = 0;          return "";
451          ctx->reset ();      }
452          return "save";      else if (step == 5 && !strcmp (key, "ask_revocation_reason.okay")) {
453      }          *r_step = step = 6;
454      return NULL;          return "Y";
455  }      }
456        else if (step == 6 && !strcmp (key, "passphrase.enter")) {
457            *r_step = step = 7;
458  const char*          return ctx->pass;
459  cmd_revsig_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,      }
460                      const char *key, int *r_step)      else if (step == 7 && !strcmp (key, "keyedit.prompt")) {
461  {          *r_step = step = 0;
462      static char buf[64];          ctx->reset ();
463      int step = *r_step;          return "save";
464            }
465      if( step == 0 && !strcmp ( key, "keyedit.prompt" ) ) {      return NULL;
466          sprintf( buf, "uid %d", ctx->uid_index);  }
467          *r_step = step = 1;  
468          return buf;  
469      }  const char*
470      if( step == 1 && !strcmp ( key, "keyedit.prompt" ) ) {  cmd_revsig_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,
471          *r_step = step = 2;                      const char *key, int *r_step)
472          return "revsig";  {
473      }      static char buf[64];
474      if( step == 2 && !strcmp (key, "ask_revoke_sig.one" ) ) {      int step = *r_step;
475          *r_step = step = 3;      
476          return "Y";      if( step == 0 && !strcmp ( key, "keyedit.prompt" ) ) {
477      }          sprintf( buf, "uid %d", ctx->uid_index);
478      if( step == 3 && !strcmp (key, "ask_revoke_sig.okay" ) ) {          *r_step = step = 1;
479          *r_step = step = 4;          return buf;
480          return "Y";      }
481      }      if( step == 1 && !strcmp ( key, "keyedit.prompt" ) ) {
482      if( step == 4 && !strcmp ( key, "ask_revocation_reason.code" ) ) {          *r_step = step = 2;
483          *r_step = step = 5;          return "revsig";
484          return "0";      }
485      }      if( step == 2 && !strcmp (key, "ask_revoke_sig.one" ) ) {
486      if( step == 5 && !strcmp ( key, "ask_revocation_reason.text" ) ) {          *r_step = step = 3;
487          *r_step = step = 6;          return "Y";
488          return "";      }
489      }      if( step == 3 && !strcmp (key, "ask_revoke_sig.okay" ) ) {
490      if( step == 6 && !strcmp (key, "ask_revocation_reason.okay" ) ) {          *r_step = step = 4;
491          *r_step = step = 7;          return "Y";
492          return "Y";      }
493      }      if( step == 4 && !strcmp ( key, "ask_revocation_reason.code" ) ) {
494      if( step == 7 && !strcmp (key, "passphrase.enter" ) ) {          *r_step = step = 5;
495          *r_step = step = 8;          return "0";
496          return ctx->pass;      }
497      }      if( step == 5 && !strcmp ( key, "ask_revocation_reason.text" ) ) {
498      if( step == 8 && !strcmp ( key, "keyedit.prompt" ) ) {          *r_step = step = 6;
499          *r_step = step = 0;          return "";
500          ctx->reset ();      }
501          return "save";      if( step == 6 && !strcmp (key, "ask_revocation_reason.okay" ) ) {
502      }          *r_step = step = 7;
503                return "Y";
504      return NULL;      }
505  }      if( step == 7 && !strcmp (key, "passphrase.enter" ) ) {
506            *r_step = step = 8;
507            return ctx->pass;
508  /* 'revoke' command handler. */      }
509  static const char *      if( step == 8 && !strcmp ( key, "keyedit.prompt" ) ) {
510  cmd_revkey_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,          *r_step = step = 0;
511                      const char * key, int *r_step)          ctx->reset ();
512  {          return "save";
513      int step = *r_step;      }
514      static char buf[64];      
515        return NULL;
516      if( step == 0 && !strcmp ( key, "keyedit.prompt" ) ) {  }
517          sprintf( buf, "key %d", ctx->key_index);  
518          *r_step = step = 1;  
519          return buf;  /* 'revoke' command handler. */
520      }  static const char *
521      if( step == 1 && !strcmp ( key, "keyedit.prompt" ) ) {  cmd_revkey_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,
522          *r_step = step = 2;                      const char * key, int *r_step)
523          return "revkey";  {
524      }      int step = *r_step;
525      if( step == 2 && !strcmp (key, "keyedit.revoke.subkey.okay" ) ) {      static char buf[64];
526          *r_step = step = 3;  
527          return "Y";      if( step == 0 && !strcmp ( key, "keyedit.prompt" ) ) {
528      }          sprintf( buf, "key %d", ctx->key_index);
529      if( step == 3 &&  !strcmp ( key, "ask_revocation_reason.code" ) ) {          *r_step = step = 1;
530          sprintf( buf, "%d", ctx->reason);          return buf;
531          *r_step = step = 4;      }
532          return buf;      if( step == 1 && !strcmp ( key, "keyedit.prompt" ) ) {
533      }          *r_step = step = 2;
534      if( step == 4 && !strcmp ( key, "ask_revocation_reason.text" ) ) {          return "revkey";
535          *r_step = step = 5;      }
536          return "";      if( step == 2 && !strcmp (key, "keyedit.revoke.subkey.okay" ) ) {
537      }          *r_step = step = 3;
538      if( step == 5 && !strcmp (key, "ask_revocation_reason.okay" ) ) {          return "Y";
539          *r_step = step = 6;      }
540          return "Y";      if( step == 3 &&  !strcmp ( key, "ask_revocation_reason.code" ) ) {
541      }          sprintf( buf, "%d", ctx->reason);
542      if( step == 6 && !strcmp (key, "passphrase.enter" ) ) {          *r_step = step = 4;
543          *r_step = step = 7;          return buf;
544          return ctx->pass;      }
545      }      if( step == 4 && !strcmp ( key, "ask_revocation_reason.text" ) ) {
546      if( step == 7 && !strcmp ( key, "keyedit.prompt" ) ) {          *r_step = step = 5;
547          *r_step = step = 0;          return "";
548          ctx->reset ();      }
549          return "save";      if( step == 5 && !strcmp (key, "ask_revocation_reason.okay" ) ) {
550      }          *r_step = step = 6;
551      return NULL;          return "Y";
552  }      }
553        if( step == 6 && !strcmp (key, "passphrase.enter" ) ) {
554            *r_step = step = 7;
555  /* 'addrevoker' command handler. */          return ctx->pass;
556  static const char *      }
557  cmd_addrev_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,      if( step == 7 && !strcmp ( key, "keyedit.prompt" ) ) {
558                      const char * key, int * r_step)          *r_step = step = 0;
559  {          ctx->reset ();
560      int step = *r_step;          return "save";
561        }
562      if (step == 0 && !strcmp (key, "keyedit.prompt")) {      return NULL;
563          *r_step = step = 1;  }
564          return "addrevoker";  
565      }  
566      if (step == 1 && !strcmp (key, "keyedit.add_revoker")) {  /* 'addrevoker' command handler. */
567          *r_step = step = 2;  static const char *
568          /* XXX: handle already-signed. */  cmd_addrev_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,
569          return ctx->name;                      const char *key, int *r_step)
570      }  {
571      if (step == 2 && !strcmp (key, "keyedit.add_revoker.okay")) {      int step = *r_step;
572          *r_step = step = 3;  
573          return "Y";      /* If the isuser already signed the key, send an empty
574      }             string and jump to quit. */
575      if (step == 3 && !strcmp (key, "passphrase.enter")) {      if (ctx->getResult () & EDITKEY_ERR_ALREADY_SIGNED
576          *r_step = step = 4;          && *r_step != -1 && *r_step != 4) {
577          return ctx->pass;          *r_step = step = -1;
578      }          return "";
579      if (step == 4 && !strcmp (key, "keyedit.prompt")) {      }
580          *r_step = step = 0;      if (*r_step == -1) {
581          ctx->reset ();          *r_step = step = 4;
582          return "save";          return ""; /* empty value to abort. */
583      }      }
584        if (step == 0 && !strcmp (key, "keyedit.prompt")) {
585      return NULL;          *r_step = step = 1;
586  }          return "addrevoker";
587        }
588        if (step == 1 && !strcmp (key, "keyedit.add_revoker")) {
589  /* 'addphoto' command handler. */          *r_step = step = 2;
590  static const char*          return ctx->name;
591  cmd_addphoto_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)      }
592  {      if (step == 2 && !strcmp (key, "keyedit.add_revoker.okay")) {
593      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {          *r_step = step = 3;
594          ctx->cmd_sent = 1;          return "Y";
595          return "addphoto";      }
596      }      if (step == 3 && !strcmp (key, "passphrase.enter")) {
597      if (!strcmp (key, "photoid.jpeg.add"))          *r_step = step = 4;
598          return ctx->url;          return ctx->pass;
599      if (!strcmp (key, "photoid.jpeg.size"))      }
600          return "Y";      if (step == 4 && !strcmp (key, "keyedit.prompt")) {
601      if (!strcmp (key, "passphrase.enter"))          *r_step = step = 0;
602          return ctx->pass;          ctx->reset ();
603      if (!strcmp (key, "keyedit.prompt")) {                return "save";
604          ctx->reset ();      }
605          return "save";  
606      }      return NULL;
607      return NULL;  }
608  }  
609    
610  /* 'enable' and 'disable' command handler. */  /* 'addphoto' command handler. */
611  static const char *  static const char*
612  cmd_enable_disable_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,  cmd_addphoto_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)
613                              const char * key, int mode)  {
614  {      if (!ctx->cmd_sent && !strcmp (key, "keyedit.prompt")) {
615      if (!strcmp (key, "keyedit.prompt") && !ctx->cmd_sent) {          ctx->cmd_sent = 1;
616          ctx->cmd_sent = 1;          return "addphoto";
617          if (mode)      }
618              return "disable";      if (!strcmp (key, "photoid.jpeg.add"))
619          return "enable";          return ctx->url;
620      }      if (!strcmp (key, "photoid.jpeg.size"))
621      if (!strcmp (key, "keyedit.prompt")) {          return "Y";
622          ctx->reset ();      if (!strcmp (key, "passphrase.enter"))
623          return "save";          return ctx->pass;
624      }      if (!strcmp (key, "keyedit.prompt")) {      
625      return NULL;          ctx->reset ();
626  }          return "save";
627        }
628        return NULL;
629  /* edit key dispatch handler. */  }
630  static gpgme_error_t                      
631  editkey_command_handler (void *opaque, gpgme_status_code_t code,  
632                           const char *key, int fd)  /* 'clean' command handler. */
633  {  static const char*
634      static int step = 0;  cmd_clean_handler (GpgKeyEdit *ctx, gpgme_status_code_t code, const char *key)
635      const char *out = NULL;  {
636      GpgKeyEdit *ke = (GpgKeyEdit *)opaque;      if (!strcmp (key, "keyedit.prompt") && !ctx->cmd_sent) {
637      HANDLE hd = (HANDLE)fd;          ctx->cmd_sent = 1;
638      DWORD n;          return "clean";
639            }
640      if (!ke)      if (!strcmp (key, "keyedit.prompt")) {
641          return gpg_error (GPG_ERR_INV_ARG);          ctx->reset ();
642            return "save";
643      /*log_debug ("key=%s code=%d\r\n", key, code);*/      }
644      switch (code) {      return NULL;
645      case GPGME_STATUS_ALREADY_SIGNED:  }
646          ke->setResult (GPG_EDITRES_ALREADY_SIGNED);  
647          break;  
648      case GPGME_STATUS_BAD_PASSPHRASE:  /* 'enable' and 'disable' command handler. */
649          ke->setResult (GPG_EDITRES_BAD_PASSPHRASE);  static const char *
650          break;  cmd_enable_disable_handler (GpgKeyEdit *ctx, gpgme_status_code_t code,
651      }                              const char * key, int mode)
652    {
653      if (ke->getResult () & GPG_EDITRES_BAD_PASSPHRASE) {      if (!strcmp (key, "keyedit.prompt") && !ctx->cmd_sent) {
654          /* If the entered passphrase is bad, we supply empty          ctx->cmd_sent = 1;
655             passphrase to abort and send 'quit' as soon as possible. */          if (mode)
656          if (!strcmp (key, "passphrase.enter"))              return "disable";
657              WriteFile (hd, "\n", 1, &n, NULL);          return "enable";
658          if (!strcmp (key, "keyedit.prompt"))      }
659              WriteFile (hd, "quit\n", 5, &n, NULL);      if (!strcmp (key, "keyedit.prompt")) {
660      }          ctx->reset ();
661                return "save";
662      switch (ke->getType ()) {      }
663      case GPG_EDITKEY_LSIGN:      return NULL;
664      case GPG_EDITKEY_SIGN:  }
665      case GPG_EDITKEY_NRSIGN:  
666      case GPG_EDITKEY_TSIGN:  
667      case GPG_EDITKEY_NRLSIGN:  /* edit key dispatch handler. */
668          out = cmd_sign_handler (ke, code, key);  static gpgme_error_t                    
669          break;  editkey_command_handler (void *opaque, gpgme_status_code_t code,
670                                     const char *key, int fd)
671      case GPG_EDITKEY_TRUST:  {
672          out =  cmd_trust_handler (ke, code, key);      static int step = 0; /* XXX use ke->cnt */
673          break;      const char *out = NULL;
674                GpgKeyEdit *ke = (GpgKeyEdit *)opaque;
675      case GPG_EDITKEY_ADDUID:      HANDLE hd = (HANDLE)fd;
676          out =  cmd_adduid_handler (ke, code, key);      DWORD n;
677          break;      
678                if (!ke)
679      case GPG_EDITKEY_DELUID:          return gpg_error (GPG_ERR_INV_ARG);
680          out =  cmd_deluid_handler (ke, code, key, &step);  
681          break;      /*log_debug ("key=%s code=%d\r\n", key, code);*/
682                switch (code) {
683      case GPG_EDITKEY_DELSIG:      case GPGME_STATUS_ALREADY_SIGNED:
684          out =  cmd_delsig_handler (ke, code, key, &step);          ke->setResult (EDITKEY_ERR_ALREADY_SIGNED);
685          break;          break;
686    
687      case GPG_EDITKEY_DELKEY:      case GPGME_STATUS_BAD_PASSPHRASE:
688          out =  cmd_delkey_handler(ke, code, key, &step );          ke->setResult (EDITKEY_ERR_BAD_PASSPHRASE);
689          break;          break;
690            
691      case GPG_EDITKEY_ADDKEY:      default:
692          out =  cmd_addkey_handler (ke, code, key);          break;
693          break;      }
694            
695      case GPG_EDITKEY_PASSWD:      if (ke->getResult () & EDITKEY_ERR_BAD_PASSPHRASE) {
696          out =  cmd_passwd_handler (ke, code, key);          /* If the entered passphrase is bad, we supply empty
697          break;             passphrase to abort and send 'quit' as soon as possible. */
698                    if (!strcmp (key, "passphrase.enter"))
699      case GPG_EDITKEY_PRIMARY:              WriteFile (hd, "\n", 1, &n, NULL);
700          out =  cmd_primary_handler (ke, code, key, &step);          if (!strcmp (key, "keyedit.prompt"))
701          break;              WriteFile (hd, "quit\n", 5, &n, NULL);
702                    ke->reset ();
703      case GPG_EDITKEY_EXPIRE:          step = 0;
704          out =  cmd_expire_handler (ke, code, key, &step);          return 0;
705          break;      }
706        
707      case GPG_EDITKEY_REVSIG:      switch (ke->getType ()) {
708          out =  cmd_revsig_handler (ke, code, key, &step);      case GPG_EDITKEY_LSIGN:
709          break;      case GPG_EDITKEY_SIGN:
710        case GPG_EDITKEY_NRSIGN:
711      case GPG_EDITKEY_REVKEY:      case GPG_EDITKEY_TSIGN:
712          out =  cmd_revkey_handler (ke, code, key, &step);      case GPG_EDITKEY_NRLSIGN:
713          break;          out = cmd_sign_handler (ke, code, key);
714                        break;
715      case GPG_EDITKEY_REVUID:          
716          out = cmd_revuid_handler (ke, code, key, &step);      case GPG_EDITKEY_TRUST:
717          break;          out =  cmd_trust_handler (ke, code, key);
718            break;
719      case GPG_EDITKEY_ADDREV:          
720          out =  cmd_addrev_handler (ke, code, key, &step);      case GPG_EDITKEY_ADDUID:
721          break;          out =  cmd_adduid_handler (ke, code, key);
722            break;
723      case GPG_EDITKEY_ADDPHOTO:          
724          out =  cmd_addphoto_handler (ke, code, key);      case GPG_EDITKEY_DELUID:
725          break;          out =  cmd_deluid_handler (ke, code, key, &step);
726            break;
727      case GPG_EDITKEY_ENABLE:          
728      case GPG_EDITKEY_DISABLE:      case GPG_EDITKEY_DELSIG:
729          out = cmd_enable_disable_handler (ke, code, key,          out =  cmd_delsig_handler (ke, code, key, &step);
730                                            ke->getType () == GPG_EDITKEY_DISABLE? 1: 0);          break;
731          break;  
732        case GPG_EDITKEY_DELKEY:
733      case GPG_EDITKEY_SETPREF:          out =  cmd_delkey_handler(ke, code, key, &step );
734          out =  cmd_setpref_handler (ke, code, key);          break;
735          break;          
736        case GPG_EDITKEY_ADDKEY:
737      case GPG_EDITKEY_KEYSERV:          out =  cmd_addkey_handler (ke, code, key);
738          out =  cmd_keyserv_handler (ke, code, key);          break;
739          break;          
740      }      case GPG_EDITKEY_PASSWD:
741            out =  cmd_passwd_handler (ke, code, key);
742      if (out != NULL) {          break;
743          /* XXX: check return codes. */          
744          WriteFile (hd, out, strlen (out), &n, NULL);      case GPG_EDITKEY_PRIMARY:
745          WriteFile (hd, "\n", 1, &n, NULL);          out =  cmd_primary_handler (ke, code, key, &step);
746      }          break;
747      return 0;          
748  }      case GPG_EDITKEY_EXPIRE:
749            out =  cmd_expire_handler (ke, code, key, &step);
750            break;
751  /* Check if a GPG status code occured which marks the  
752     current operation as failed.      case GPG_EDITKEY_REVSIG:
753     Return value: gpg error constant. */          out =  cmd_revsig_handler (ke, code, key, &step);
754  static gpgme_error_t          break;
755  map_result (GpgKeyEdit *ke)  
756  {      case GPG_EDITKEY_REVKEY:
757      if (!ke->getResult ())          out =  cmd_revkey_handler (ke, code, key, &step);
758          return gpg_error (GPG_ERR_NO_ERROR);          break;
759      if (ke->getResult () & GPG_EDITRES_BAD_PASSPHRASE)              
760          return gpg_error (GPG_ERR_BAD_PASSPHRASE);      case GPG_EDITKEY_REVUID:
761      return 0;          out = cmd_revuid_handler (ke, code, key, &step);
762  }          break;
763    
764        case GPG_EDITKEY_ADDREV:
765  /* Wrapper around the gpgme edit interface.          out =  cmd_addrev_handler (ke, code, key, &step);
766     @ctx context to use.          break;
767     @key key on which the operation should be performed.  
768     @ek  key edit context.      case GPG_EDITKEY_ADDPHOTO:
769     Return value: 0 on success. */          out =  cmd_addphoto_handler (ke, code, key);
770  gpgme_error_t          break;
771  gpg_editkey (gpgme_ctx_t ctx, gpgme_key_t key, GpgKeyEdit *ek)  
772  {      case GPG_EDITKEY_CLEAN:
773      gpgme_error_t err;          out = cmd_clean_handler (ke, code, key);
774      gpgme_data_t out;          break;
775      
776      err = gpgme_data_new (&out);      case GPG_EDITKEY_ENABLE:
777      if (err)      case GPG_EDITKEY_DISABLE:
778          return err;          out = cmd_enable_disable_handler (ke, code, key,
779      err = gpgme_op_edit (ctx, key, editkey_command_handler, ek, out);                                            ke->getType () == GPG_EDITKEY_DISABLE? 1: 0);
780      if (!err)          break;
781          err = map_result (ek);  
782        case GPG_EDITKEY_SETPREF:
783      gpgme_data_release (out);          out =  cmd_setpref_handler (ke, code, key);
784      return err;          break;
785  }  
786        case GPG_EDITKEY_KEYSERV:
787            out =  cmd_keyserv_handler (ke, code, key);
788            break;
789        }
790    
791        if (out != NULL) {
792            /* XXX: check return codes. */
793            WriteFile (hd, out, strlen (out), &n, NULL);
794            WriteFile (hd, "\n", 1, &n, NULL);
795        }
796        return 0;
797    }
798    
799    
800    /* Check if a GPG status code occured which marks the
801       current operation as failed.
802       Return value: gpg error constant. */
803    static gpgme_error_t
804    map_result (GpgKeyEdit *ke)
805    {
806        /* XXX Sometimes ALREADY_SIGNED indicates an failure. */
807        if (!ke->getResult ())
808            return gpg_error (GPG_ERR_NO_ERROR);
809        if (ke->getResult () & EDITKEY_ERR_BAD_PASSPHRASE)
810            return gpg_error (GPG_ERR_BAD_PASSPHRASE);
811        return 0;
812    }
813    
814    
815    /* Wrapper around the gpgme edit interface.
816       @ctx context to use.
817       @key key on which the operation should be performed.
818       @ek  key edit context.
819       Return value: 0 on success. */
820    gpgme_error_t
821    gpg_editkey (gpgme_ctx_t ctx, gpgme_key_t key, GpgKeyEdit *ek)
822    {
823        gpgme_error_t err;
824        gpgme_data_t out;
825      
826        err = gpgme_data_new (&out);
827        if (err)
828            return err;
829        err = gpgme_op_edit (ctx, key, editkey_command_handler, ek, out);
830        if (!err)
831            err = map_result (ek);
832    
833        gpgme_data_release (out);
834        return err;
835    }

Legend:
Removed from v.28  
changed lines
  Added in v.160

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26