1b06d7f58bb8cf02d98cb76da9ce91a54dd29db7
[reactos.git] / reactos / win32ss / user / user32 / windows / prop.c
1 /*
2 * ReactOS kernel
3 * Copyright (C) 1998, 1999, 2000, 2001 ReactOS Team
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 */
19 /*
20 * PROJECT: ReactOS user32.dll
21 * FILE: user/user32/windows/prop.c
22 * PURPOSE: Window Property
23 * PROGRAMMER: Casper S. Hornstrup (chorns@users.sourceforge.net)
24 * UPDATE HISTORY:
25 * 09-05-2001 CSH Created
26 */
27
28 /* INCLUDES ******************************************************************/
29
30 #include <user32.h>
31
32 #include <wine/debug.h>
33
34 WINE_DEFAULT_DEBUG_CHANNEL(user32);
35
36 #define ATOM_BUFFER_SIZE 256
37
38 /* INTERNAL FUNCTIONS ********************************************************/
39
40 HANDLE
41 FASTCALL
42 IntGetProp(HWND hWnd, ATOM Atom)
43 {
44 PLIST_ENTRY ListEntry, temp;
45 PPROPERTY Property;
46 PWND pWnd;
47 int i;
48
49 pWnd = ValidateHwnd(hWnd);
50 if (!pWnd) return NULL;
51
52 ListEntry = SharedPtrToUser(pWnd->PropListHead.Flink);
53 for (i = 0; i < pWnd->PropListItems; i++ )
54 {
55 Property = CONTAINING_RECORD(ListEntry, PROPERTY, PropListEntry);
56 if (!Property) break;
57 if (Property->Atom == Atom)
58 {
59 return(Property);
60 }
61 temp = ListEntry->Flink;
62 ListEntry = SharedPtrToUser(temp);
63 }
64 return NULL;
65 }
66
67 HANDLE
68 FASTCALL
69 UserGetProp(HWND hWnd, ATOM Atom)
70 {
71 PPROPERTY Prop;
72 Prop = IntGetProp(hWnd, Atom);
73 return Prop ? Prop->Data : NULL;
74 }
75
76 /* FUNCTIONS *****************************************************************/
77
78 /*
79 * @implemented
80 */
81 int WINAPI
82 EnumPropsA(HWND hWnd, PROPENUMPROCA lpEnumFunc)
83 {
84 PPROPLISTITEM pli, i;
85 NTSTATUS Status;
86 DWORD Count;
87 int ret = -1;
88
89 if(!lpEnumFunc)
90 {
91 SetLastError(ERROR_INVALID_PARAMETER);
92 return ret;
93 }
94
95 Status = NtUserBuildPropList(hWnd, NULL, 0, &Count);
96 if(!NT_SUCCESS(Status))
97 {
98 if(Status == STATUS_INVALID_HANDLE)
99 SetLastError(ERROR_INVALID_WINDOW_HANDLE);
100 else
101 SetLastError(RtlNtStatusToDosError(Status));
102 return ret;
103 }
104
105 if(Count > 0)
106 {
107 pli = RtlAllocateHeap(GetProcessHeap(), 0, Count);
108 if (pli == NULL)
109 {
110 SetLastError(ERROR_OUTOFMEMORY);
111 return -1;
112 }
113
114 Status = NtUserBuildPropList(hWnd, (LPVOID)pli, Count, &Count);
115 if(!NT_SUCCESS(Status))
116 {
117 RtlFreeHeap(GetProcessHeap(), 0, pli);
118 if(Status == STATUS_INVALID_HANDLE)
119 SetLastError(ERROR_INVALID_WINDOW_HANDLE);
120 else
121 SetLastError(RtlNtStatusToDosError(Status));
122 return ret;
123 }
124
125 i = pli;
126 for(; Count > 0; Count--, i++)
127 {
128 char str[ATOM_BUFFER_SIZE];
129
130 if(!GlobalGetAtomNameA(i->Atom, str, ATOM_BUFFER_SIZE))
131 continue;
132
133 ret = lpEnumFunc(hWnd, str, i->Data);
134 if(!ret)
135 break;
136 }
137
138 RtlFreeHeap(GetProcessHeap(), 0, pli);
139 }
140
141 return ret;
142 }
143
144
145 /*
146 * @implemented
147 */
148 int WINAPI
149 EnumPropsExA(HWND hWnd, PROPENUMPROCEXA lpEnumFunc, LPARAM lParam)
150 {
151 PPROPLISTITEM pli, i;
152 NTSTATUS Status;
153 DWORD Count;
154 int ret = -1;
155
156 if(!lpEnumFunc)
157 {
158 SetLastError(ERROR_INVALID_PARAMETER);
159 return ret;
160 }
161
162 Status = NtUserBuildPropList(hWnd, NULL, 0, &Count);
163 if(!NT_SUCCESS(Status))
164 {
165 if(Status == STATUS_INVALID_HANDLE)
166 SetLastError(ERROR_INVALID_WINDOW_HANDLE);
167 else
168 SetLastError(RtlNtStatusToDosError(Status));
169 return ret;
170 }
171
172 if(Count > 0)
173 {
174 pli = RtlAllocateHeap(GetProcessHeap(), 0, Count);
175 if (pli == NULL)
176 {
177 SetLastError(ERROR_OUTOFMEMORY);
178 return -1;
179 }
180
181 Status = NtUserBuildPropList(hWnd, (LPVOID)pli, Count, &Count);
182 if(!NT_SUCCESS(Status))
183 {
184 RtlFreeHeap(GetProcessHeap(), 0, pli);
185 if(Status == STATUS_INVALID_HANDLE)
186 SetLastError(ERROR_INVALID_WINDOW_HANDLE);
187 else
188 SetLastError(RtlNtStatusToDosError(Status));
189 return ret;
190 }
191
192 i = pli;
193 for(; Count > 0; Count--, i++)
194 {
195 char str[ATOM_BUFFER_SIZE];
196
197 if(!GlobalGetAtomNameA(i->Atom, str, ATOM_BUFFER_SIZE))
198 continue;
199
200 ret = lpEnumFunc(hWnd, str, i->Data, lParam);
201 if(!ret)
202 break;
203 }
204
205 RtlFreeHeap(GetProcessHeap(), 0, pli);
206 }
207
208 return ret;
209 }
210
211
212 /*
213 * @implemented
214 */
215 int WINAPI
216 EnumPropsExW(HWND hWnd, PROPENUMPROCEXW lpEnumFunc, LPARAM lParam)
217 {
218 PPROPLISTITEM pli, i;
219 NTSTATUS Status;
220 DWORD Count;
221 int ret = -1;
222
223 if(!lpEnumFunc)
224 {
225 SetLastError(ERROR_INVALID_PARAMETER);
226 return ret;
227 }
228
229 Status = NtUserBuildPropList(hWnd, NULL, 0, &Count);
230 if(!NT_SUCCESS(Status))
231 {
232 if(Status == STATUS_INVALID_HANDLE)
233 SetLastError(ERROR_INVALID_WINDOW_HANDLE);
234 else
235 SetLastError(RtlNtStatusToDosError(Status));
236 return ret;
237 }
238
239 if(Count > 0)
240 {
241 pli = RtlAllocateHeap(GetProcessHeap(), 0, Count);
242 if (pli == NULL)
243 {
244 SetLastError(ERROR_OUTOFMEMORY);
245 return -1;
246 }
247
248 Status = NtUserBuildPropList(hWnd, (LPVOID)pli, Count, &Count);
249 if(!NT_SUCCESS(Status))
250 {
251 RtlFreeHeap(GetProcessHeap(), 0, pli);
252 if(Status == STATUS_INVALID_HANDLE)
253 SetLastError(ERROR_INVALID_WINDOW_HANDLE);
254 else
255 SetLastError(RtlNtStatusToDosError(Status));
256 return ret;
257 }
258
259 i = pli;
260 for(; Count > 0; Count--, i++)
261 {
262 WCHAR str[ATOM_BUFFER_SIZE];
263
264 if(!GlobalGetAtomNameW(i->Atom, str, ATOM_BUFFER_SIZE))
265 continue;
266
267 ret = lpEnumFunc(hWnd, str, i->Data, lParam);
268 if(!ret)
269 break;
270 }
271
272 RtlFreeHeap(GetProcessHeap(), 0, pli);
273 }
274
275 return ret;
276 }
277
278
279 /*
280 * @implemented
281 */
282 int WINAPI
283 EnumPropsW(HWND hWnd, PROPENUMPROCW lpEnumFunc)
284 {
285 PPROPLISTITEM pli, i;
286 NTSTATUS Status;
287 DWORD Count;
288 int ret = -1;
289
290 if(!lpEnumFunc)
291 {
292 SetLastError(ERROR_INVALID_PARAMETER);
293 return ret;
294 }
295
296 Status = NtUserBuildPropList(hWnd, NULL, 0, &Count);
297 if(!NT_SUCCESS(Status))
298 {
299 if(Status == STATUS_INVALID_HANDLE)
300 SetLastError(ERROR_INVALID_WINDOW_HANDLE);
301 else
302 SetLastError(RtlNtStatusToDosError(Status));
303 return ret;
304 }
305
306 if(Count > 0)
307 {
308 pli = RtlAllocateHeap(GetProcessHeap(), 0, Count);
309 if (pli == NULL)
310 {
311 SetLastError(ERROR_OUTOFMEMORY);
312 return -1;
313 }
314
315 Status = NtUserBuildPropList(hWnd, (LPVOID)pli, Count, &Count);
316 if(!NT_SUCCESS(Status))
317 {
318 RtlFreeHeap(GetProcessHeap(), 0, pli);
319 if(Status == STATUS_INVALID_HANDLE)
320 SetLastError(ERROR_INVALID_WINDOW_HANDLE);
321 else
322 SetLastError(RtlNtStatusToDosError(Status));
323 return ret;
324 }
325
326 i = pli;
327 for(; Count > 0; Count--, i++)
328 {
329 WCHAR str[ATOM_BUFFER_SIZE];
330
331 if(!GlobalGetAtomNameW(i->Atom, str, ATOM_BUFFER_SIZE))
332 continue;
333
334 ret = lpEnumFunc(hWnd, str, i->Data);
335 if(!ret)
336 break;
337 }
338
339 RtlFreeHeap(GetProcessHeap(), 0, pli);
340 }
341
342 return ret;
343 }
344
345
346 /*
347 * @implemented
348 */
349 HANDLE WINAPI
350 GetPropA(HWND hWnd, LPCSTR lpString)
351 {
352 PWSTR lpWString;
353 UNICODE_STRING UString;
354 HANDLE Ret;
355 if (HIWORD(lpString))
356 {
357 RtlCreateUnicodeStringFromAsciiz(&UString, (LPSTR)lpString);
358 lpWString = UString.Buffer;
359 if (lpWString == NULL)
360 {
361 return(FALSE);
362 }
363 Ret = GetPropW(hWnd, lpWString);
364 RtlFreeUnicodeString(&UString);
365 }
366 else
367 {
368 Ret = GetPropW(hWnd, (LPWSTR)lpString);
369 }
370 return(Ret);
371 }
372
373
374 /*
375 * @implemented
376 */
377 HANDLE WINAPI
378 GetPropW(HWND hWnd, LPCWSTR lpString)
379 {
380 ATOM Atom;
381 HANDLE Data = NULL;
382 PPROPERTY Prop;
383 if (HIWORD(lpString))
384 {
385 Atom = GlobalFindAtomW(lpString);
386 }
387 else
388 {
389 Atom = LOWORD((DWORD_PTR)lpString);
390 }
391 Prop = IntGetProp(hWnd, Atom);
392 if (Prop != NULL) Data = Prop->Data;
393 return Data;
394 }
395
396
397 /*
398 * @implemented
399 */
400 HANDLE WINAPI
401 RemovePropA(HWND hWnd, LPCSTR lpString)
402 {
403 PWSTR lpWString;
404 UNICODE_STRING UString;
405 HANDLE Ret;
406
407 if (HIWORD(lpString))
408 {
409 RtlCreateUnicodeStringFromAsciiz(&UString, (LPSTR)lpString);
410 lpWString = UString.Buffer;
411 if (lpWString == NULL)
412 {
413 return(FALSE);
414 }
415 Ret = RemovePropW(hWnd, lpWString);
416 RtlFreeUnicodeString(&UString);
417 }
418 else
419 {
420 Ret = RemovePropW(hWnd, (LPCWSTR)lpString);
421 }
422 return(Ret);
423 }
424
425
426 /*
427 * @implemented
428 */
429 HANDLE WINAPI
430 RemovePropW(HWND hWnd,
431 LPCWSTR lpString)
432 {
433 ATOM Atom;
434 if (HIWORD(lpString))
435 {
436 Atom = GlobalFindAtomW(lpString);
437 }
438 else
439 {
440 Atom = LOWORD((DWORD_PTR)lpString);
441 }
442 return(NtUserRemoveProp(hWnd, Atom));
443 }
444
445
446 /*
447 * @implemented
448 */
449 BOOL WINAPI
450 SetPropA(HWND hWnd, LPCSTR lpString, HANDLE hData)
451 {
452 PWSTR lpWString;
453 UNICODE_STRING UString;
454 BOOL Ret;
455
456 if (HIWORD(lpString))
457 {
458 RtlCreateUnicodeStringFromAsciiz(&UString, (LPSTR)lpString);
459 lpWString = UString.Buffer;
460 if (lpWString == NULL)
461 {
462 return(FALSE);
463 }
464 Ret = SetPropW(hWnd, lpWString, hData);
465 RtlFreeUnicodeString(&UString);
466 }
467 else
468 {
469 Ret = SetPropW(hWnd, (LPWSTR)lpString, hData);
470 }
471 return(Ret);
472 }
473
474
475 /*
476 * @implemented
477 */
478 BOOL WINAPI
479 SetPropW(HWND hWnd, LPCWSTR lpString, HANDLE hData)
480 {
481 ATOM Atom;
482 if (HIWORD(lpString))
483 {
484 Atom = GlobalAddAtomW(lpString);
485 }
486 else
487 {
488 Atom = LOWORD((DWORD_PTR)lpString);
489 }
490
491 return(NtUserSetProp(hWnd, Atom, hData));
492 }