From: Paul Gofman pgofman@codeweavers.com
--- dlls/kernelbase/kernelbase.spec | 1 + dlls/kernelbase/security.c | 46 +++++++++++++++++++++++++++++++++ include/winbase.h | 1 + 3 files changed, 48 insertions(+)
diff --git a/dlls/kernelbase/kernelbase.spec b/dlls/kernelbase/kernelbase.spec index 104dd99d619..9c096d1b003 100644 --- a/dlls/kernelbase/kernelbase.spec +++ b/dlls/kernelbase/kernelbase.spec @@ -241,6 +241,7 @@ @ stdcall CtrlRoutine(ptr) # @ stub CveEventWrite @ stdcall DeactivateActCtx(long long) +@ stdcall DeriveCapabilitySidsFromName(ptr ptr ptr ptr ptr) @ stdcall DebugActiveProcess(long) @ stdcall DebugActiveProcessStop(long) @ stdcall DebugBreak() diff --git a/dlls/kernelbase/security.c b/dlls/kernelbase/security.c index 4434a59a53a..c432d8eacd3 100644 --- a/dlls/kernelbase/security.c +++ b/dlls/kernelbase/security.c @@ -1512,3 +1512,49 @@ BOOL WINAPI SetCachedSigningLevel( PHANDLE source, ULONG count, ULONG flags, HAN FIXME( "%p %lu %lu %p - stub\n", source, count, flags, file ); return TRUE; } + +/****************************************************************************** + * DeriveCapabilitySidsFromName (kernelbase.@) + */ +BOOL WINAPI DeriveCapabilitySidsFromName( const WCHAR *cap_name, PSID **cap_group_sids, DWORD *cap_group_sid_count, + PSID **cap_sids, DWORD *cap_sid_count ) +{ + NTSTATUS status = STATUS_NO_MEMORY; + UNICODE_STRING name_us; + DWORD size; + + TRACE( "cap_name %s, cap_group_sids %p, cap_group_sid_count %p, cap_sids %p, cap_sid_count %p.\n", + debugstr_w(cap_name), cap_group_sids, cap_group_sid_count, cap_sids, cap_sid_count ); + + *cap_group_sid_count = 1; + *cap_sid_count = 1; + *cap_group_sids = NULL; + *cap_sids = NULL; + + if (!(*cap_group_sids = RtlAllocateHeap( GetProcessHeap(), 0, *cap_group_sid_count * sizeof(**cap_group_sids) ))) + goto done; + if (!(*cap_sids = RtlAllocateHeap( GetProcessHeap(), 0, *cap_sid_count * sizeof(**cap_sids) ))) + goto done; + + /* There is no obvious way to query returned subauthority count for RtlDeriveCapabilitySidsFromName, + * so let's reserve a bit more. */ + size = RtlLengthRequiredSid( 16 ); + if (!(**cap_group_sids = RtlAllocateHeap( GetProcessHeap(), 0, size ))) goto done; + if (!(**cap_sids = RtlAllocateHeap( GetProcessHeap(), 0, size ))) goto done; + RtlInitUnicodeString( &name_us, cap_name ); + status = RtlDeriveCapabilitySidsFromName( &name_us, **cap_group_sids, **cap_sids ); + +done: + if (!status) return TRUE; + if (*cap_group_sids) + { + RtlFreeHeap( GetProcessHeap(), 0, **cap_group_sids ); + RtlFreeHeap( GetProcessHeap(), 0, *cap_group_sids ); + } + if (*cap_sids) + { + RtlFreeHeap( GetProcessHeap(), 0, **cap_sids ); + RtlFreeHeap( GetProcessHeap(), 0, *cap_sids ); + } + return set_ntstatus( status ); +} diff --git a/include/winbase.h b/include/winbase.h index 135c2603a70..f656c302317 100644 --- a/include/winbase.h +++ b/include/winbase.h @@ -2002,6 +2002,7 @@ WINBASEAPI BOOL WINAPI DeleteVolumeMountPointW(LPCWSTR); #define DeleteVolumeMountPoint WINELIB_NAME_AW(DeleteVolumeMountPoint) WINBASEAPI BOOL WINAPI DequeueUmsCompletionListItems(void *, DWORD, PUMS_CONTEXT *); WINADVAPI BOOL WINAPI DeregisterEventSource(HANDLE); +WINADVAPI BOOL WINAPI DeriveCapabilitySidsFromName(const WCHAR *, PSID **, DWORD *, PSID **, DWORD *); WINADVAPI BOOL WINAPI DestroyPrivateObjectSecurity(PSECURITY_DESCRIPTOR*); WINBASEAPI BOOL WINAPI DeviceIoControl(HANDLE,DWORD,LPVOID,DWORD,LPVOID,DWORD,LPDWORD,LPOVERLAPPED); WINBASEAPI BOOL WINAPI DisableThreadLibraryCalls(HMODULE);