/[rdesktop]/sourceforge.net/trunk/seamlessrdp/ServerExe/HookDll/hookdll.cpp
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.cpp

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1009 - (show annotations)
Wed Aug 31 07:20:19 2005 UTC (18 years, 8 months ago) by astrand
File size: 11464 byte(s)
POSITION1 should be terminated by newline.

1 //
2 // Copyright (C) 2004-2005 Martin Wickett
3 //
4
5 #include "hookdll.h"
6 #include <windows.h>
7 #include <winuser.h>
8 #include <stdio.h>
9 #include <stdarg.h>
10
11 #include "wtsapi32.h"
12 #include "Cchannel.h"
13
14 #define DLL_EXPORT extern "C" __declspec(dllexport)
15
16 // Shared DATA
17 #pragma data_seg ( "SHAREDDATA" )
18
19 // this is the total number of processes this dll is currently attached to
20 int iInstanceCount = 0;
21 HWND hWnd = 0;
22
23 #pragma data_seg ()
24
25 #pragma comment(linker, "/section:SHAREDDATA,rws")
26
27 #define snprintf _snprintf
28
29 HHOOK hCbtProc = 0;
30 HHOOK hShellProc = 0;
31 HHOOK hWndProc = 0;
32 HINSTANCE hInst = 0;
33 HANDLE m_vcHandle = 0;
34
35
36 void SendDebug( char *format, ... )
37 {
38 va_list argp;
39 char buf [ 256 ];
40
41 va_start( argp, format );
42 vsprintf( buf, format, argp );
43 va_end( argp );
44
45 WriteToChannel( "DEBUG1," );
46 WriteToChannel( buf );
47 WriteToChannel( "\n" );
48 }
49
50
51
52 BOOL APIENTRY DllMain( HINSTANCE hinstDLL, DWORD ul_reason_for_call, LPVOID lpReserved )
53 {
54 switch ( ul_reason_for_call ) {
55 case DLL_PROCESS_ATTACH: {
56 // remember our instance handle
57 hInst = hinstDLL;
58 ++iInstanceCount;
59 OpenVirtualChannel();
60 break;
61 }
62
63 case DLL_THREAD_ATTACH:
64 break;
65 case DLL_THREAD_DETACH:
66 break;
67 case DLL_PROCESS_DETACH: {
68 --iInstanceCount;
69 CloseVirtualChannel();
70 }
71 break;
72 }
73
74 return TRUE;
75 }
76
77 LRESULT CALLBACK CallWndProc( int nCode, WPARAM wParam, LPARAM lParam )
78 {
79 if ( nCode < 0 ) {
80 return CallNextHookEx( hWndProc, nCode, wParam, lParam );
81 }
82
83 char windowTitle[ 150 ] = { ""
84 };
85 HWND windowHandle = NULL;
86 HWND windowHandle2 = NULL;
87 char result[ 255 ] = { ""
88 };
89 CWPSTRUCT *details = ( CWPSTRUCT * ) lParam;
90 CREATESTRUCT *cs = ( CREATESTRUCT * ) details->lParam;
91 LONG dwStyle = GetWindowLong( details->hwnd, GWL_STYLE );
92 WINDOWPOS *wp = ( WINDOWPOS * ) details->lParam;
93 RECT *rect = ( RECT * ) details->lParam;
94
95 switch ( details->message ) {
96
97 case WM_SIZING:
98 case WM_MOVING:
99 if ( !( dwStyle & WS_VISIBLE ) )
100 break;
101
102 if ( !( dwStyle & WS_DLGFRAME ) )
103 break;
104
105 snprintf( result, sizeof( result ),
106 "POSITION1,0x%p,%d,%d,%d,%d,0x%x\n",
107 details->hwnd,
108 rect->left, rect->top,
109 rect->right - rect->left,
110 rect->bottom - rect->top,
111 0 );
112 result[ sizeof( result ) - 1 ] = '\0';
113 WriteToChannel( result );
114 break;
115
116
117 /* Note: WM_WINDOWPOSCHANGING/WM_WINDOWPOSCHANGED are
118 strange. Sometimes, for example when bringing up the
119 Notepad About dialog, only an WM_WINDOWPOSCHANGING is
120 sent. In some other cases, for exmaple when opening
121 Format->Text in Notepad, both events are sent. Also, for
122 some reason, when closing the Notepad About dialog, an
123 WM_WINDOWPOSCHANGING event is sent which looks just like
124 the event that was sent when the About dialog was opened... */
125 case WM_WINDOWPOSCHANGING:
126
127 if ( !( dwStyle & WS_VISIBLE ) )
128 break;
129
130 if ( !( dwStyle & WS_DLGFRAME ) )
131 break;
132
133 if ( !( wp->flags & SWP_NOZORDER ) ) {
134 snprintf( result, sizeof( result ),
135 "ZCHANGE1,0x%p,0x%p,0x%x\n",
136 details->hwnd,
137 wp->flags & SWP_NOACTIVATE ? wp->hwndInsertAfter : 0,
138 0 );
139 result[ sizeof( result ) - 1 ] = '\0';
140 WriteToChannel( result );
141 }
142 break;
143
144
145 case WM_CREATE:
146 if ( cs->style & WS_DLGFRAME ) {
147
148 snprintf( result, sizeof( result ),
149 "CREATE1,0x%p,0x%x\n",
150 details->hwnd, 0 );
151 result[ sizeof( result ) - 1 ] = '\0';
152 WriteToChannel( result );
153
154 snprintf( result, sizeof( result ),
155 "SETSTATE1,0x%p,%s,0x%x,0x%x\n",
156 details->hwnd,
157 cs->lpszName,
158 1, // FIXME: Check for WS_MAXIMIZE/WS_MINIMIZE
159 0 );
160 result[ sizeof( result ) - 1 ] = '\0';
161 WriteToChannel( result );
162
163 snprintf( result, sizeof( result ),
164 "POSITION1,0x%p,%d,%d,%d,%d,0x%x\n",
165 details->hwnd,
166 cs->x,
167 cs->y,
168 cs->cx,
169 cs->cy,
170 0 );
171 result[ sizeof( result ) - 1 ] = '\0';
172 WriteToChannel( result );
173
174 }
175 break;
176
177
178 case WM_DESTROY:
179 if ( dwStyle & WS_DLGFRAME ) {
180 snprintf( result, sizeof( result ),
181 "DESTROY1,0x%p,0x%x\n",
182 details->hwnd, 0 );
183 result[ sizeof( result ) - 1 ] = '\0';
184 WriteToChannel( result );
185 }
186
187 break;
188
189
190 default:
191 break;
192 }
193
194 return CallNextHookEx( hWndProc, nCode, wParam, lParam );
195 }
196
197 LRESULT CALLBACK CbtProc( int nCode, WPARAM wParam, LPARAM lParam )
198 {
199 if ( nCode < 0 ) {
200 return CallNextHookEx( hCbtProc, nCode, wParam, lParam );
201 }
202
203 char windowTitle[ 150 ] = { ""
204 };
205 HWND windowHandle = NULL;
206 char result[ 255 ] = { ""
207 };
208 switch ( nCode ) {
209 case HCBT_MINMAX:
210
211 if ( ( LOWORD( lParam ) == SW_SHOWMINIMIZED )
212 || ( LOWORD( lParam ) == SW_MINIMIZE ) ) {
213 MessageBox( 0, "Minimizing windows is not allowed in this version. Sorry!", "SeamlessRDP", MB_OK );
214 return 1;
215 }
216
217 GetWindowText( ( HWND ) wParam, windowTitle, 150 );
218
219 snprintf( result, sizeof( result ),
220 "SETSTATE1,0x%p,%s,0x%x,0x%x\n",
221 ( HWND ) wParam,
222 windowTitle,
223 LOWORD( lParam ),
224 0 );
225 result[ sizeof( result ) - 1 ] = '\0';
226 WriteToChannel( result );
227 break;
228
229
230 default:
231 break;
232 }
233
234
235
236 return CallNextHookEx( hCbtProc, nCode, wParam, lParam );
237 }
238
239
240 LRESULT CALLBACK ShellProc( int nCode, WPARAM wParam, LPARAM lParam )
241 {
242 if ( nCode < 0 ) {
243 return CallNextHookEx( hShellProc, nCode, wParam, lParam );
244 }
245
246 char windowTitle[ 150 ] = { ""
247 };
248 HWND windowHandle = NULL;
249 char result[ 255 ] = { ""
250 };
251 char strWindowId[ 25 ];
252 LONG b, t, l, r;
253 char strW[ 5 ];
254 char strY[ 5 ];
255 char strX[ 5 ];
256 char strH[ 5 ];
257 RECT rect;
258
259 switch ( nCode ) {
260 case HSHELL_WINDOWCREATED:
261
262 //get window id
263 windowHandle = ( HWND ) wParam;
264 itoa( ( int ) windowHandle, strWindowId, 10 );
265
266 //get coords
267 GetWindowRect( windowHandle, &rect );
268 b = rect.bottom;
269 t = rect.top;
270 l = rect.left;
271 r = rect.right;
272 ltoa( b - t, strH, 10 );
273 ltoa( t, strY, 10 );
274 ltoa( r - l, strW, 10 );
275 ltoa( l, strX, 10 );
276
277 //get name
278 GetWindowText( windowHandle, windowTitle, 150 );
279
280 ////setup return string
281 strcat( result, "MSG=HSHELL_WINDOWCREATED;OP=0;" );
282 strcat( result, "ID=" );
283 strcat( result, strWindowId );
284 strcat( result, ";" );
285 strcat( result, "TITLE=" );
286 strcat( result, windowTitle );
287 strcat( result, ";" );
288 strcat( result, "X=" );
289 strcat( result, strX );
290 strcat( result, ";" );
291 strcat( result, "Y=" );
292 strcat( result, strY );
293 strcat( result, ";" );
294 strcat( result, "H=" );
295 strcat( result, strH );
296 strcat( result, ";" );
297 strcat( result, "W=" );
298 strcat( result, strW );
299 strcat( result, "." );
300 WriteToChannel( result );
301 break;
302
303 case HSHELL_WINDOWDESTROYED:
304
305 //get window id
306 windowHandle = ( HWND ) wParam;
307 itoa( ( int ) windowHandle, strWindowId, 10 );
308
309 //get coords
310 GetWindowRect( windowHandle, &rect );
311 b = rect.bottom;
312 t = rect.top;
313 l = rect.left;
314 r = rect.right;
315 ltoa( b - t, strH, 10 );
316 ltoa( t, strY, 10 );
317 ltoa( r - l, strW, 10 );
318 ltoa( l, strX, 10 );
319
320 //get name
321 GetWindowText( windowHandle, windowTitle, 150 );
322
323 ////setup return string
324 strcat( result, "MSG=HSHELL_WINDOWDESTROYED;OP=1;" );
325 strcat( result, "ID=" );
326 strcat( result, strWindowId );
327 strcat( result, ";" );
328 strcat( result, "TITLE=" );
329 strcat( result, windowTitle );
330 strcat( result, ";" );
331 strcat( result, "X=" );
332 strcat( result, strX );
333 strcat( result, ";" );
334 strcat( result, "Y=" );
335 strcat( result, strY );
336 strcat( result, ";" );
337 strcat( result, "H=" );
338 strcat( result, strH );
339 strcat( result, ";" );
340 strcat( result, "W=" );
341 strcat( result, strW );
342 strcat( result, "." );
343 WriteToChannel( result );
344 break;
345
346
347 default:
348 break;
349 }
350
351
352 return CallNextHookEx( hShellProc, nCode, wParam, lParam );
353 }
354
355 DLL_EXPORT void SetHooks( void )
356 {
357 if ( !hCbtProc ) {
358 hCbtProc = SetWindowsHookEx( WH_CBT, ( HOOKPROC ) CbtProc, hInst, ( DWORD ) NULL );
359 }
360
361 #if 0
362 if ( !hShellProc ) {
363 hShellProc = SetWindowsHookEx( WH_SHELL, ( HOOKPROC ) ShellProc, hInst, ( DWORD ) NULL );
364 }
365 #endif
366
367 if ( !hWndProc ) {
368 hWndProc = SetWindowsHookEx( WH_CALLWNDPROC, ( HOOKPROC ) CallWndProc, hInst, ( DWORD ) NULL );
369 }
370 }
371
372 DLL_EXPORT void RemoveHooks( void )
373 {
374 if ( hCbtProc ) {
375 UnhookWindowsHookEx( hCbtProc );
376 }
377
378 if ( hShellProc ) {
379 UnhookWindowsHookEx( hShellProc );
380 }
381
382 if ( hWndProc ) {
383 UnhookWindowsHookEx( hWndProc );
384 }
385 }
386
387 DLL_EXPORT int GetInstanceCount()
388 {
389 return iInstanceCount;
390 }
391
392 int OpenVirtualChannel()
393 {
394 m_vcHandle = WTSVirtualChannelOpen( WTS_CURRENT_SERVER_HANDLE, WTS_CURRENT_SESSION, CHANNELNAME );
395
396 if ( m_vcHandle == NULL ) {
397 return 0;
398 } else {
399 return 1;
400 }
401 }
402
403 int CloseVirtualChannel()
404 {
405 BOOL result = WTSVirtualChannelClose( m_vcHandle );
406
407 m_vcHandle = NULL;
408
409 if ( result ) {
410 return 1;
411 } else {
412 return 0;
413 }
414 }
415
416 int ChannelIsOpen()
417 {
418 if ( m_vcHandle == NULL ) {
419 return 0;
420 } else {
421 return 1;
422 }
423 }
424
425 int WriteToChannel( PCHAR buffer )
426 {
427 PULONG bytesRead = 0;
428 PULONG pBytesWritten = 0;
429
430 if ( !ChannelIsOpen() )
431 return 1;
432
433 BOOL result = WTSVirtualChannelWrite( m_vcHandle, buffer, ( ULONG ) strlen( buffer ), pBytesWritten );
434
435 if ( result ) {
436 return 1;
437 } else {
438 return 0;
439 }
440 }

  ViewVC Help
Powered by ViewVC 1.1.26