3 * reactos/subsys/csrss/api/handle.c
5 * CSRSS handle functions
7 * ReactOS Operating System
10 /* INCLUDES ******************************************************************/
17 /* FUNCTIONS *****************************************************************/
19 static unsigned ObjectDefinitionsCount
= 0;
20 static PCSRSS_OBJECT_DEFINITION ObjectDefinitions
= NULL
;
24 CsrIsConsoleHandle(HANDLE Handle
)
26 return ((ULONG_PTR
)Handle
& 0x10000003) == 0x3;
32 CsrRegisterObjectDefinitions(
33 PCSRSS_OBJECT_DEFINITION NewDefinitions
)
36 PCSRSS_OBJECT_DEFINITION Scan
;
37 PCSRSS_OBJECT_DEFINITION New
;
40 for (Scan
= NewDefinitions
; 0 != Scan
->Type
; Scan
++)
45 New
= RtlAllocateHeap(CsrssApiHeap
,
47 (ObjectDefinitionsCount
+ NewCount
)
48 * sizeof(CSRSS_OBJECT_DEFINITION
));
51 DPRINT1("Unable to allocate memory\n");
52 return STATUS_NO_MEMORY
;
55 if (0 != ObjectDefinitionsCount
)
59 ObjectDefinitionsCount
* sizeof(CSRSS_OBJECT_DEFINITION
));
60 RtlFreeHeap(CsrssApiHeap
, 0, ObjectDefinitions
);
63 RtlCopyMemory(New
+ ObjectDefinitionsCount
,
65 NewCount
* sizeof(CSRSS_OBJECT_DEFINITION
));
66 ObjectDefinitions
= New
;
67 ObjectDefinitionsCount
+= NewCount
;
69 return STATUS_SUCCESS
;
75 PCSRSS_PROCESS_DATA ProcessData
,
80 ULONG_PTR h
= (ULONG_PTR
)Handle
>> 2;
81 DPRINT("CsrGetObject, Object: %x, %x, %x\n", Object
, Handle
, ProcessData
? ProcessData
->HandleTableSize
: 0);
83 DPRINT("CsrGetObject, Object: %x, %x, %x\n",
84 Object
, Handle
, ProcessData
? ProcessData
->HandleTableSize
: 0);
86 RtlEnterCriticalSection(&ProcessData
->HandleTableLock
);
87 if (!CsrIsConsoleHandle(Handle
) || h
>= ProcessData
->HandleTableSize
88 || (*Object
= ProcessData
->HandleTable
[h
].Object
) == NULL
89 || ~ProcessData
->HandleTable
[h
].Access
& Access
)
91 DPRINT1("CsrGetObject returning invalid handle (%x)\n", Handle
);
92 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
93 return STATUS_INVALID_HANDLE
;
95 _InterlockedIncrement(&(*Object
)->ReferenceCount
);
96 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
97 // DbgPrint( "CsrGetObject returning\n" );
98 return STATUS_SUCCESS
;
104 CsrReleaseObjectByPointer(
110 if (_InterlockedDecrement(&Object
->ReferenceCount
) == 0)
112 for (DefIndex
= 0; DefIndex
< ObjectDefinitionsCount
; DefIndex
++)
114 if (Object
->Type
== ObjectDefinitions
[DefIndex
].Type
)
116 (ObjectDefinitions
[DefIndex
].CsrCleanupObjectProc
)(Object
);
117 return STATUS_SUCCESS
;
121 DPRINT1("CSR: Error: releasing unknown object type 0x%x", Object
->Type
);
124 return STATUS_SUCCESS
;
131 PCSRSS_PROCESS_DATA ProcessData
,
134 ULONG_PTR h
= (ULONG_PTR
)Handle
>> 2;
137 RtlEnterCriticalSection(&ProcessData
->HandleTableLock
);
138 if (h
>= ProcessData
->HandleTableSize
139 || (Object
= ProcessData
->HandleTable
[h
].Object
) == NULL
)
141 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
142 return STATUS_INVALID_HANDLE
;
144 ProcessData
->HandleTable
[h
].Object
= NULL
;
145 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
147 return CsrReleaseObjectByPointer(Object
);
153 PCSRSS_PROCESS_DATA ProcessData
,
162 RtlEnterCriticalSection(&ProcessData
->HandleTableLock
);
164 for (i
= 0; i
< ProcessData
->HandleTableSize
; i
++)
166 if (ProcessData
->HandleTable
[i
].Object
== NULL
)
171 if (i
>= ProcessData
->HandleTableSize
)
173 Block
= RtlAllocateHeap(CsrssApiHeap
,
175 (ProcessData
->HandleTableSize
+ 64) * sizeof(CSRSS_HANDLE
));
178 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
179 return(STATUS_UNSUCCESSFUL
);
182 ProcessData
->HandleTable
,
183 ProcessData
->HandleTableSize
* sizeof(CSRSS_HANDLE
));
184 Block
= _InterlockedExchangePointer((void* volatile)&ProcessData
->HandleTable
, Block
);
185 RtlFreeHeap( CsrssApiHeap
, 0, Block
);
186 ProcessData
->HandleTableSize
+= 64;
188 ProcessData
->HandleTable
[i
].Object
= Object
;
189 ProcessData
->HandleTable
[i
].Access
= Access
;
190 ProcessData
->HandleTable
[i
].Inheritable
= Inheritable
;
191 *Handle
= (HANDLE
)((i
<< 2) | 0x3);
192 _InterlockedIncrement( &Object
->ReferenceCount
);
193 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
194 return(STATUS_SUCCESS
);
199 CsrDuplicateHandleTable(
200 PCSRSS_PROCESS_DATA SourceProcessData
,
201 PCSRSS_PROCESS_DATA TargetProcessData
)
205 if (TargetProcessData
->HandleTableSize
)
207 return STATUS_INVALID_PARAMETER
;
210 RtlEnterCriticalSection(&SourceProcessData
->HandleTableLock
);
212 /* we are called from CreateProcessData, it isn't necessary to lock the target process data */
214 TargetProcessData
->HandleTable
= RtlAllocateHeap(CsrssApiHeap
,
216 SourceProcessData
->HandleTableSize
217 * sizeof(CSRSS_HANDLE
));
218 if (TargetProcessData
->HandleTable
== NULL
)
220 RtlLeaveCriticalSection(&SourceProcessData
->HandleTableLock
);
221 return(STATUS_UNSUCCESSFUL
);
223 TargetProcessData
->HandleTableSize
= SourceProcessData
->HandleTableSize
;
224 for (i
= 0; i
< SourceProcessData
->HandleTableSize
; i
++)
226 if (SourceProcessData
->HandleTable
[i
].Object
!= NULL
&&
227 SourceProcessData
->HandleTable
[i
].Inheritable
)
229 TargetProcessData
->HandleTable
[i
] = SourceProcessData
->HandleTable
[i
];
230 _InterlockedIncrement( &SourceProcessData
->HandleTable
[i
].Object
->ReferenceCount
);
233 RtlLeaveCriticalSection(&SourceProcessData
->HandleTableLock
);
234 return(STATUS_SUCCESS
);
240 PCSRSS_PROCESS_DATA ProcessData
,
243 ULONG_PTR h
= (ULONG_PTR
)Handle
>> 2;
245 if (h
>= ProcessData
->HandleTableSize
||
246 ProcessData
->HandleTable
[h
].Object
== NULL
)
248 return STATUS_INVALID_HANDLE
;
251 return STATUS_SUCCESS
;