update for HEAD-2003091401
[reactos.git] / lib / kernel32 / synch / sem.c
1 /* $Id$
2  *
3  * COPYRIGHT:       See COPYING in the top level directory
4  * PROJECT:         ReactOS system libraries
5  * FILE:            lib/kernel32/synch/sem.c
6  * PURPOSE:         Semaphore functions
7  * PROGRAMMER:      Eric Kohl (ekohl@rz-online.de)
8  * UPDATE HISTORY:
9  *                  Created 01/20/2001
10  */
11
12 /* INCLUDES *****************************************************************/
13
14 #include <k32.h>
15
16 #define NDEBUG
17 #include <kernel32/kernel32.h>
18
19 /* FUNCTIONS ****************************************************************/
20
21 /*
22  * @implemented
23  */
24 HANDLE STDCALL
25 CreateSemaphoreA(LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,
26                  LONG lInitialCount,
27                  LONG lMaximumCount,
28                  LPCSTR lpName)
29 {
30    UNICODE_STRING NameU;
31    ANSI_STRING Name;
32    HANDLE Handle;
33
34    RtlInitAnsiString(&Name,
35                      (LPSTR)lpName);
36    RtlAnsiStringToUnicodeString(&NameU,
37                                 &Name,
38                                 TRUE);
39
40    Handle = CreateSemaphoreW(lpSemaphoreAttributes,
41                              lInitialCount,
42                              lMaximumCount,
43                              NameU.Buffer);
44
45    RtlFreeUnicodeString (&NameU);
46
47    return Handle;
48 }
49
50
51 /*
52  * @implemented
53  */
54 HANDLE STDCALL
55 CreateSemaphoreW(LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,
56                  LONG lInitialCount,
57                  LONG lMaximumCount,
58                  LPCWSTR lpName)
59 {
60    OBJECT_ATTRIBUTES ObjectAttributes;
61    NTSTATUS Status;
62    UNICODE_STRING NameString;
63    HANDLE SemaphoreHandle;
64
65    if (lpName)
66      {
67         NameString.Length = lstrlenW(lpName)*sizeof(WCHAR);
68      }
69    else
70      {
71         NameString.Length = 0;
72      }
73
74    NameString.Buffer = (WCHAR *)lpName;
75    NameString.MaximumLength = NameString.Length;
76
77    ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES);
78    ObjectAttributes.RootDirectory = hBaseDir;
79    ObjectAttributes.ObjectName = &NameString;
80    ObjectAttributes.Attributes = 0;
81    ObjectAttributes.SecurityDescriptor = NULL;
82    ObjectAttributes.SecurityQualityOfService = NULL;
83    if (lpSemaphoreAttributes != NULL)
84      {
85         ObjectAttributes.SecurityDescriptor = lpSemaphoreAttributes->lpSecurityDescriptor;
86         if (lpSemaphoreAttributes->bInheritHandle == TRUE)
87           {
88              ObjectAttributes.Attributes |= OBJ_INHERIT;
89           }
90      }
91
92    Status = NtCreateSemaphore(&SemaphoreHandle,
93                               SEMAPHORE_ALL_ACCESS,
94                               &ObjectAttributes,
95                               lInitialCount,
96                               lMaximumCount);
97    if (!NT_SUCCESS(Status))
98      {
99         SetLastErrorByStatus(Status);
100         return NULL;
101      }
102    return SemaphoreHandle;
103 }
104
105
106 /*
107  * @implemented
108  */
109 HANDLE STDCALL
110 OpenSemaphoreA(DWORD dwDesiredAccess,
111                WINBOOL bInheritHandle,
112                LPCSTR lpName)
113 {
114    OBJECT_ATTRIBUTES ObjectAttributes;
115    UNICODE_STRING NameU;
116    ANSI_STRING Name;
117    HANDLE Handle;
118    NTSTATUS Status;
119
120    if (lpName == NULL)
121      {
122         SetLastErrorByStatus(STATUS_INVALID_PARAMETER);
123         return NULL;
124      }
125
126    RtlInitAnsiString(&Name,
127                      (LPSTR)lpName);
128    RtlAnsiStringToUnicodeString(&NameU,
129                                 &Name,
130                                 TRUE);
131
132    ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES);
133    ObjectAttributes.RootDirectory = hBaseDir;
134    ObjectAttributes.ObjectName = &NameU;
135    ObjectAttributes.Attributes = 0;
136    ObjectAttributes.SecurityDescriptor = NULL;
137    ObjectAttributes.SecurityQualityOfService = NULL;
138    if (bInheritHandle == TRUE)
139      {
140         ObjectAttributes.Attributes |= OBJ_INHERIT;
141      }
142
143    Status = NtOpenSemaphore(&Handle,
144                             (ACCESS_MASK)dwDesiredAccess,
145                             &ObjectAttributes);
146
147    RtlFreeUnicodeString(&NameU);
148
149    if (!NT_SUCCESS(Status))
150      {
151         SetLastErrorByStatus(Status);
152         return NULL;
153      }
154
155    return Handle;
156 }
157
158
159 /*
160  * @implemented
161  */
162 HANDLE STDCALL
163 OpenSemaphoreW(DWORD dwDesiredAccess,
164                WINBOOL bInheritHandle,
165                LPCWSTR lpName)
166 {
167    OBJECT_ATTRIBUTES ObjectAttributes;
168    UNICODE_STRING Name;
169    HANDLE Handle;
170    NTSTATUS Status;
171
172    if (lpName == NULL)
173      {
174         SetLastErrorByStatus(STATUS_INVALID_PARAMETER);
175         return NULL;
176      }
177
178    RtlInitUnicodeString(&Name,
179                         (LPWSTR)lpName);
180
181    ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES);
182    ObjectAttributes.RootDirectory = hBaseDir;
183    ObjectAttributes.ObjectName = &Name;
184    ObjectAttributes.Attributes = 0;
185    ObjectAttributes.SecurityDescriptor = NULL;
186    ObjectAttributes.SecurityQualityOfService = NULL;
187    if (bInheritHandle == TRUE)
188      {
189         ObjectAttributes.Attributes |= OBJ_INHERIT;
190      }
191
192    Status = NtOpenSemaphore(&Handle,
193                             (ACCESS_MASK)dwDesiredAccess,
194                             &ObjectAttributes);
195    if (!NT_SUCCESS(Status))
196      {
197         SetLastErrorByStatus(Status);
198         return NULL;
199      }
200
201    return Handle;
202 }
203
204
205 /*
206  * @implemented
207  */
208 WINBOOL STDCALL
209 ReleaseSemaphore(HANDLE hSemaphore,
210                  LONG lReleaseCount,
211                  LPLONG lpPreviousCount)
212 {
213    NTSTATUS Status;
214
215    Status = NtReleaseSemaphore(hSemaphore,
216                                lReleaseCount,
217                                lpPreviousCount);
218    if (!NT_SUCCESS(Status))
219      {
220         SetLastErrorByStatus(Status);
221         return FALSE;
222      }
223
224    return TRUE;
225 }
226
227 /* EOF */