/[rdesktop]/sourceforge.net/trunk/seamlessrdp/ServerExe/HookDll/hookdll.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Contents of /sourceforge.net/trunk/seamlessrdp/ServerExe/HookDll/hookdll.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1081 - (show annotations)
Thu Mar 9 16:13:26 2006 UTC (18 years, 3 months ago) by ossman_
File MIME type: text/plain
File size: 5357 byte(s)
Catch WM_MOVE and WM_SIZE.

1 /* -*- c-basic-offset: 8 -*-
2 rdesktop: A Remote Desktop Protocol client.
3 Seamless windows - Remote server hook DLL
4
5 Based on code copyright (C) 2004-2005 Martin Wickett
6
7 Copyright (C) Peter Åstrand <astrand@cendio.se> 2005-2006
8 Copyright (C) Pierre Ossman <ossman@cendio.se> 2006
9
10 This program is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 2 of the License, or
13 (at your option) any later version.
14
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License for more details.
19
20 You should have received a copy of the GNU General Public License
21 along with this program; if not, write to the Free Software
22 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 */
24
25 #include <stdio.h>
26 #include <stdarg.h>
27
28 #include <windows.h>
29 #include <winuser.h>
30
31 #include "../vchannel.h"
32
33 #define DLL_EXPORT __declspec(dllexport)
34
35 // Shared DATA
36 #pragma data_seg ( "SHAREDDATA" )
37
38 // this is the total number of processes this dll is currently attached to
39 int g_instance_count = 0;
40
41 #pragma data_seg ()
42
43 #pragma comment(linker, "/section:SHAREDDATA,rws")
44
45 static HHOOK g_cbt_hook = NULL;
46 static HHOOK g_wndproc_hook = NULL;
47
48 static HINSTANCE g_instance = NULL;
49
50 static HANDLE g_mutex = NULL;
51
52 static void
53 update_position(HWND hwnd)
54 {
55 RECT rect;
56
57 if (!GetWindowRect(hwnd, &rect))
58 {
59 debug("GetWindowRect failed!\n");
60 return;
61 }
62
63 vchannel_write("POSITION1,0x%p,%d,%d,%d,%d,0x%x",
64 hwnd,
65 rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top, 0);
66 }
67
68 static LRESULT CALLBACK
69 wndproc_hook_proc(int code, WPARAM cur_thread, LPARAM details)
70 {
71 HWND hwnd;
72 UINT msg;
73 WPARAM wparam;
74 LPARAM lparam;
75
76 LONG style;
77
78 if (code < 0)
79 goto end;
80
81 hwnd = ((CWPSTRUCT *) details)->hwnd;
82 msg = ((CWPSTRUCT *) details)->message;
83 wparam = ((CWPSTRUCT *) details)->wParam;
84 lparam = ((CWPSTRUCT *) details)->lParam;
85
86 style = GetWindowLong(hwnd, GWL_STYLE);
87
88 if (style & WS_CHILD)
89 goto end;
90
91 switch (msg)
92 {
93
94 case WM_WINDOWPOSCHANGED:
95 {
96 WINDOWPOS *wp = (WINDOWPOS *) lparam;
97
98 if (wp->flags & SWP_SHOWWINDOW)
99 {
100 // FIXME: Now, just like create!
101 debug("SWP_SHOWWINDOW for %p!", hwnd);
102 vchannel_write("CREATE1,0x%p,0x%x", hwnd, 0);
103
104 // FIXME: SETSTATE
105
106 update_position(hwnd);
107 }
108
109 if (wp->flags & SWP_HIDEWINDOW)
110 vchannel_write("DESTROY1,0x%p,0x%x", hwnd, 0);
111
112 if (!(style & WS_VISIBLE))
113 break;
114
115 if (!(wp->flags & SWP_NOMOVE && wp->flags & SWP_NOSIZE))
116 update_position(hwnd);
117
118 if (!(wp->flags & SWP_NOZORDER))
119 {
120 vchannel_write("ZCHANGE1,0x%p,0x%p,0x%x",
121 hwnd,
122 wp->flags & SWP_NOACTIVATE ? wp->
123 hwndInsertAfter : 0, 0);
124 }
125
126 break;
127 }
128
129 case WM_SIZE:
130 update_position(hwnd);
131 break;
132
133 case WM_MOVE:
134 update_position(hwnd);
135 break;
136
137 case WM_DESTROY:
138 vchannel_write("DESTROY1,0x%p,0x%x", hwnd, 0);
139 break;
140
141 default:
142 break;
143 }
144
145 end:
146 return CallNextHookEx(g_wndproc_hook, code, cur_thread, details);
147 }
148
149 static LRESULT CALLBACK
150 cbt_hook_proc(int code, WPARAM wparam, LPARAM lparam)
151 {
152 char title[150];
153
154 if (code < 0)
155 goto end;
156
157 switch (code)
158 {
159 case HCBT_MINMAX:
160 {
161 int show, state;
162
163 show = LOWORD(lparam);
164
165 if ((show == SW_SHOWMINIMIZED) || (show == SW_MINIMIZE))
166 {
167 MessageBox(0,
168 "Minimizing windows is not allowed in this version. Sorry!",
169 "SeamlessRDP", MB_OK);
170 return 1;
171 }
172
173 GetWindowText((HWND) wparam, title, sizeof(title));
174
175 /* FIXME: Strip title of dangerous characters */
176
177 if (show == SW_SHOWNORMAL)
178 state = 0;
179 else if (show == SW_SHOWMINIMIZED)
180 state = 1;
181 else if (show == SW_SHOWMAXIMIZED)
182 state = 2;
183 vchannel_write("SETSTATE1,0x%p,%s,0x%x,0x%x",
184 (HWND) wparam, title, state, 0);
185 break;
186 }
187
188 default:
189 break;
190 }
191
192 end:
193 return CallNextHookEx(g_cbt_hook, code, wparam, lparam);
194 }
195
196 DLL_EXPORT void
197 SetHooks(void)
198 {
199 if (!g_cbt_hook)
200 g_cbt_hook = SetWindowsHookEx(WH_CBT, cbt_hook_proc, g_instance, 0);
201
202 if (!g_wndproc_hook)
203 g_wndproc_hook = SetWindowsHookEx(WH_CALLWNDPROC, wndproc_hook_proc, g_instance, 0);
204 }
205
206 DLL_EXPORT void
207 RemoveHooks(void)
208 {
209 if (g_cbt_hook)
210 UnhookWindowsHookEx(g_cbt_hook);
211
212 if (g_wndproc_hook)
213 UnhookWindowsHookEx(g_wndproc_hook);
214 }
215
216 DLL_EXPORT int
217 GetInstanceCount()
218 {
219 return g_instance_count;
220 }
221
222 BOOL APIENTRY
223 DllMain(HINSTANCE hinstDLL, DWORD ul_reason_for_call, LPVOID lpReserved)
224 {
225 switch (ul_reason_for_call)
226 {
227 case DLL_PROCESS_ATTACH:
228 // remember our instance handle
229 g_instance = hinstDLL;
230
231 g_mutex = CreateMutex(NULL, FALSE, "Local\\SeamlessDLL");
232 if (!g_mutex)
233 return FALSE;
234
235 WaitForSingleObject(g_mutex, INFINITE);
236 ++g_instance_count;
237 ReleaseMutex(g_mutex);
238
239 vchannel_open();
240
241 break;
242
243 case DLL_THREAD_ATTACH:
244 break;
245
246 case DLL_THREAD_DETACH:
247 break;
248
249 case DLL_PROCESS_DETACH:
250 WaitForSingleObject(g_mutex, INFINITE);
251 --g_instance_count;
252 ReleaseMutex(g_mutex);
253
254 vchannel_close();
255
256 CloseHandle(g_mutex);
257
258 break;
259 }
260
261 return TRUE;
262 }

Properties

Name Value
svn:executable *

  ViewVC Help
Powered by ViewVC 1.1.26