strip whitespace from end of lines
[reactos.git] / reactos / ntoskrnl / ps / cid.c
1 /* $Id$
2 *
3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS kernel
5 * FILE: ntoskrnl/ps/cid.c
6 * PURPOSE: Client ID (CID) management
7 *
8 * PROGRAMMERS: Thomas Weidenmueller <w3seek@reactos.com>
9 */
10
11 /* INCLUDES ******************************************************************/
12
13 #include <ntoskrnl.h>
14 #define NDEBUG
15 #include <internal/debug.h>
16
17 /* GLOBALS ******************************************************************/
18
19 PHANDLE_TABLE PspCidTable = NULL;
20
21 #define TAG_CIDOBJECT TAG('C', 'I', 'D', 'O')
22
23 #define CID_FLAG_PROCESS 0x1
24 #define CID_FLAG_THREAD 0x2
25 #define CID_FLAGS_MASK (CID_FLAG_PROCESS | CID_FLAG_THREAD)
26
27 /* FUNCTIONS *****************************************************************/
28
29 VOID INIT_FUNCTION
30 PsInitClientIDManagment(VOID)
31 {
32 PspCidTable = ExCreateHandleTable(NULL);
33 ASSERT(PspCidTable);
34 }
35
36 NTSTATUS
37 PsCreateCidHandle(PVOID Object, POBJECT_TYPE ObjectType, PHANDLE Handle)
38 {
39 HANDLE_TABLE_ENTRY NewEntry;
40 LONG ExHandle;
41
42 PAGED_CODE();
43
44 NewEntry.u1.Object = Object;
45 if(ObjectType == PsThreadType)
46 NewEntry.u2.GrantedAccess = CID_FLAG_THREAD;
47 else if(ObjectType == PsProcessType)
48 NewEntry.u2.GrantedAccess = CID_FLAG_PROCESS;
49 else
50 {
51 DPRINT1("Can't create CID handles for %wZ objects\n", &ObjectType->TypeName);
52 KEBUGCHECK(0);
53 }
54
55 ExHandle = ExCreateHandle(PspCidTable,
56 &NewEntry);
57 if(ExHandle != EX_INVALID_HANDLE)
58 {
59 *Handle = EX_HANDLE_TO_HANDLE(ExHandle);
60 return STATUS_SUCCESS;
61 }
62
63 return STATUS_UNSUCCESSFUL;
64 }
65
66 NTSTATUS
67 PsDeleteCidHandle(HANDLE CidHandle, POBJECT_TYPE ObjectType)
68 {
69 PHANDLE_TABLE_ENTRY Entry;
70 LONG ExHandle = HANDLE_TO_EX_HANDLE(CidHandle);
71
72 PAGED_CODE();
73
74 KeEnterCriticalRegion();
75
76 Entry = ExMapHandleToPointer(PspCidTable,
77 ExHandle);
78 if(Entry != NULL)
79 {
80 if((ObjectType == PsThreadType && ((Entry->u2.GrantedAccess & CID_FLAGS_MASK) == CID_FLAG_THREAD)) ||
81 (ObjectType == PsProcessType && ((Entry->u2.GrantedAccess & CID_FLAGS_MASK) == CID_FLAG_PROCESS)))
82 {
83 ExDestroyHandleByEntry(PspCidTable,
84 Entry,
85 ExHandle);
86 KeLeaveCriticalRegion();
87 return STATUS_SUCCESS;
88 }
89 else
90 {
91 ExUnlockHandleTableEntry(PspCidTable,
92 Entry);
93 KeLeaveCriticalRegion();
94 return STATUS_OBJECT_TYPE_MISMATCH;
95 }
96 }
97 KeLeaveCriticalRegion();
98 return STATUS_INVALID_HANDLE;
99 }
100
101 PHANDLE_TABLE_ENTRY
102 PsLookupCidHandle(HANDLE CidHandle, POBJECT_TYPE ObjectType, PVOID *Object)
103 {
104 PHANDLE_TABLE_ENTRY Entry;
105
106 PAGED_CODE();
107
108 KeEnterCriticalRegion();
109
110 Entry = ExMapHandleToPointer(PspCidTable,
111 HANDLE_TO_EX_HANDLE(CidHandle));
112 if(Entry != NULL)
113 {
114 if((ObjectType == PsProcessType && ((Entry->u2.GrantedAccess & CID_FLAGS_MASK) == CID_FLAG_PROCESS)) ||
115 (ObjectType == PsThreadType && ((Entry->u2.GrantedAccess & CID_FLAGS_MASK) == CID_FLAG_THREAD)))
116 {
117 *Object = Entry->u1.Object;
118 return Entry;
119 }
120 else
121 {
122 DPRINT1("CID Obj type mismatch handle 0x%x %wZ vs 0x%x\n", CidHandle,
123 &ObjectType->TypeName, Entry->u2.GrantedAccess);
124 ExUnlockHandleTableEntry(PspCidTable,
125 Entry);
126 }
127 }
128
129 KeLeaveCriticalRegion();
130
131 return NULL;
132 }
133
134 /*
135 * @implemented
136 */
137 NTSTATUS STDCALL
138 PsLookupProcessThreadByCid(IN PCLIENT_ID Cid,
139 OUT PEPROCESS *Process OPTIONAL,
140 OUT PETHREAD *Thread)
141 {
142 PHANDLE_TABLE_ENTRY CidEntry;
143 PETHREAD FoundThread;
144
145 PAGED_CODE();
146
147 ASSERT(Thread);
148 ASSERT(Cid);
149
150 CidEntry = PsLookupCidHandle(Cid->UniqueThread, PsThreadType, (PVOID*)&FoundThread);
151 if(CidEntry != NULL)
152 {
153 ObReferenceObject(FoundThread);
154
155 PsUnlockCidHandle(CidEntry);
156
157 if(Process != NULL)
158 {
159 *Process = FoundThread->ThreadsProcess;
160 }
161 *Thread = FoundThread;
162 return STATUS_SUCCESS;
163 }
164
165 return STATUS_INVALID_PARAMETER;
166 }
167
168
169 /*
170 * @implemented
171 */
172 NTSTATUS STDCALL
173 PsLookupThreadByThreadId(IN HANDLE ThreadId,
174 OUT PETHREAD *Thread)
175 {
176 PHANDLE_TABLE_ENTRY CidEntry;
177 PETHREAD FoundThread;
178
179 PAGED_CODE();
180
181 ASSERT(Thread);
182
183 CidEntry = PsLookupCidHandle(ThreadId, PsThreadType, (PVOID*)&FoundThread);
184 if(CidEntry != NULL)
185 {
186 ObReferenceObject(FoundThread);
187
188 PsUnlockCidHandle(CidEntry);
189
190 *Thread = FoundThread;
191 return STATUS_SUCCESS;
192 }
193
194 return STATUS_INVALID_PARAMETER;
195 }
196
197 VOID
198 PsUnlockCidHandle(PHANDLE_TABLE_ENTRY CidEntry)
199 {
200 PAGED_CODE();
201
202 ExUnlockHandleTableEntry(PspCidTable,
203 CidEntry);
204 KeLeaveCriticalRegion();
205 }
206
207 /* EOF */