Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

179 lines
4.2 KiB

/*
Copyright (c) Microsoft Corporation
*/
#include "stdinc.h"
#include "sxsp.h"
#include "windows.h"
#include "ntexapi.h"
#define HASH_ALGORITHM HASH_STRING_ALGORITHM_X65599
ULONG
SxspSetLastNTError(
NTSTATUS Status
);
BOOL
SxspGetAssemblyRootDirectoryHelper(
SIZE_T CchBuffer,
WCHAR Buffer[],
SIZE_T *CchWritten
)
{
BOOL fSuccess = FALSE;
const PCWSTR NtSystemRoot = USER_SHARED_DATA->NtSystemRoot;
const SIZE_T cchSystemRoot = wcslen(NtSystemRoot);
#define SLASH_WINSXS_SLASH L"\\WinSxS\\"
const SIZE_T cch = cchSystemRoot + (NUMBER_OF(SLASH_WINSXS_SLASH) - 1);
if ((CchBuffer == 0) && (CchWritten == NULL))
{
::SxspSetLastNTError(STATUS_INVALID_PARAMETER);
goto Exit;
}
if ((CchBuffer != 0) && (Buffer == NULL))
{
::SxspSetLastNTError(STATUS_INVALID_PARAMETER);
goto Exit;
}
if (cch > CchBuffer)
{
if (CchWritten != NULL)
{
*CchWritten = cch;
}
if (Buffer != NULL)
{
::SxspSetLastNTError(STATUS_BUFFER_TOO_SMALL);
}
else
{
fSuccess = TRUE;
}
goto Exit;
}
memcpy(Buffer, NtSystemRoot, cchSystemRoot * sizeof(WCHAR));
memcpy(Buffer + cchSystemRoot, SLASH_WINSXS_SLASH, sizeof(SLASH_WINSXS_SLASH));
fSuccess = TRUE;
Exit:
return fSuccess;
}
ULONG
SxspSetLastNTError(
NTSTATUS Status
)
{
ULONG dwErrorCode;
dwErrorCode = ::FusionpRtlNtStatusToDosError(Status);
::FusionpSetLastWin32Error(dwErrorCode);
return dwErrorCode;
}
BOOL
SxspHashString(
PCWSTR String,
SIZE_T cch,
PULONG HashValue,
bool CaseInsensitive
)
{
UNICODE_STRING s;
NTSTATUS Status = STATUS_SUCCESS;
s.MaximumLength = static_cast<USHORT>(cch * sizeof(WCHAR));
// check for overflow
if (s.MaximumLength != (cch * sizeof(WCHAR)))
{
::SxspSetLastNTError(STATUS_NAME_TOO_LONG);
return FALSE;
}
s.Length = s.MaximumLength;
s.Buffer = const_cast<PWSTR>(String);
Status = ::FusionpRtlHashUnicodeString(&s, CaseInsensitive, HASH_ALGORITHM, HashValue);
if (!NT_SUCCESS(Status))
::SxspSetLastNTError(Status);
return (NT_SUCCESS(Status));
}
ULONG
SxspGetHashAlgorithm(VOID)
{
return HASH_ALGORITHM;
}
BOOL
SxspCreateLocallyUniqueId(
OUT PSXSP_LOCALLY_UNIQUE_ID psxsLuid
)
{
FN_PROLOG_WIN32
static WORD s_wMilliseconds = 0;
static ULONG s_ulUniquification = 0;
SYSTEMTIME stLocalTime;
PARAMETER_CHECK(psxsLuid != NULL);
GetSystemTime(&stLocalTime);
IFW32FALSE_EXIT(SystemTimeToTzSpecificLocalTime(NULL, &stLocalTime, &psxsLuid->stTimeStamp));
if (psxsLuid->stTimeStamp.wMilliseconds == s_wMilliseconds)
{
s_ulUniquification = ::SxspInterlockedIncrement(&s_ulUniquification);
}
else
{
s_wMilliseconds = psxsLuid->stTimeStamp.wMilliseconds;
s_ulUniquification = 0;
}
psxsLuid->ulUniquifier = s_ulUniquification;
FN_EPILOG
}
#define CHARS_IN_TIMESTAMP (4 + (2*5) + 3 + 10) // 8 * 4 + 4
BOOL
SxspFormatLocallyUniqueId(
IN const SXSP_LOCALLY_UNIQUE_ID &rsxsLuid,
OUT CBaseStringBuffer &rbuffUidBuffer
)
{
FN_PROLOG_WIN32
if (rbuffUidBuffer.GetBufferCb() < CHARS_IN_TIMESTAMP)
{
IFW32FALSE_EXIT(rbuffUidBuffer.Win32ResizeBuffer(
CHARS_IN_TIMESTAMP,
eDoNotPreserveBufferContents));
}
else
{
//
// The caller may have previously grown the buffer
// larger because they are putting in the
// unique id followed by additional text. Don't
// change the size on them.
//
}
IFW32FALSE_EXIT(rbuffUidBuffer.Win32Format(
L"%04u%02u%02u%02u%02u%02u%03u.%u",
rsxsLuid.stTimeStamp.wYear,
rsxsLuid.stTimeStamp.wMonth,
rsxsLuid.stTimeStamp.wDay,
rsxsLuid.stTimeStamp.wHour,
rsxsLuid.stTimeStamp.wMinute,
rsxsLuid.stTimeStamp.wSecond,
rsxsLuid.stTimeStamp.wMilliseconds,
rsxsLuid.ulUniquifier));
FN_EPILOG
}