ReactOS 0.4.15-dev-7842-g558ab78
dde.c
Go to the documentation of this file.
1/*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS user32.dll
4 * PURPOSE: Dynamic Data Exchange
5 * FILE: win32ss/user/user32/misc/dde.c
6 * PROGRAMER:
7 */
8
9#include <user32.h>
10
12
13BOOL FASTCALL DdeAddPair(HGLOBAL ClientMem, HGLOBAL ServerMem);
15
16
17/* description of the data fields that need to be packed along with a sent message */
19{
20 //union packed_structs ps;
21 int count;
22 const void *data;
23 int size;
24};
25
26/* add a data field to a packed message */
27static inline void push_data( struct packed_message *data, const void *ptr, int size )
28{
29 data->data = ptr;
30 data->size = size;
31 data->count++;
32}
33
34/* pack a pointer into a 32/64 portable format */
35static inline ULONGLONG pack_ptr( const void *ptr )
36{
37 return (ULONG_PTR)ptr;
38}
39
40/* unpack a potentially 64-bit pointer, returning 0 when truncated */
41static inline void *unpack_ptr( ULONGLONG ptr64 )
42{
43 if ((ULONG_PTR)ptr64 != ptr64) return 0;
44 return (void *)(ULONG_PTR)ptr64;
45}
46
47
48/***********************************************************************
49 * post_dde_message
50 *
51 * Post a DDE message
52 */
54{
55 void* ptr = NULL;
56 int size = 0;
57 UINT_PTR uiLo, uiHi;
58 HGLOBAL hunlock = 0;
59 ULONGLONG hpack;
60
61 if (!UnpackDDElParam( message, lParam, &uiLo, &uiHi ))
62 {
63 ERR("Unpack failed %x\n",message);
64 return FALSE;
65 }
66
67 *lp = lParam;
68 switch (message)
69 {
70 /* DDE messages which don't require packing are:
71 * WM_DDE_INITIATE
72 * WM_DDE_TERMINATE
73 * WM_DDE_REQUEST
74 * WM_DDE_UNADVISE
75 */
76 case WM_DDE_ACK:
77 if (HIWORD(uiHi))
78 {
79 /* uiHi should contain a hMem from WM_DDE_EXECUTE */
80 HGLOBAL h = DdeGetPair( (HANDLE)uiHi );
81 if (h)
82 {
83 hpack = pack_ptr( h );
84 /* send back the value of h on the other side */
85 push_data( data, &hpack, sizeof(hpack) );
86 *lp = uiLo;
87 TRACE( "send dde-ack %lx %08lx => %p\n", uiLo, uiHi, h );
88 }
89 }
90 else
91 {
92 /* uiHi should contain either an atom or 0 */
93 TRACE( "send dde-ack %lx atom=%lx\n", uiLo, uiHi );
94 *lp = MAKELONG( uiLo, uiHi );
95 }
96 break;
97 case WM_DDE_ADVISE:
98 case WM_DDE_DATA:
99 case WM_DDE_POKE:
100 size = 0;
101 if (uiLo)
102 {
103 size = GlobalSize( (HGLOBAL)uiLo ) ;
104 TRACE("WM_DDE_A D P size %d\n",size);
105 if ( (message == WM_DDE_ADVISE && size < sizeof(DDEADVISE)) ||
108 return FALSE;
109 }
110 else if (message != WM_DDE_DATA)
111 {
112 TRACE("WM_DDE uiLo 0\n");
113 return FALSE;
114 }
115
116 *lp = uiHi;
117 if (uiLo)
118 {
119 if ((ptr = GlobalLock( (HGLOBAL)uiLo) ))
120 {
121 DDEDATA *dde_data = ptr;
122 TRACE("unused %d, fResponse %d, fRelease %d, fDeferUpd %d, fAckReq %d, cfFormat %d\n",
123 dde_data->unused, dde_data->fResponse, dde_data->fRelease,
124 dde_data->reserved, dde_data->fAckReq, dde_data->cfFormat);
125 push_data( data, ptr, size );
126 hunlock = (HGLOBAL)uiLo;
127 }
128 }
129 TRACE( "send ddepack %u %lx\n", size, uiHi );
130 break;
131 case WM_DDE_EXECUTE:
132 if (lParam)
133 {
134 if ((ptr = GlobalLock( (HGLOBAL)lParam) ))
135 {
138 /* so that the other side can send it back on ACK */
139 *lp = lParam;
140 hunlock = (HGLOBAL)lParam;
141 TRACE("WM_DDE_EXECUTE text size %d\n",GlobalSize( (HGLOBAL)lParam ));
142 }
143 }
144 break;
145 }
146
148
149 if (hunlock) GlobalUnlock(hunlock);
150
151 return TRUE;
152}
153
154/***********************************************************************
155 * unpack_dde_message
156 *
157 * Unpack a posted DDE message received from another process.
158 */
160{
161 UINT_PTR uiLo, uiHi;
162 HGLOBAL hMem = 0;
163 void* ptr;
164
165 TRACE("udm : Size %d\n",size);
166
167 switch (message)
168 {
169 case WM_DDE_ACK:
170 if (size)
171 {
172 ULONGLONG hpack;
173 /* hMem is being passed */
174 if (size != sizeof(hpack)) return FALSE;
175 if (!buffer) return FALSE;
176 uiLo = *lparam;
177 memcpy( &hpack, buffer, size );
178 hMem = unpack_ptr( hpack );
179 uiHi = (UINT_PTR)hMem;
180 TRACE("recv dde-ack %lx mem=%lx[%lx]\n", uiLo, uiHi, GlobalSize( hMem ));
181 }
182 else
183 {
184 uiLo = LOWORD( *lparam );
185 uiHi = HIWORD( *lparam );
186 TRACE("recv dde-ack %lx atom=%lx\n", uiLo, uiHi);
187 }
188 *lparam = PackDDElParam( WM_DDE_ACK, uiLo, uiHi );
189 break;
190 case WM_DDE_ADVISE:
191 case WM_DDE_DATA:
192 case WM_DDE_POKE:
193 if ((!buffer) && message != WM_DDE_DATA) return FALSE;
194 uiHi = *lparam;
195 if (size)
196 {
198 return FALSE;
199 if ((ptr = GlobalLock( hMem )))
200 {
201 memcpy( ptr, buffer, size );
202 GlobalUnlock( hMem );
203 }
204 else
205 {
206 GlobalFree( hMem );
207 return FALSE;
208 }
209 }
210 uiLo = (UINT_PTR)hMem;
211
212 *lparam = PackDDElParam( message, uiLo, uiHi );
213 break;
214 case WM_DDE_EXECUTE:
215 if (size)
216 {
217 if (!buffer) return FALSE;
218 if (!(hMem = GlobalAlloc( GMEM_MOVEABLE|GMEM_DDESHARE, size ))) return FALSE;
219 if ((ptr = GlobalLock( hMem )))
220 {
221 memcpy( ptr, buffer, size );
222 GlobalUnlock( hMem );
223 TRACE( "exec: pairing c=%08lx s=%p\n", *lparam, hMem );
224 if (!DdeAddPair( (HGLOBAL)*lparam, hMem ))
225 {
226 GlobalFree( hMem );
227 TRACE("udm exec: GF 1\n");
228 return FALSE;
229 }
230 }
231 else
232 {
233 GlobalFree( hMem );
234 TRACE("udm exec: GF 2\n");
235 return FALSE;
236 }
237 }
238 else
239 {
240 TRACE("udm exec: No Size\n");
241 return FALSE;
242 }
243
244 TRACE( "exec: exit c=%08lx s=%p\n", *lparam, hMem );
245 *lparam = (LPARAM)hMem;
246 break;
247 }
248 return TRUE;
249}
250
251//
252// DDE Post kernel callback.
253//
255WINAPI
256User32CallDDEPostFromKernel(PVOID Arguments, ULONG ArgumentLength)
257{
258 struct packed_message data;
259 BOOL Ret;
261 PDDEPOSTGET_CALLBACK_ARGUMENTS Common = Arguments;
262
263 data.data = 0;
264 data.size = 0;
265 TRACE("DDE Post CB\n");
266 Ret = post_dde_message( &data, Common->message, Common->lParam, &Common->lParam);
267
268 if (Ret)
269 {
270 Common->pvData = (PVOID)data.data;
271 Common->size = data.size;
272 TRACE("DDE Post CB size %d\n",data.size);
273 }
274 else
275 {
276 ERR("DDE Post CB Return bad msg 0x%x Size %d\n",Common->message,Common->size);
278 }
279
280 return ZwCallbackReturn(Arguments, ArgumentLength, Status);
281}
282
283//
284// DDE Get/Peek kernel callback.
285//
287WINAPI
288User32CallDDEGetFromKernel(PVOID Arguments, ULONG ArgumentLength)
289{
290 BOOL Ret;
292 PDDEPOSTGET_CALLBACK_ARGUMENTS Common = Arguments;
293
294 TRACE("DDE Get CB size %d\n",Common->size);
295
296 Ret = unpack_dde_message( Common->hwnd, Common->message, &Common->lParam, Common->buffer, Common->size );
297
298 if (!Ret)
299 {
300 ERR("DDE Get CB Return bad msg 0x%x\n",Common->message);
302 }
303 return ZwCallbackReturn(Arguments, ArgumentLength, Status);
304}
305
306
307/*
308 * @unimplemented
309 */
311{
313 return FALSE;
314}
@ lparam
Definition: SystemMenu.c:31
HWND hWnd
Definition: settings.c:17
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
LONG NTSTATUS
Definition: precomp.h:26
#define UNIMPLEMENTED
Definition: debug.h:115
#define ERR(fmt,...)
Definition: debug.h:110
LPARAM lParam
Definition: combotst.c:139
BOOL WINAPI UnpackDDElParam(UINT, LPARAM, PUINT_PTR, PUINT_PTR)
Definition: ddemisc.c:105
#define WM_DDE_DATA
Definition: dde.h:42
#define WM_DDE_POKE
Definition: dde.h:44
#define WM_DDE_ADVISE
Definition: dde.h:39
BOOL WINAPI FreeDDElParam(UINT, LPARAM)
Definition: ddemisc.c:147
#define WM_DDE_ACK
Definition: dde.h:41
#define WM_DDE_EXECUTE
Definition: dde.h:45
LPARAM WINAPI PackDDElParam(UINT, UINT_PTR, UINT_PTR)
Definition: ddemisc.c:63
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define ULONG_PTR
Definition: config.h:101
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
Status
Definition: gdiplustypes.h:25
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
Definition: gl.h:1950
GLsizeiptr size
Definition: glext.h:5919
GLuint buffer
Definition: glext.h:5915
GLfloat GLfloat GLfloat GLfloat h
Definition: glext.h:7723
LPVOID NTAPI GlobalLock(HGLOBAL hMem)
Definition: heapmem.c:755
HGLOBAL NTAPI GlobalFree(HGLOBAL hMem)
Definition: heapmem.c:611
BOOL NTAPI GlobalUnlock(HGLOBAL hMem)
Definition: heapmem.c:1190
HGLOBAL NTAPI GlobalAlloc(UINT uFlags, SIZE_T dwBytes)
Definition: heapmem.c:368
SIZE_T NTAPI GlobalSize(HGLOBAL hMem)
Definition: heapmem.c:1090
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
static PVOID ptr
Definition: dispmode.c:27
unsigned __int3264 UINT_PTR
Definition: mstsclib_h.h:274
unsigned int UINT
Definition: ndis.h:50
NTSYSAPI NTSTATUS NTAPI ZwCallbackReturn(_In_ PVOID Result, _In_ ULONG ResultLength, _In_ NTSTATUS Status)
#define FASTCALL
Definition: nt_native.h:50
#define HGLOBAL
Definition: ole.h:15
#define LOWORD(l)
Definition: pedump.c:82
#define STATUS_SUCCESS
Definition: shellext.h:65
#define TRACE(s)
Definition: solgame.cpp:4
Definition: dde.h:65
Definition: dde.h:57
unsigned short fAckReq
Definition: dde.h:58
unsigned short unused
Definition: dde.h:58
unsigned short reserved
Definition: dde.h:58
short cfFormat
Definition: dde.h:59
unsigned short fResponse
Definition: dde.h:58
unsigned short fRelease
Definition: dde.h:58
Definition: dde.h:72
Definition: tftpd.h:60
int size
Definition: dde.c:23
int count
Definition: dde.c:21
const void * data
Definition: dde.c:22
#define FIELD_OFFSET(t, f)
Definition: typedefs.h:255
void * PVOID
Definition: typedefs.h:50
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define MAKELONG(a, b)
Definition: typedefs.h:249
uint32_t ULONG
Definition: typedefs.h:59
uint64_t ULONGLONG
Definition: typedefs.h:67
#define HIWORD(l)
Definition: typedefs.h:247
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
_Must_inspect_result_ _In_ WDFKEY _In_ PCUNICODE_STRING _Out_opt_ PUSHORT _Inout_opt_ PUNICODE_STRING Value
Definition: wdfregistry.h:413
static void * unpack_ptr(ULONGLONG ptr64)
Definition: dde.c:41
NTSTATUS WINAPI User32CallDDEGetFromKernel(PVOID Arguments, ULONG ArgumentLength)
Definition: dde.c:288
NTSTATUS WINAPI User32CallDDEPostFromKernel(PVOID Arguments, ULONG ArgumentLength)
Definition: dde.c:256
static void push_data(struct packed_message *data, const void *ptr, int size)
Definition: dde.c:27
static ULONGLONG pack_ptr(const void *ptr)
Definition: dde.c:35
BOOL FASTCALL DdeAddPair(HGLOBAL ClientMem, HGLOBAL ServerMem)
Definition: message.c:181
BOOL post_dde_message(struct packed_message *data, UINT message, LPARAM lParam, LPARAM *lp)
Definition: dde.c:53
BOOL unpack_dde_message(HWND hwnd, UINT message, LPARAM *lparam, PVOID buffer, int size)
Definition: dde.c:159
BOOL WINAPI DdeGetQualityOfService(HWND hWnd, DWORD Reserved, PSECURITY_QUALITY_OF_SERVICE pqosPrev)
Definition: dde.c:310
HGLOBAL FASTCALL DdeGetPair(HGLOBAL ServerMem)
Definition: message.c:231
#define GMEM_MOVEABLE
Definition: winbase.h:294
#define GMEM_DDESHARE
Definition: winbase.h:298
_In_ LONG _In_ HWND hwnd
Definition: winddi.h:4023
_Reserved_ PVOID Reserved
Definition: winddi.h:3974
LONG_PTR LPARAM
Definition: windef.h:208
#define WINAPI
Definition: msvc.h:6