/[gpgoe]/trunk/src/OEPassphraseCBDlg.c
ViewVC logotype

Annotation of /trunk/src/OEPassphraseCBDlg.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 16 - (hide annotations)
Tue Apr 11 06:56:23 2006 UTC (19 years ago) by twoaday
File MIME type: text/plain
File size: 6960 byte(s)


1 twoaday 1 /* OEPassphraseDLG.cpp - GPGME Passphrase Callback
2     * Copyright (C) 2001, 2002, 2006 Timo Schulz
3     *
4     * This file is part of GPGOE.
5     *
6     * GPGOE is free software; you can redistribute it and/or modify
7     * it under the terms of the GNU Lesser General Public License as published by
8     * the Free Software Foundation; either version 2.1 of the License, or
9     * (at your option) any later version.
10     *
11     * GPGOE 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 Lesser General Public License
17     * along with GPGOE; if not, write to the Free Software Foundation,
18     * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA7 USA
19     */
20    
21     #ifdef HAVE_CONFIG_H
22     #include <config.h>
23     #endif
24     #include <windows.h>
25     #include <assert.h>
26     #include "resource.h"
27     #include "gpgme.h"
28     #include "GPGOE.h"
29    
30 twoaday 11
31 twoaday 16 /* Structure for the passphrase cache. */
32     struct pass_cache_s {
33     struct pass_cache_s *next;
34     char *keyid;
35     char *pass;
36     };
37     typedef struct pass_cache_s *pass_cache_t;
38    
39 twoaday 1 /* Structure for the passphrase callback. */
40     struct pass_cb_s {
41     const char *uid_hint;
42     const char *passphrase_info;
43 twoaday 16 char keyid[8+2];
44 twoaday 1 char *pass;
45 twoaday 16 pass_cache_t cache;
46     HWND main_wnd;
47 twoaday 1 int cancel;
48     int prev_was_bad;
49     };
50    
51    
52 twoaday 16 /* Global passphrase cache. */
53     static pass_cache_t the_cache = NULL;
54    
55    
56     /* Release the passphrase cache @ctx and invalidate all passphrases. */
57     static void
58     invalidate_cache (pass_cache_t ctx)
59     {
60     pass_cache_t c;
61    
62     while (ctx) {
63     c = ctx->next;
64     free_if_alloc (ctx->keyid);
65     wipememory (ctx->pass, strlen (ctx->pass));
66     free_if_alloc (ctx->pass);
67     ctx = c;
68     }
69     }
70    
71     /* Put the passphrase @pass into the passphrase cache @ctx. */
72     static void
73     passphrase_put (pass_cache_t *ctx, const char *keyid, const char *pass)
74     {
75     pass_cache_t c, n;
76    
77     /* check if the item is already present. */
78     for (n = *ctx; n; n = n->next) {
79     if (!strcmp (n->keyid, keyid))
80     return;
81     }
82    
83     c = xcalloc (1, sizeof *c);
84     c->keyid = xstrdup (keyid);
85     c->pass = xstrdup (pass);
86    
87     if (!*ctx)
88     *ctx = c;
89     else {
90     for (n = *ctx; n->next; n = n->next)
91     ;
92     n->next = c;
93     }
94     }
95    
96    
97     /* Return the passphrase for the key with the keyid @keyid
98     or NULL if the passphrase was not cached for this key. */
99     static const char*
100     passphrase_get (pass_cache_t ctx, const char *keyid)
101     {
102     pass_cache_t c;
103    
104     for (c = ctx; c; c = c->next) {
105     if (!strcmp (c->keyid, keyid))
106     return c->pass;
107     }
108     return NULL;
109     }
110    
111    
112    
113    
114 twoaday 1 /* Extract public key algorithm from passwd info. */
115     const char*
116     get_pubkey_algo (const char *passphrase_info)
117     {
118     size_t pos = 16+1+16+1;
119    
120     /* AA6F7AB7DD3B4A21 E71D9BC8C93A8529 1 0 */
121     assert (strlen (passphrase_info) > pos);
122     switch (atol (passphrase_info+pos)) {
123 twoaday 16 case 1: return "RSA";
124 twoaday 1 case 17: return "DSA";
125     case 16: return "ELG";
126     }
127     return "???";
128     }
129    
130    
131     /* Passphrase callback dialog box procedure. */
132     BOOL CALLBACK
133     pass_cb_dlg_proc (HWND dlg, UINT msg, WPARAM wparam, LPARAM lparam)
134     {
135     static pass_cb_t ctx;
136 twoaday 16 char *info;
137 twoaday 1 int n;
138    
139     switch (msg) {
140     case WM_INITDIALOG:
141     ctx = (pass_cb_t)lparam;
142     assert (ctx);
143     if (ctx->uid_hint && ctx->passphrase_info) {
144     char *utf8_uid = utf8_to_native (ctx->uid_hint+17);
145 twoaday 16 info = xcalloc (1, strlen (utf8_uid) + strlen (ctx->keyid) + 32);
146 twoaday 1 sprintf (info, _("%s\n%s key, ID %s"), utf8_uid,
147 twoaday 16 get_pubkey_algo (ctx->passphrase_info), ctx->keyid);
148 twoaday 1 SetDlgItemText (dlg, IDC_DECRYPT_MSG, info);
149     free_if_alloc (utf8_uid);
150     free_if_alloc (info);
151     }
152 twoaday 12 SetDlgItemText (dlg, IDOK, _("&OK"));
153     SetDlgItemText (dlg, IDCANCEL, _("&Cancel"));
154     SetDlgItemText (dlg, IDC_DECRYPT_PWDINFO, _("Please enter your passphrase"));
155 twoaday 1 SendDlgItemMessage (dlg, IDC_DECRYPT_PWD, EM_SETPASSWORDCHAR,
156     (WPARAM)(UINT)'*', 0);
157 twoaday 16 CheckDlgButton (dlg, IDC_DECRYPT_HIDE, BST_CHECKED);
158 twoaday 12 SetWindowText (dlg, _("Decryption"));
159 twoaday 1 SetForegroundWindow (dlg);
160 twoaday 16 center_window (dlg, ctx->main_wnd);
161 twoaday 1 break;
162    
163     case WM_COMMAND:
164 twoaday 16 if (HIWORD (wparam) == BN_CLICKED &&
165     LOWORD (wparam) == IDC_DECRYPT_HIDE) {
166     HWND hwnd;
167     hwnd = GetDlgItem (dlg, IDC_DECRYPT_PWD);
168     SendMessage (hwnd, EM_SETPASSWORDCHAR,
169     IsDlgButtonChecked (dlg, IDC_DECRYPT_HIDE)? '*' : 0, 0);
170     SetFocus (hwnd);
171     break;
172     }
173    
174 twoaday 1 switch (LOWORD (wparam)) {
175     case IDCANCEL:
176     ctx->cancel = 1;
177     free_if_alloc (ctx->pass);
178     EndDialog (dlg, FALSE);
179     break;
180    
181     case IDOK:
182     if (ctx->prev_was_bad)
183     SetDlgItemText (dlg, IDC_DECRYPT_PWDINFO,
184     _("Invalid passphrase; please enter your passphrase again"));
185     else
186     SetDlgItemText (dlg, IDC_DECRYPT_PWDINFO,
187     _("Please enter your passphrase"));
188 twoaday 16 n = SendDlgItemMessage (dlg, IDC_DECRYPT_PWD,
189 twoaday 1 WM_GETTEXTLENGTH, 0, 0);
190     if (n < 1) {
191     MessageBox (dlg, _("Please enter your passphrase"),
192     _("GPG Plug-in Info"), MB_ICONINFORMATION|MB_OK);
193     return FALSE;
194     }
195     ctx->cancel = 0;
196     ctx->pass = xcalloc (1, n+2);
197     GetDlgItemText (dlg, IDC_DECRYPT_PWD, ctx->pass, n+1);
198 twoaday 16
199     /*passphrase_put (&the_cache, ctx->keyid, ctx->pass);*/
200 twoaday 1 EndDialog (dlg, TRUE);
201     break;
202     }
203     break;
204     }
205     return FALSE;
206     }
207    
208    
209     /* GPGME compatible passphrase callback. */
210     gpgme_error_t
211     passphrase_cb (void *hook,
212     const char *uid_hint,
213     const char *passphrase_info,
214     int prev_was_bad, int fd)
215     {
216     pass_cb_t cb = (pass_cb_t)hook;
217     HANDLE fp = (HANDLE)fd;
218 twoaday 16 const char *pass;
219 twoaday 1 DWORD nwritten = 0;
220    
221     cb->prev_was_bad = prev_was_bad;
222     if (prev_was_bad && !cb->cancel) {
223     wipememory (cb->pass, strlen (cb->pass));
224     free_if_alloc (cb->pass);
225     }
226     if (!cb->pass && !cb->cancel) {
227     cb->uid_hint = uid_hint;
228     cb->passphrase_info = passphrase_info;
229 twoaday 16 memset (cb->keyid, 0, sizeof (cb->keyid));
230     memcpy (cb->keyid, cb->passphrase_info+8, 8);
231    
232     if (the_cache && (pass=passphrase_get (the_cache, cb->keyid)))
233     cb->pass = xstrdup (pass);
234     else
235     DialogBoxParam (mod_hinst_dll, (LPCTSTR)IDD_DECRYPT,
236     cb->main_wnd, pass_cb_dlg_proc, (LPARAM)cb);
237 twoaday 1 }
238     if (cb->cancel)
239     WriteFile (fp, "\n", 1, &nwritten, NULL);
240     else if (cb->pass != NULL) {
241     WriteFile (fp, cb->pass, strlen (cb->pass), &nwritten, NULL);
242     WriteFile (fp, "\n", 1, &nwritten, NULL);
243     }
244     return 0;
245     }
246    
247    
248     /* Allocate new passphrase callback context. */
249     pass_cb_t
250     new_pass_cb (HWND main)
251     {
252     pass_cb_t cb_val;
253    
254     cb_val = xcalloc (1, sizeof *cb_val);
255 twoaday 16 cb_val->main_wnd = main;
256 twoaday 1 return cb_val;
257     }
258    
259    
260    
261     /* Free passphrase callback context. */
262     void
263     free_pass_cb (pass_cb_t cb)
264     {
265     if (!cb)
266     return;
267     if (cb->pass) {
268     wipememory (cb->pass, strlen (cb->pass));
269     free_if_alloc (cb->pass);
270     }
271     free_if_alloc (cb);
272     }
273 twoaday 16
274    
275     /* Release the passphrase cache. */
276     void
277     free_pass_cache (void)
278     {
279     invalidate_cache (the_cache);
280     the_cache = NULL;
281     }

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26