2 * PROJECT: ReactOS Service Control Manager
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: base/system/services/lock.c
5 * PURPOSE: Service lock functions
6 * COPYRIGHT: Copyright 2012 Hermès Bélusca
9 /* INCLUDES *****************************************************************/
17 /* GLOBALS *******************************************************************/
19 static PSTART_LOCK pServiceStartLock
= NULL
;
22 /* FUNCTIONS *****************************************************************/
25 * NOTE: IsServiceController is TRUE if locked by the
26 * Service Control Manager, and FALSE otherwise.
29 ScmAcquireServiceStartLock(IN BOOL IsServiceController
,
30 OUT LPSC_RPC_LOCK lpLock
)
33 DWORD dwError
= ERROR_SUCCESS
;
37 /* Lock the service database exclusively */
38 ScmLockDatabaseExclusive();
40 if (pServiceStartLock
!= NULL
)
42 dwError
= ERROR_SERVICE_DATABASE_LOCKED
;
46 /* Allocate a new lock for the database */
47 dwRequiredSize
= sizeof(START_LOCK
);
49 if (!IsServiceController
)
51 /* FIXME: dwRequiredSize += RtlLengthSid(UserSid <-- to be retrieved); */
54 pServiceStartLock
= HeapAlloc(GetProcessHeap(),
57 if (pServiceStartLock
== NULL
)
59 dwError
= ERROR_NOT_ENOUGH_MEMORY
;
63 pServiceStartLock
->Tag
= LOCK_TAG
;
64 pServiceStartLock
->TimeWhenLocked
= (DWORD
)time(NULL
);
66 /* FIXME: Retrieve the owner SID. Use IsServiceController. */
67 pServiceStartLock
->LockOwnerSid
= (PSID
)NULL
;
69 *lpLock
= (LPSC_RPC_LOCK
)pServiceStartLock
;
72 /* Unlock the service database */
80 ScmReleaseServiceStartLock(IN OUT LPSC_RPC_LOCK lpLock
)
82 PSTART_LOCK pStartLock
;
83 DWORD dwError
= ERROR_SUCCESS
;
86 return ERROR_INVALID_SERVICE_LOCK
;
88 pStartLock
= (PSTART_LOCK
)*lpLock
;
90 if (pStartLock
->Tag
!= LOCK_TAG
)
91 return ERROR_INVALID_SERVICE_LOCK
;
93 /* Lock the service database exclusively */
94 ScmLockDatabaseExclusive();
96 /* Release the lock handle */
97 if ((pStartLock
== pServiceStartLock
) &&
98 (pServiceStartLock
!= NULL
))
100 HeapFree(GetProcessHeap(), 0, pServiceStartLock
);
101 pServiceStartLock
= NULL
;
104 dwError
= ERROR_SUCCESS
;
108 dwError
= ERROR_INVALID_SERVICE_LOCK
;
111 /* Unlock the service database */
119 * Helper functions for RQueryServiceLockStatusW() and
120 * RQueryServiceLockStatusA().
121 * We suppose that lpLockStatus points to a valid
125 ScmQueryServiceLockStatusW(OUT LPQUERY_SERVICE_LOCK_STATUSW lpLockStatus
)
127 /* Lock the service database shared */
128 ScmLockDatabaseShared();
130 if (pServiceStartLock
!= NULL
)
132 lpLockStatus
->fIsLocked
= TRUE
;
134 /* FIXME: Retrieve the owner name. */
135 lpLockStatus
->lpLockOwner
= NULL
;
137 lpLockStatus
->dwLockDuration
= (DWORD
)time(NULL
) - pServiceStartLock
->TimeWhenLocked
;
141 lpLockStatus
->fIsLocked
= FALSE
;
143 wcscpy((LPWSTR
)(lpLockStatus
+ 1), L
"");
144 lpLockStatus
->lpLockOwner
= (LPWSTR
)(ULONG_PTR
)sizeof(QUERY_SERVICE_LOCK_STATUSW
);
146 lpLockStatus
->dwLockDuration
= 0;
149 /* Unlock the service database */
157 ScmQueryServiceLockStatusA(OUT LPQUERY_SERVICE_LOCK_STATUSA lpLockStatus
)
159 /* Lock the service database shared */
160 ScmLockDatabaseShared();
162 if (pServiceStartLock
!= NULL
)
164 lpLockStatus
->fIsLocked
= TRUE
;
166 /* FIXME: Retrieve the owner name. */
167 lpLockStatus
->lpLockOwner
= NULL
;
169 lpLockStatus
->dwLockDuration
= (DWORD
)time(NULL
) - pServiceStartLock
->TimeWhenLocked
;
173 lpLockStatus
->fIsLocked
= FALSE
;
175 strcpy((LPSTR
)(lpLockStatus
+ 1), "");
176 lpLockStatus
->lpLockOwner
= (LPSTR
)(ULONG_PTR
)sizeof(QUERY_SERVICE_LOCK_STATUSA
);
178 lpLockStatus
->dwLockDuration
= 0;
181 /* Unlock the service database */