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

Contents of /trunk/Src/wptSafeEditCtrl.cpp

Parent Directory Parent Directory | Revision Log Revision Log


Revision 181 - (show annotations)
Tue Mar 14 11:01:22 2006 UTC (18 years, 11 months ago) by twoaday
File size: 6282 byte(s)
2006-03-12  Timo Schulz  <ts@g10code.de>
 
        * wptGPG.cpp (gnupg_load_config): Search for 'ask-cert-expire'.
        * wptKeyPropsDlg.cpp (display_key_info): Automatically update
        sym algorithm preferences if needed.
        * wptKeysignDlg.cpp (date_is_today): New.
        (keysign_dlg_proc): Only allow to set cert expire date if
        the option was found.
        * wptGPGPrefsDlg.cpp (gpgprefs_dlg_proc): Allow to set
        'ask-cert-expire'.
         


1 /* wptSafeEditCtrl.cpp - Safe edit control for passwords
2 * Copyright (C) 2006 Timo Schulz, g10 Code GmbH
3 *
4 * This file is part of WinPT.
5 *
6 * WinPT 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 * WinPT 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 WinPT; if not, write to the Free Software Foundation,
18 * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
19 */
20
21 #include <windows.h>
22 #include <stdio.h>
23 #include <richedit.h>
24 #include "resource.h"
25
26 #include "wptTypes.h"
27 #include "wptW32API.h"
28
29 /* New message to retrieve text. */
30 #define WM_SAFE_GETTEXT (WM_USER+11)
31
32 /* Hook context. */
33 struct hook_ctx_s {
34 HHOOK keyb; /* handle for the keyboard. */
35 HHOOK cbt; /* handle for computer based training (CBT) */
36 };
37 typedef struct hook_ctx_s *hook_ctx_t;
38
39 /* Subclassing context. */
40 struct subclass_ctx_s {
41 WNDPROC new_wnd_fnc; /* old window procedure. */
42 WNDPROC old_wnd_fnc; /* new window procedure. */
43 HWND wnd; /* window handle that is subclassed. */
44 void *opaque;
45 };
46 typedef struct subclass_ctx_s *subclass_ctx_t;
47
48
49 /* Dummy hook procedure to avoid channing. */
50 static LRESULT CALLBACK
51 dummy_hook_proc (int code, WPARAM wparam, LPARAM lparam)
52 {
53 return FALSE;
54 }
55
56
57 /* Set dummy hooks to prevent that the control is monitored
58 by some external hook functions. */
59 static hook_ctx_t
60 install_dummy_hooks (void)
61 {
62 hook_ctx_t hc;
63
64 hc = (hook_ctx_t)calloc (1, sizeof *hc);
65 if (!hc)
66 return NULL;
67 hc->cbt = SetWindowsHookEx (WH_CBT, dummy_hook_proc,
68 GetModuleHandle (NULL), 0);
69 if (hc->cbt == NULL) {
70 free (hc);
71 return NULL;
72 }
73 hc->keyb = SetWindowsHookEx (WH_KEYBOARD, dummy_hook_proc,
74 GetModuleHandle (NULL), 0);
75 if (hc->keyb == NULL) {
76 free (hc);
77 return NULL;
78 }
79 return hc;
80 }
81
82
83 /* Remove dummy hooks and free memory. */
84 static void
85 deinstall_dummy_hooks (hook_ctx_t hc)
86 {
87 UnhookWindowsHookEx (hc->cbt);
88 UnhookWindowsHookEx (hc->keyb);
89 free (hc);
90 }
91
92
93 /* Filtered window procedure for the passphrase edit control. */
94 static LRESULT CALLBACK
95 safe_edit_dlg_proc (HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam)
96 {
97 static subclass_ctx_t ctx = NULL;
98
99 /* XXX: filter all messages which were not send from
100 the current process. */
101
102 if (ctx == NULL)
103 ctx = (subclass_ctx_t)GetWindowLong (hwnd, GWL_USERDATA);
104
105 switch (msg) {
106 case WM_CUT:
107 case WM_COPY:
108 case WM_PASTE:
109 /* do not allow to copy or paste the inserted text. */
110 return TRUE;
111
112 case WM_KEYUP:
113 case WM_KEYDOWN:
114 /* XXX: maybe in a future release, we might want to provide
115 our own buffer implementation. */
116
117 /* ignore 'end' and 'home' to make text selection more difficult. */
118 if ((int)wparam == VK_END || (int)wparam == VK_HOME)
119 return TRUE;
120 break;
121
122 case WM_GETTEXT:
123 /* disallow normal gettext message. */
124 return TRUE;
125
126 case WM_SAFE_GETTEXT:
127 { /* transform WM_GETTEXT request into EM_GETLINE request. */
128 char *buffer = (char*)wparam;
129 int n;
130 buffer[0] = (char)lparam;
131 n = SendMessage (hwnd, EM_GETLINE, 0, wparam);
132 buffer[n] = 0;
133 }
134 break;
135
136 case EM_GETLINE:
137 break;
138
139 case WM_LBUTTONDBLCLK:
140 case WM_RBUTTONUP:
141 case WM_RBUTTONDOWN:
142 /* prevent that the popup menu is displayed. */
143 return TRUE;
144
145 case EM_SETSEL:
146 case EM_SCROLLCARET:
147 case EM_FINDTEXT:
148 case EM_FINDTEXTEX:
149 case EM_GETSELTEXT:
150 case EM_PASTESPECIAL:
151 case EM_GETTEXTRANGE:
152 case EM_STREAMIN:
153 case EM_STREAMOUT:
154 /* disallow message which could be used to copy the text. */
155 return TRUE;
156 }
157
158 return CallWindowProc (ctx->old_wnd_fnc, hwnd, msg, wparam, lparam);
159 }
160
161
162 /* Sublclass the window in the dialog @dlg with the id @ctrlid.
163 @new_wnd_fnc is the new window procedure. */
164 static int
165 subclass_window (HWND dlg, int ctrlid, WNDPROC new_wnd_fnc,
166 subclass_ctx_t *r_ctx)
167 {
168 subclass_ctx_t ctx;
169
170 *r_ctx = NULL;
171 ctx = (subclass_ctx_t)calloc (1, sizeof *ctx);
172 if (!ctx)
173 return -1;
174 ctx->wnd = GetDlgItem (dlg, ctrlid);
175 ctx->new_wnd_fnc = new_wnd_fnc;
176 ctx->old_wnd_fnc = (WNDPROC)GetWindowLong (ctx->wnd, GWL_WNDPROC);
177 if (!ctx->old_wnd_fnc) {
178 free (ctx);
179 return -1;
180 }
181 SetLastError (0);
182 SetWindowLong (ctx->wnd, GWL_WNDPROC, (LONG)new_wnd_fnc);
183 if (GetLastError () != 0) {
184 free (ctx);
185 return -1;
186 }
187 SetLastError (0);
188 SetWindowLong (ctx->wnd, GWL_USERDATA, (LONG)ctx);
189 if (GetLastError () != 0) {
190 free (ctx);
191 return -1;
192 }
193 if (r_ctx)
194 *r_ctx = ctx;
195 return 0;
196 }
197
198
199 /* Restore the old window procedure for the subclassed control
200 and free the memory. */
201 static void
202 subclass_free_memory (HWND dlg, int ctrlid)
203 {
204 subclass_ctx_t ctx;
205 HWND wnd;
206
207 wnd = GetDlgItem (dlg, ctrlid);
208 ctx = (subclass_ctx_t)GetWindowLong (wnd, GWL_USERDATA);
209 SetWindowLong (ctx->wnd, GWL_WNDPROC, (LONG)ctx->old_wnd_fnc);
210 if (ctx != NULL)
211 free (ctx);
212 }
213
214
215 /* Init subclassing to provide a safer edit control
216 for the dialog @dlg control @ctlid. */
217 void
218 safe_edit_control_init (HWND dlg, int ctlid)
219 {
220 subclass_ctx_t ctx;
221
222 subclass_window (dlg, ctlid, safe_edit_dlg_proc, &ctx);
223 if (ctx != NULL)
224 ctx->opaque = install_dummy_hooks ();
225 }
226
227
228 /* Reset subclassing for the edit control @ctlid. */
229 void
230 safe_edit_control_free (HWND dlg, int ctlid)
231 {
232 subclass_ctx_t ctx;
233 HWND wnd;
234
235 wnd = GetDlgItem (dlg, ctlid);
236 ctx = (subclass_ctx_t)GetWindowLong (wnd, GWL_USERDATA);
237 if (ctx != NULL && ctx->opaque != NULL)
238 deinstall_dummy_hooks ((hook_ctx_t)ctx->opaque);
239 subclass_free_memory (dlg, ctlid);
240 }
241
242
243 UINT
244 SafeGetDlgItemText (HWND dlg, int id, char *buf, int buflen)
245 {
246 /* XXX: use memset (buf, 0, buflen)? */
247 SendDlgItemMessage (dlg, id, WM_SAFE_GETTEXT, (WPARAM)buf, (LPARAM)buflen);
248 return strlen (buf);
249 }

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26