source: trunk/src/NTDLL/rtl.cpp@ 5568

Last change on this file since 5568 was 5568, checked in by sandervl, 24 years ago

merge with latest wine (rtlstr.c)

File size: 21.1 KB
Line 
1/* $Id: rtl.cpp,v 1.12 2001-04-22 10:38:59 sandervl Exp $ */
2
3/*
4 * Project Odin Software License can be found in LICENSE.TXT
5 * Win32 NT Runtime / NTDLL for OS/2
6 *
7 * Copyright 1998 original WINE Author
8 * Copyright 1998, 1999 Patrick Haller (phaller@gmx.net)
9 *
10 * NT basis DLL
11 *
12 * This file contains the Rtl* API functions. These should be implementable.
13 *
14 * Copyright 1996-1998 Marcus Meissner
15 * 1999 Alex Korobka
16 */
17
18#include <stdlib.h>
19#include <stdio.h>
20#include <string.h>
21#include <odinwrap.h>
22#include <os2win.h>
23
24#include "debugtools.h"
25
26#include "winuser.h"
27#include "windef.h"
28#include "winerror.h"
29#include "stackframe.h"
30#include "ntddk.h"
31#include "imagehlp.h"
32#include "winreg.h"
33#include "heapstring.h"
34
35#include <misc.h>
36
37
38ODINDEBUGCHANNEL(NTDLL-RTL)
39
40
41/*
42 * WINE Adoption - we won't support the Win64 model.
43 */
44#define SIZE_T UINT
45
46/*
47 * resource functions
48 */
49
50/***********************************************************************
51 * RtlInitializeResource (NTDLL.409)
52 *
53 * xxxResource() functions implement multiple-reader-single-writer lock.
54 * The code is based on information published in WDJ January 1999 issue.
55 */
56void WINAPI RtlInitializeResource(LPRTL_RWLOCK rwl)
57{
58 dprintf(("NTDLL: RtlInitializeResource(%08xh)\n",
59 rwl));
60
61 if( rwl )
62 {
63 rwl->iNumberActive = 0;
64 rwl->uExclusiveWaiters = 0;
65 rwl->uSharedWaiters = 0;
66 rwl->hOwningThreadId = 0;
67 rwl->dwTimeoutBoost = 0; /* no info on this one, default value is 0 */
68 InitializeCriticalSection( &rwl->rtlCS );
69 rwl->hExclusiveReleaseSemaphore = CreateSemaphoreA( NULL, 0, 65535, NULL );
70 rwl->hSharedReleaseSemaphore = CreateSemaphoreA( NULL, 0, 65535, NULL );
71 }
72}
73
74
75/***********************************************************************
76 * RtlDeleteResource (NTDLL.330)
77 */
78void WINAPI RtlDeleteResource(LPRTL_RWLOCK rwl)
79{
80 dprintf(("NTDLL: RtlDeleteResource(%08xh)\n",
81 rwl));
82
83 if( rwl )
84 {
85 EnterCriticalSection( &rwl->rtlCS );
86 if( rwl->iNumberActive || rwl->uExclusiveWaiters || rwl->uSharedWaiters )
87 dprintf(("NTDLL: RtlDeleteResource active MRSW lock (%p), expect failure\n",
88 rwl));
89
90 rwl->hOwningThreadId = 0;
91 rwl->uExclusiveWaiters = rwl->uSharedWaiters = 0;
92 rwl->iNumberActive = 0;
93 CloseHandle( rwl->hExclusiveReleaseSemaphore );
94 CloseHandle( rwl->hSharedReleaseSemaphore );
95 LeaveCriticalSection( &rwl->rtlCS );
96 DeleteCriticalSection( &rwl->rtlCS );
97 }
98}
99
100
101/***********************************************************************
102 * RtlAcquireResourceExclusive (NTDLL.256)
103 */
104BYTE WINAPI RtlAcquireResourceExclusive(LPRTL_RWLOCK rwl,
105 BYTE fWait)
106{
107 BYTE retVal = 0;
108
109 if( !rwl )
110 return 0;
111
112 dprintf(("NTDLL: RtlAcquireResourceExclusive(%08xh,%08xh)\n",
113 rwl,
114 fWait));
115
116start:
117 EnterCriticalSection( &rwl->rtlCS );
118 if( rwl->iNumberActive == 0 ) /* lock is free */
119 {
120 rwl->iNumberActive = -1;
121 retVal = 1;
122 }
123 else if( rwl->iNumberActive < 0 ) /* exclusive lock in progress */
124 {
125 if( rwl->hOwningThreadId == GetCurrentThreadId() )
126 {
127 retVal = 1;
128 rwl->iNumberActive--;
129 goto done;
130 }
131wait:
132 if( fWait )
133 {
134 rwl->uExclusiveWaiters++;
135
136 LeaveCriticalSection( &rwl->rtlCS );
137 if( WaitForSingleObject( rwl->hExclusiveReleaseSemaphore, INFINITE ) == WAIT_FAILED )
138 goto done;
139 goto start; /* restart the acquisition to avoid deadlocks */
140 }
141 }
142 else /* one or more shared locks are in progress */
143 if( fWait )
144 goto wait;
145
146 if( retVal == 1 )
147 rwl->hOwningThreadId = GetCurrentThreadId();
148done:
149 LeaveCriticalSection( &rwl->rtlCS );
150 return retVal;
151}
152
153/***********************************************************************
154 * RtlAcquireResourceShared (NTDLL.257)
155 */
156BYTE WINAPI RtlAcquireResourceShared(LPRTL_RWLOCK rwl,
157 BYTE fWait)
158{
159 DWORD dwWait = WAIT_FAILED;
160 BYTE retVal = 0;
161
162 if( !rwl )
163 return 0;
164
165 dprintf(("NTDLL: RtlAcquireResourceShared(%08xh,%08xh)\n",
166 rwl,
167 fWait));
168
169start:
170 EnterCriticalSection( &rwl->rtlCS );
171 if( rwl->iNumberActive < 0 )
172 {
173 if( rwl->hOwningThreadId == GetCurrentThreadId() )
174 {
175 rwl->iNumberActive--;
176 retVal = 1;
177 goto done;
178 }
179
180 if( fWait )
181 {
182 rwl->uSharedWaiters++;
183 LeaveCriticalSection( &rwl->rtlCS );
184 if( (dwWait = WaitForSingleObject( rwl->hSharedReleaseSemaphore, INFINITE )) == WAIT_FAILED )
185 goto done;
186 goto start;
187 }
188 }
189 else
190 {
191 if( dwWait != WAIT_OBJECT_0 ) /* otherwise RtlReleaseResource() has already done it */
192 rwl->iNumberActive++;
193 retVal = 1;
194 }
195done:
196 LeaveCriticalSection( &rwl->rtlCS );
197 return retVal;
198}
199
200
201/***********************************************************************
202 * RtlReleaseResource (NTDLL.471)
203 */
204void WINAPI RtlReleaseResource(LPRTL_RWLOCK rwl)
205{
206 dprintf(("NTDLL: RtlReleaseResource(%08xh)\n",
207 rwl));
208
209 EnterCriticalSection( &rwl->rtlCS );
210
211 if( rwl->iNumberActive > 0 ) /* have one or more readers */
212 {
213 if( --rwl->iNumberActive == 0 )
214 {
215 if( rwl->uExclusiveWaiters )
216 {
217wake_exclusive:
218 rwl->uExclusiveWaiters--;
219 ReleaseSemaphore( rwl->hExclusiveReleaseSemaphore, 1, NULL );
220 }
221 }
222 }
223 else
224 if( rwl->iNumberActive < 0 ) /* have a writer, possibly recursive */
225 {
226 if( ++rwl->iNumberActive == 0 )
227 {
228 rwl->hOwningThreadId = 0;
229 if( rwl->uExclusiveWaiters )
230 goto wake_exclusive;
231 else
232 if( rwl->uSharedWaiters )
233 {
234 UINT n = rwl->uSharedWaiters;
235 rwl->iNumberActive = rwl->uSharedWaiters; /* prevent new writers from joining until
236 * all queued readers have done their thing */
237 rwl->uSharedWaiters = 0;
238 ReleaseSemaphore( rwl->hSharedReleaseSemaphore, n, NULL );
239 }
240 }
241 }
242 LeaveCriticalSection( &rwl->rtlCS );
243}
244
245
246/***********************************************************************
247 * RtlDumpResource (NTDLL.340)
248 */
249void WINAPI RtlDumpResource(LPRTL_RWLOCK rwl)
250{
251 dprintf(("NTDLL: RtlDumpResource(%08x)\n",
252 rwl));
253
254 if( rwl )
255 {
256 dprintf(("NTDLL: RtlDumpResource(%p):\n\tactive count = %i\n\twaiting readers = %i\n\twaiting writers = %i\n",
257 rwl,
258 rwl->iNumberActive,
259 rwl->uSharedWaiters,
260 rwl->uExclusiveWaiters));
261
262 if( rwl->iNumberActive )
263 dprintf(("NTDLL: \towner thread = %08x\n",
264 rwl->hOwningThreadId ));
265 }
266}
267
268
269/*
270 * heap functions
271 */
272
273/******************************************************************************
274 * RtlCreateHeap [NTDLL]
275 */
276HANDLE WINAPI RtlCreateHeap(ULONG Flags,
277 PVOID BaseAddress,
278 ULONG SizeToReserve,
279 ULONG SizeToCommit,
280 PVOID Unknown,
281 PRTL_HEAP_DEFINITION Definition)
282{
283 dprintf(("NTDLL: RtlCreateHeap(%08xh,%08xh,%08xh,%08xh,%08xh,%08xh).\n",
284 Flags,
285 BaseAddress,
286 SizeToReserve,
287 SizeToCommit,
288 Unknown,
289 Definition));
290
291 return HeapCreate(Flags,
292 SizeToCommit,
293 SizeToReserve);
294}
295
296
297/******************************************************************************
298 * RtlAllocateHeap [NTDLL]
299 */
300PVOID WINAPI RtlAllocateHeap(HANDLE Heap,
301 ULONG Flags,
302 ULONG Size)
303{
304 dprintf(("NTDLL: RtlAllocateHeap(%08xh,%08xh,%08xh).\n",
305 Heap,
306 Flags,
307 Size));
308
309 return HeapAlloc(Heap,
310 Flags,
311 Size);
312}
313
314
315/******************************************************************************
316 * RtlFreeHeap [NTDLL]
317 */
318BOOLEAN WINAPI RtlFreeHeap(HANDLE Heap,
319 ULONG Flags,
320 PVOID Address)
321{
322 dprintf(("NTDLL: RtlFreeHeap(%08xh,%08xh,%08xh)\n",
323 Heap,
324 Flags,
325 Address));
326
327 return HeapFree(Heap, Flags, Address);
328}
329
330
331/******************************************************************************
332 * RtlDestroyHeap [NTDLL]
333 *
334 * FIXME: prototype guessed
335 */
336BOOLEAN WINAPI RtlDestroyHeap(HANDLE Heap)
337{
338 dprintf(("NTDLL: RtlDestroyHeap(%08xh)\n",
339 Heap));
340
341 return HeapDestroy(Heap);
342}
343
344
345
346/******************************************************************************
347 * RtlSizeHeap [NTDLL]
348 */
349
350ODINFUNCTION3(DWORD,RtlSizeHeap,HANDLE,hHeap,
351 DWORD, dwFlags,
352 PVOID, pAddress)
353{
354 return HeapSize(hHeap,
355 dwFlags,
356 pAddress);
357}
358
359
360
361/*
362 * misc functions
363 */
364
365
366/******************************************************************************
367 * RtlAcquirePebLock [NTDLL]
368 */
369VOID WINAPI RtlAcquirePebLock(void)
370{
371 dprintf(("NTDLL: RtlAcquirePebLock() not implemented.\n"));
372
373 /* enter critical section ? */
374}
375
376
377/******************************************************************************
378 * RtlReleasePebLock [NTDLL]
379 */
380VOID WINAPI RtlReleasePebLock(void)
381{
382 dprintf(("NTDLL: RtlReleasePebLock() not implemented.\n"));
383
384 /* leave critical section ? */
385}
386
387
388/******************************************************************************
389 * RtlIntegerToChar [NTDLL]
390 */
391DWORD WINAPI RtlIntegerToChar(DWORD x1,
392 DWORD x2,
393 DWORD x3,
394 DWORD x4)
395{
396 dprintf(("NTDLL: RtlIntegerToChar(%08xh,%08xh,%08xh,%08xh) not implemented.\n",
397 x1,
398 x2,
399 x3,
400 x4));
401
402 return 0;
403}
404
405
406/******************************************************************************
407 * RtlSetEnvironmentVariable [NTDLL]
408 */
409DWORD WINAPI RtlSetEnvironmentVariable(DWORD x1,
410 PUNICODE_STRING key,
411 PUNICODE_STRING val)
412{
413 dprintf(("NTDLL: RtlSetEnvironmentVariable(%08xh,%08xh,%08xh) not implemented.\n",
414 x1,
415 key,
416 val));
417
418 return 0;
419}
420
421
422/******************************************************************************
423 * RtlNewSecurityObject [NTDLL]
424 */
425DWORD WINAPI RtlNewSecurityObject(DWORD x1,
426 DWORD x2,
427 DWORD x3,
428 DWORD x4,
429 DWORD x5,
430 DWORD x6)
431{
432 dprintf(("NTDLL: RtlNewSecurityObject(%08xh,%08xh,%08xh,%08xh,%08xh,%08xh) not implemented.\n",
433 x1,
434 x2,
435 x3,
436 x4,
437 x5,
438 x6));
439
440 return 0;
441}
442
443
444/******************************************************************************
445 * RtlDeleteSecurityObject [NTDLL]
446 */
447DWORD WINAPI RtlDeleteSecurityObject(DWORD x1)
448{
449 dprintf(("NTDLL: RtlDeleteSecurityObject(%08xh) not implemented.\n",
450 x1));
451
452 return 0;
453}
454
455
456/**************************************************************************
457 * RtlNormalizeProcessParams [NTDLL.441]
458 */
459LPVOID WINAPI RtlNormalizeProcessParams(LPVOID x)
460{
461 dprintf(("NTDLL: RtlNormalizeProcessParams(%08xh) not implemented.\n",
462 x));
463
464 return x;
465}
466
467
468/**************************************************************************
469 * RtlNtStatusToDosError [NTDLL.442]
470 */
471DWORD WINAPI RtlNtStatusToDosError(DWORD error)
472{
473 dprintf(("NTDLL: RtlNtStatusToDosError(%08xh) partially implemented.\n",
474 error));
475
476 switch (error)
477 {
478 case STATUS_SUCCESS: return ERROR_SUCCESS;
479 case STATUS_INVALID_PARAMETER: return ERROR_BAD_ARGUMENTS;
480 case STATUS_BUFFER_TOO_SMALL: return ERROR_INSUFFICIENT_BUFFER;
481/* case STATUS_INVALID_SECURITY_DESCR: return ERROR_INVALID_SECURITY_DESCR;*/
482 case STATUS_NO_MEMORY: return ERROR_NOT_ENOUGH_MEMORY;
483/* case STATUS_UNKNOWN_REVISION:
484 case STATUS_BUFFER_OVERFLOW:*/
485 }
486
487 dprintf(("NTDLL: RtlNtStatusToDosError(%08xh is unknown !)\n",
488 error));
489
490 return ERROR_SUCCESS;
491}
492
493
494/**************************************************************************
495 * RtlGetNtProductType [NTDLL.390]
496 */
497BOOLEAN WINAPI RtlGetNtProductType(LPDWORD type)
498{
499 dprintf(("NTDLL: RtlGetNtProductType(%08xh) not correctly implemented.\n",
500 type));
501
502 *type=3; /* dunno. 1 for client, 3 for server? */
503 return 1;
504}
505
506
507/******************************************************************************
508 * RtlEnlargedIntegerMultiply [NTDLL.341]
509 * Note: This even works, since gcc returns 64bit values in eax/edx just like
510 * the caller expects. However... The relay code won't grok this I think.
511 *
512 * @@@PH: Parameters are unknown
513 */
514/* longlong in VAC++ ? */
515
516extern INT WINAPI RtlEnlargedIntegerMultiply(INT factor1,
517 INT factor2);
518
519
520/******************************************************************************
521 * RtlExtendedLargeIntegerDivide [NTDLL.359]
522 */
523extern INT WINAPI RtlExtendedLargeIntegerDivide(LARGE_INTEGER dividend,
524 DWORD divisor,
525 LPDWORD rest);
526
527/******************************************************************************
528 * RtlExtendedLargeIntegerMultiply [NTDLL.358]
529 * Note: This even works, since gcc returns 64bit values in eax/edx just like
530 * the caller expects. However... The relay code won't grok this I think.
531 */
532/* longlong in VAC++ ? */
533
534extern LARGE_INTEGER WINAPI RtlExtendedIntegerMultiply(LARGE_INTEGER factor1,
535 INT factor2);
536
537/******************************************************************************
538 * RtlFormatCurrentUserKeyPath [NTDLL.371]
539 */
540DWORD WINAPI RtlFormatCurrentUserKeyPath(PUNICODE_STRING pustrKeyPath)
541{
542 dprintf(("NTDLL: RtlFormatCurrentUserKeyPath(%08xh) not correctly implemented.\n",
543 pustrKeyPath));
544
545 LPSTR Path = "\\REGISTRY\\USER\\.DEFAULT";
546 ANSI_STRING AnsiPath;
547
548 RtlInitAnsiString(&AnsiPath, Path);
549 return RtlAnsiStringToUnicodeString(pustrKeyPath, &AnsiPath, TRUE);
550}
551
552
553/******************************************************************************
554 * RtlOpenCurrentUser [NTDLL]
555 */
556ODINFUNCTION2(DWORD, RtlOpenCurrentUser,
557 ACCESS_MASK,DesiredAccess,
558 PHANDLE, pKeyHandle)
559{
560 /* Note: this is not the correct solution,
561 * But this works pretty good on wine and NT4.0 binaries
562 */
563
564 if (DesiredAccess == 0x2000000 )
565 {
566 *pKeyHandle = HKEY_CURRENT_USER;
567 return TRUE;
568 }
569
570 return FALSE;
571/* PH 2000/08/18 currently disabled
572 OBJECT_ATTRIBUTES ObjectAttributes;
573 UNICODE_STRING ObjectName;
574 NTSTATUS ret;
575
576 RtlFormatCurrentUserKeyPath(&ObjectName);
577 InitializeObjectAttributes(&ObjectAttributes,&ObjectName,OBJ_CASE_INSENSITIVE,0, NULL);
578 ret = NtOpenKey(pKeyHandle, DesiredAccess, &ObjectAttributes);
579 RtlFreeUnicodeString(&ObjectName);
580 return ret;
581 */
582}
583
584
585/**************************************************************************
586 * RtlDosPathNameToNtPathName_U [NTDLL.338]
587 *
588 * FIXME: convert to UNC or whatever is expected here
589 */
590BOOLEAN WINAPI RtlDosPathNameToNtPathName_U(LPWSTR from,
591 PUNICODE_STRING us,
592 DWORD x2,
593 DWORD x3)
594{
595 LPSTR fromA = HEAP_strdupWtoA(GetProcessHeap(),0,from);
596
597 dprintf(("NTDLL: RtlDosPathNameToNtPathName_U(%08xh,%08h,%08xh,%08xh) not implemented.\n",
598 from,
599 us,
600 x2,
601 x3));
602
603 if (us)
604 RtlInitUnicodeString(us,HEAP_strdupW(GetProcessHeap(),0,from));
605
606 return TRUE;
607}
608
609
610/***********************************************************************
611 * RtlImageNtHeader (NTDLL)
612 */
613PIMAGE_NT_HEADERS WINAPI RtlImageNtHeader(HMODULE hModule)
614{
615 IMAGE_NT_HEADERS *ret = NULL;
616 IMAGE_DOS_HEADER *dos = (IMAGE_DOS_HEADER *)hModule;
617
618 if (dos->e_magic == IMAGE_DOS_SIGNATURE)
619 {
620 ret = (IMAGE_NT_HEADERS *)((char *)dos + dos->e_lfanew);
621 if (ret->Signature != IMAGE_NT_SIGNATURE) ret = NULL;
622 }
623 return ret;
624}
625
626/******************************************************************************
627 * RtlCreateEnvironment [NTDLL]
628 */
629DWORD WINAPI RtlCreateEnvironment(DWORD x1,
630 DWORD x2)
631{
632 dprintf(("NTDLL: RtlCreateEnvironment(%08xh, %08xh) not implemented.\n",
633 x1,
634 x2));
635
636 return 0;
637}
638
639
640/******************************************************************************
641 * RtlDestroyEnvironment [NTDLL]
642 */
643DWORD WINAPI RtlDestroyEnvironment(DWORD x)
644{
645 dprintf(("NTDLL: RtlDestroyEnvironment(%08xh) not implemented.\n",
646 x));
647
648 return 0;
649}
650
651
652/******************************************************************************
653 * RtlQueryEnvironmentVariable_U [NTDLL]
654 */
655DWORD WINAPI RtlQueryEnvironmentVariable_U(DWORD x1,
656 PUNICODE_STRING key,
657 PUNICODE_STRING val)
658{
659 dprintf(("NTDLL: RtlQueryEnvironmentVariable_U(%08xh,%08xh,%08xh) not implemented.\n",
660 x1,
661 key,
662 val));
663
664 return 0;
665}
666
667/******************************************************************************
668 * RtlInitializeGenericTable [NTDLL]
669 */
670DWORD WINAPI RtlInitializeGenericTable(void)
671{
672 FIXME("\n");
673 return 0;
674}
675
676/******************************************************************************
677 * RtlInitializeBitMap [NTDLL]
678 *
679 */
680NTSTATUS WINAPI RtlInitializeBitMap(DWORD x1,DWORD x2,DWORD x3)
681{
682 FIXME("(0x%08lx,0x%08lx,0x%08lx),stub\n",x1,x2,x3);
683 return 0;
684}
685
686/******************************************************************************
687 * RtlSetBits [NTDLL]
688 *
689 */
690NTSTATUS WINAPI RtlSetBits(DWORD x1,DWORD x2,DWORD x3)
691{
692 FIXME("(0x%08lx,0x%08lx,0x%08lx),stub\n",x1,x2,x3);
693 return 0;
694}
695
696/******************************************************************************
697 * RtlFindClearBits [NTDLL]
698 *
699 */
700NTSTATUS WINAPI RtlFindClearBits(DWORD x1,DWORD x2,DWORD x3)
701{
702 FIXME("(0x%08lx,0x%08lx,0x%08lx),stub\n",x1,x2,x3);
703 return 0;
704}
705
706/******************************************************************************
707 * RtlClearBits [NTDLL]
708 *
709 */
710NTSTATUS WINAPI RtlClearBits(DWORD x1,DWORD x2,DWORD x3)
711{
712 FIXME("(0x%08lx,0x%08lx,0x%08lx),stub\n",x1,x2,x3);
713 return 0;
714}
715
716/******************************************************************************
717 * RtlCopyMemory [NTDLL]
718 *
719 */
720#undef RtlCopyMemory
721VOID WINAPI RtlCopyMemory( VOID *Destination, CONST VOID *Source, SIZE_T Length )
722{
723 memcpy(Destination, Source, Length);
724}
725
726/******************************************************************************
727 * RtlMoveMemory [NTDLL]
728 */
729#undef RtlMoveMemory
730VOID WINAPI RtlMoveMemory( VOID *Destination, CONST VOID *Source, SIZE_T Length )
731{
732 memmove(Destination, Source, Length);
733}
734
735/******************************************************************************
736 * RtlFillMemory [NTDLL]
737 */
738#undef RtlFillMemory
739VOID WINAPI RtlFillMemory( VOID *Destination, SIZE_T Length, UINT Fill )
740{
741 memset(Destination, Fill, Length);
742}
743
744/******************************************************************************
745 * RtlZeroMemory [NTDLL]
746 */
747#undef RtlZeroMemory
748VOID WINAPI RtlZeroMemory( VOID *Destination, SIZE_T Length )
749{
750 memset(Destination, 0, Length);
751}
752
753/******************************************************************************
754 * RtlCompareMemory [NTDLL]
755 */
756SIZE_T WINAPI RtlCompareMemory( const VOID *Source1, const VOID *Source2, SIZE_T Length)
757{
758 int i;
759 for(i=0; (i<Length) && (((LPBYTE)Source1)[i]==((LPBYTE)Source2)[i]); i++);
760 return i;
761}
762
763/******************************************************************************
764 * RtlAssert [NTDLL]
765 *
766 * Not implemented in non-debug versions.
767 */
768void WINAPI RtlAssert(LPVOID x1,LPVOID x2,DWORD x3, DWORD x4)
769{
770 FIXME("(%p,%p,0x%08lx,0x%08lx),stub\n",x1,x2,x3,x4);
771}
772
773/*****************************************************************************
774 * Name : RtlCopyLuid
775 * Purpose : copy local unique identifier?
776 * Parameters: PLUID pluid1
777 * PLUID pluid2
778 * Variables :
779 * Result :
780 * Remark : NTDLL.321
781 * Status : COMPLETELY ? IMPLEMENTED TESTED ?
782 *
783 * Author : Patrick Haller [Tue, 1999/11/09 09:00]
784 *****************************************************************************/
785
786PLUID WINAPI RtlCopyLuid(PLUID pluid1,
787 PLUID pluid2)
788{
789 pluid2->LowPart = pluid1->LowPart;
790 pluid2->HighPart = pluid1->HighPart;
791 return (pluid1);
792}
Note: See TracBrowser for help on using the repository browser.