summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRama Krishnan Raghupathy <ramarag@microsoft.com>2016-02-18 18:21:18 -0800
committerRama Krishnan Raghupathy <ramarag@microsoft.com>2016-02-19 18:09:11 -0800
commitf98fb85e72d0f24c58d9e54b8b3bff2c67f985fb (patch)
treea532e7803fbbe420807eb7d9390108554b02c46d
parent01ffa08a2e4748e9826956ea961eacb227b6ee87 (diff)
downloadcoreclr-f98fb85e72d0f24c58d9e54b8b3bff2c67f985fb.tar.gz
coreclr-f98fb85e72d0f24c58d9e54b8b3bff2c67f985fb.tar.bz2
coreclr-f98fb85e72d0f24c58d9e54b8b3bff2c67f985fb.zip
This Change Adds initial Support for LongFiles in the VM,
They are: 1. Wrappers for OS APIs which take or return PATHS 2. Fixing the usage of following Api's: GetEnvironmentVariableW SearchPathW GetShortPathNameW GetLongPathNameW GetModuleFileName Work remaining: Remove fixed size buffers in the VM
-rw-r--r--src/classlibnative/bcltype/system.cpp37
-rw-r--r--src/debug/di/cordb.cpp6
-rw-r--r--src/debug/di/module.cpp3
-rw-r--r--src/debug/di/shimprocess.cpp27
-rw-r--r--src/debug/ee/debugger.cpp16
-rw-r--r--src/dlls/mscoree/delayload.cpp8
-rw-r--r--src/dlls/mscoree/mscoree.cpp318
-rw-r--r--src/dlls/mscorpe/ceefilegenwriter.cpp71
-rw-r--r--src/dlls/mscorpe/pewriter.cpp8
-rw-r--r--src/ilasm/grammar_after.cpp26
-rw-r--r--src/ilasm/main.cpp10
-rw-r--r--src/inc/corpriv.h14
-rw-r--r--src/inc/longfilepathwrappers.h277
-rw-r--r--src/inc/sstring.h5
-rw-r--r--src/inc/sstring.inl24
-rw-r--r--src/inc/utilcode.h11
-rw-r--r--src/inc/winwrap.h663
-rw-r--r--src/md/compiler/disp.cpp20
-rw-r--r--src/md/compiler/mdutil.cpp117
-rw-r--r--src/md/compiler/mdutil.h7
-rw-r--r--src/pal/inc/pal.h13
-rw-r--r--src/pal/src/loader/module.cpp1
-rw-r--r--src/strongname/api/strongnamecoreclr.cpp6
-rw-r--r--src/tools/crossgen/crossgen.cpp37
-rw-r--r--src/utilcode/CMakeLists.txt1
-rw-r--r--src/utilcode/UtilCode.vcproj4
-rw-r--r--src/utilcode/UtilCode.vcxproj3
-rw-r--r--src/utilcode/ccomprc.cpp130
-rw-r--r--src/utilcode/debug.cpp6
-rw-r--r--src/utilcode/jitperf.cpp7
-rw-r--r--src/utilcode/longfilepathwrappers.cpp1464
-rw-r--r--src/utilcode/makepath.cpp88
-rw-r--r--src/utilcode/perflog.cpp9
-rw-r--r--src/utilcode/regutil.cpp55
-rw-r--r--src/utilcode/safewrap.cpp16
-rw-r--r--src/utilcode/stacktrace.cpp59
-rw-r--r--src/utilcode/util.cpp89
-rw-r--r--src/utilcode/util_nodependencies.cpp43
-rw-r--r--src/utilcode/utilcode.settings.targets1
-rw-r--r--src/utilcode/utilmessagebox.cpp7
-rw-r--r--src/vm/appdomain.cpp40
-rw-r--r--src/vm/assemblynative.cpp8
-rw-r--r--src/vm/ceemain.cpp89
-rw-r--r--src/vm/codeman.cpp7
-rw-r--r--src/vm/corhost.cpp7
-rw-r--r--src/vm/dwbucketmanager.hpp15
-rw-r--r--src/vm/dwreport.cpp208
-rw-r--r--src/vm/dwreport.h2
-rw-r--r--src/vm/eeconfig.cpp68
-rw-r--r--src/vm/eepolicy.cpp6
-rw-r--r--src/vm/eventreporter.cpp10
-rw-r--r--src/vm/eventtrace.cpp16
-rw-r--r--src/vm/mdaassistants.cpp10
-rw-r--r--src/vm/peimage.cpp11
-rw-r--r--src/vm/peimage.inl46
-rw-r--r--src/vm/peimagelayout.cpp6
-rw-r--r--src/vm/securitypolicy.cpp113
-rw-r--r--src/vm/securitypolicy.h2
-rw-r--r--src/zap/zapper.cpp11
59 files changed, 3062 insertions, 1320 deletions
diff --git a/src/classlibnative/bcltype/system.cpp b/src/classlibnative/bcltype/system.cpp
index c950039fad..e902734b23 100644
--- a/src/classlibnative/bcltype/system.cpp
+++ b/src/classlibnative/bcltype/system.cpp
@@ -218,34 +218,19 @@ FCIMPL1(Object*, SystemNative::_GetEnvironmentVariable, StringObject* strVarUNSA
HELPER_METHOD_FRAME_BEGIN_RET_2(refRetVal, strVar);
- // We loop round getting the length of the env var and then trying to copy
- // the value into a managed string. Usually we'll go through this loop
- // precisely once, but the caution is ncessary in case the variable mutates
- // beneath us.
- int len, newLen;
+ int len;
// Get the length of the environment variable.
- WCHAR dummy; // prefix complains if pass a null ptr in, so rely on the final length parm instead
- len = WszGetEnvironmentVariable(strVar->GetBuffer(), &dummy, 0);
+ PathString envPath; // prefix complains if pass a null ptr in, so rely on the final length parm instead
+ len = WszGetEnvironmentVariable(strVar->GetBuffer(), envPath);
- while (len != 0)
+ if (len != 0)
{
// Allocate the string.
refRetVal = StringObject::NewString(len);
-
- // Get the value.
- newLen = WszGetEnvironmentVariable(strVar->GetBuffer(), refRetVal->GetBuffer(), len);
- if (newLen != (len - 1))
- {
- // The envvar changed, need to do this again. Let GC collect the
- // string we just allocated.
- refRetVal = NULL;
-
- // Go back and try again.
- len = newLen;
- }
- else
- break;
+
+ wcscpy_s(refRetVal->GetBuffer(), len + 1, envPath);
+
}
HELPER_METHOD_FRAME_END();
@@ -297,15 +282,15 @@ FCIMPL0(StringObject*, SystemNative::_GetModuleFileName)
}
else
{
- SString wszFilePathString;
+ PathString wszFilePathString;
- WCHAR * wszFile = wszFilePathString.OpenUnicodeBuffer(MAX_LONGPATH);
- DWORD lgth = WszGetModuleFileName(NULL, wszFile, MAX_LONGPATH);
+
+ DWORD lgth = WszGetModuleFileName(NULL, wszFilePathString);
if (!lgth)
{
COMPlusThrowWin32();
}
- wszFilePathString.CloseBuffer(lgth);
+
refRetVal = StringObject::NewString(wszFilePathString.GetUnicode());
}
diff --git a/src/debug/di/cordb.cpp b/src/debug/di/cordb.cpp
index 3a4fdff901..497225fd67 100644
--- a/src/debug/di/cordb.cpp
+++ b/src/debug/di/cordb.cpp
@@ -201,11 +201,11 @@ BOOL WINAPI DbgDllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
#if defined(LOGGING)
{
- WCHAR rcFile[_MAX_PATH];
- WszGetModuleFileName(hInstance, rcFile, NumItems(rcFile));
+ PathString rcFile;
+ WszGetModuleFileName(hInstance, rcFile);
LOG((LF_CORDB, LL_INFO10000,
"DI::DbgDllMain: load right side support from file '%s'\n",
- rcFile));
+ rcFile.GetUnicode()));
}
#endif
diff --git a/src/debug/di/module.cpp b/src/debug/di/module.cpp
index 700a362c94..78c7599455 100644
--- a/src/debug/di/module.cpp
+++ b/src/debug/di/module.cpp
@@ -2568,8 +2568,9 @@ HRESULT CordbModule::CreateReaderForInMemorySymbols(REFIID riid, void** ppObj)
#ifndef FEATURE_PAL
// PDB format - use diasymreader.dll with COM activation
InlineSString<_MAX_PATH> ssBuf;
+ IfFailThrow(GetHModuleDirectory(GetModuleInst(), ssBuf));
IfFailThrow(FakeCoCreateInstanceEx(CLSID_CorSymBinder_SxS,
- GetHModuleDirectory(GetModuleInst(), ssBuf).GetUnicode(),
+ ssBuf.GetUnicode(),
IID_ISymUnmanagedBinder,
(void**)&pBinder,
NULL));
diff --git a/src/debug/di/shimprocess.cpp b/src/debug/di/shimprocess.cpp
index f15ab3fff6..a6fc15407e 100644
--- a/src/debug/di/shimprocess.cpp
+++ b/src/debug/di/shimprocess.cpp
@@ -1823,50 +1823,41 @@ HRESULT ShimProcess::FindLoadedCLR(CORDB_ADDRESS * pClrInstanceId)
HMODULE ShimProcess::GetDacModule()
{
HModuleHolder hDacDll;
- WCHAR wszAccessDllPath[MAX_LONGPATH];
+ PathString wszAccessDllPath;
#ifdef FEATURE_PAL
- if (!PAL_GetPALDirectoryW(wszAccessDllPath, _countof(wszAccessDllPath)))
+ if (!PAL_GetPALDirectoryWrapper(wszAccessDllPath))
{
ThrowLastError();
}
- wcscat_s(wszAccessDllPath, _countof(wszAccessDllPath), MAKEDLLNAME_W(W("mscordaccore")));
+ PCWSTR eeFlavor = MAKEDLLNAME_W(W("mscordaccore"));
#else
//
// Load the access DLL from the same directory as the the current CLR Debugging Services DLL.
//
- if (!WszGetModuleFileName(GetModuleInst(), wszAccessDllPath, NumItems(wszAccessDllPath)))
+ if (!WszGetModuleFileName(GetModuleInst(), wszAccessDllPath))
{
ThrowLastError();
}
- PWSTR pPathTail = wcsrchr(wszAccessDllPath, DIRECTORY_SEPARATOR_CHAR_W);
- if (!pPathTail)
+ if (!SUCCEEDED(CopySystemDirectory(wszAccessDllPath, wszAccessDllPath)))
{
ThrowHR(E_INVALIDARG);
}
- pPathTail++;
// Dac Dll is named:
// mscordaccore.dll <-- coreclr
// mscordacwks.dll <-- desktop
PCWSTR eeFlavor =
#if defined(FEATURE_MAIN_CLR_MODULE_USES_CORE_NAME)
- W("core");
+ W("mscordaccore.dll");
#else
- W("wks");
+ W("mscordacwks.dll");
#endif
-
- if (_snwprintf_s(pPathTail,
- _countof(wszAccessDllPath) + (wszAccessDllPath - pPathTail),
- NumItems(wszAccessDllPath) - (pPathTail - wszAccessDllPath),
- MAKEDLLNAME_W(W("mscordac%s")),
- eeFlavor) <= 0)
- {
- ThrowHR(E_INVALIDARG);
- }
+
#endif // FEATURE_PAL
+ wszAccessDllPath.Append(eeFlavor);
hDacDll.Assign(WszLoadLibrary(wszAccessDllPath));
if (!hDacDll)
diff --git a/src/debug/ee/debugger.cpp b/src/debug/ee/debugger.cpp
index 5905965c8b..c063eb829f 100644
--- a/src/debug/ee/debugger.cpp
+++ b/src/debug/ee/debugger.cpp
@@ -2244,9 +2244,9 @@ HRESULT Debugger::StartupPhase2(Thread * pThread)
if (!CORDebuggerAttached())
{
#define DBG_ATTACH_ON_STARTUP_ENV_VAR W("COMPlus_DbgAttachOnStartup")
-
+ PathString temp;
// We explicitly just check the env because we don't want a switch this invasive to be global.
- DWORD fAttach = WszGetEnvironmentVariable(DBG_ATTACH_ON_STARTUP_ENV_VAR, NULL, 0) > 0;
+ DWORD fAttach = WszGetEnvironmentVariable(DBG_ATTACH_ON_STARTUP_ENV_VAR, temp) > 0;
if (fAttach)
{
@@ -15166,8 +15166,7 @@ HRESULT Debugger::InitAppDomainIPC(void)
} hEnsureCleanup(this);
DWORD dwStrLen = 0;
- SString szExeNamePathString;
- WCHAR * szExeName = szExeNamePathString.OpenUnicodeBuffer(MAX_LONGPATH);
+ SString szExeName;
int i;
// all fields in the object can be zero initialized.
@@ -15216,15 +15215,14 @@ HRESULT Debugger::InitAppDomainIPC(void)
// also initialize the process name
dwStrLen = WszGetModuleFileName(NULL,
- szExeName,
- MAX_LONGPATH);
+ szExeName);
- szExeNamePathString.CloseBuffer(dwStrLen);
+
// If we couldn't get the name, then use a nice default.
if (dwStrLen == 0)
{
- wcscpy_s(szExeName, COUNTOF(szExeName), W("<NoProcessName>"));
- dwStrLen = (DWORD)wcslen(szExeName);
+ szExeName.Set(W("<NoProcessName>"));
+ dwStrLen = szExeName.GetCount();
}
// If we got the name, copy it into a buffer. dwStrLen is the
diff --git a/src/dlls/mscoree/delayload.cpp b/src/dlls/mscoree/delayload.cpp
index 40fb24707b..d74f58b444 100644
--- a/src/dlls/mscoree/delayload.cpp
+++ b/src/dlls/mscoree/delayload.cpp
@@ -376,16 +376,16 @@ FARPROC __stdcall CorDelayLoadHook( // Always 0.
// If we've not yet looked at our environment, then do so.
if (!bInit)
{
- WCHAR rcBreak[16];
+ PathString rcBreak;
// set DelayLoadBreak=[0|1]
- if (WszGetEnvironmentVariable(W("DelayLoadBreak"), rcBreak, NumItems(rcBreak)))
+ if (WszGetEnvironmentVariable(W("DelayLoadBreak"), rcBreak))
{
// "1" means to break hard and display errors.
- if (*rcBreak == '1')
+ if (rcBreak[0] == '1')
bBreak = 1;
// "2" means no break, but display errors.
- else if (*rcBreak == '2')
+ else if (rcBreak[0] == '2')
bBreak = 2;
else
bBreak = false;
diff --git a/src/dlls/mscoree/mscoree.cpp b/src/dlls/mscoree/mscoree.cpp
index 11863e936e..d42733ad35 100644
--- a/src/dlls/mscoree/mscoree.cpp
+++ b/src/dlls/mscoree/mscoree.cpp
@@ -14,7 +14,7 @@
#include <mscoree.h>
#include "shimload.h"
#include "metadataexports.h"
-
+#include "ex.h"
#if !defined(FEATURE_CORECLR)
#include "corsym.h"
#endif
@@ -121,7 +121,7 @@ extern "C" BOOL WINAPI CoreDllMain(HANDLE hInstance, DWORD dwReason, LPVOID lpRe
CoreClrCallbacks cccallbacks;
cccallbacks.m_hmodCoreCLR = (HINSTANCE)hInstance;
cccallbacks.m_pfnIEE = IEE;
- cccallbacks.m_pfnGetCORSystemDirectory = GetCORSystemDirectoryInternal;
+ cccallbacks.m_pfnGetCORSystemDirectory = GetCORSystemDirectoryInternaL;
cccallbacks.m_pfnGetCLRFunction = GetCLRFunction;
InitUtilcode(cccallbacks);
@@ -284,13 +284,18 @@ STDAPI InternalDllGetClassObject(
{
EX_TRY
{
- // PDB format - use diasymreader.dll with COM activation
- InlineSString<_MAX_PATH> ssBuf;
- hr = FakeCoCallDllGetClassObject(rclsid,
- GetHModuleDirectory(GetModuleInst(), ssBuf).GetUnicode(),
- riid,
- ppv,
- NULL);
+
+ // PDB format - use diasymreader.dll with COM activation
+ InlineSString<_MAX_PATH> ssBuf;
+ if (SUCCEEDED(GetHModuleDirectory(GetModuleInst(), ssBuf)))
+ {
+ hr = FakeCoCallDllGetClassObject(rclsid,
+ ssBuf,
+ riid,
+ ppv,
+ NULL
+ );
+ }
}
EX_CATCH_HRESULT(hr);
}
@@ -719,116 +724,6 @@ STDAPI LoadStringRCEx(
#endif // CROSSGEN_COMPILE
-#if defined(FEATURE_CORECLR) || defined(CROSSGEN_COMPILE)
-
-extern HINSTANCE g_pMSCorEE;
-
-#ifndef FEATURE_PAL
-
-//
-// Returns path name from a file name. The path name will be (null-terminated, incl. the last '\' if present).
-// Example: For input "C:\Windows\System.dll" returns "C:\Windows\".
-// Warning: The input file name string might be destroyed.
-//
-// Arguments:
-// pFileName - [in] Null-terminated file name. Will be destroyed (an additional null-terminator might be
-// written into the string).
-// pBuffer - [out] buffer allocated by caller of size cchBuffer.
-// cchBuffer - Size of pBuffer in characters.
-// pdwLength - [out] Size of the path name in characters (incl. null-terminator). Will be filled even if
-// ERROR_INSUFFICIENT_BUFFER is returned.
-//
-// Return Value:
-// S_OK - Output buffer contains path name.
-// HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER) - *pdwLength contains required size of the buffer in
-// characters.
-// other errors - If input parameters are incorrect (NULL).
-//
-static
-HRESULT CopySystemDirectory(__in WCHAR *pFileName,
- __out_ecount_z_opt(cchBuffer) LPWSTR pBuffer,
- DWORD cchBuffer,
- __out DWORD *pdwLength)
-{
- if ((pBuffer != NULL) && (cchBuffer > 0))
- { // Initialize the output for case the function fails
- *pBuffer = W('\0');
- }
-
- if (pdwLength == NULL)
- return E_POINTER;
-
- HRESULT hr = S_OK;
- if (pFileName == NULL)
- return HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND);
-
- SIZE_T dwFileNameLength = wcslen(pFileName);
- LPWSTR pSeparator = wcsrchr(pFileName, W('\\'));
- if (pSeparator != NULL)
- {
- dwFileNameLength = (DWORD)(pSeparator - pFileName + 1);
- pFileName[dwFileNameLength] = W('\0');
- }
-
- dwFileNameLength++; // Add back in the null
- *pdwLength = (DWORD)dwFileNameLength;
- if ((dwFileNameLength > cchBuffer) || (pBuffer == NULL))
- {
- hr = HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
- }
- else
- {
- CopyMemory(pBuffer,
- pFileName,
- dwFileNameLength * sizeof(WCHAR));
- }
- return hr;
-}
-
-BOOL PAL_GetPALDirectory(__out_ecount(cchBuffer) LPWSTR pbuffer,
- DWORD cchBuffer)
-{
-
- HRESULT hr = S_OK;
-
- WCHAR * pPath = new (nothrow) WCHAR[MAX_LONGPATH];
- if (pPath == NULL)
- {
- return FALSE;
- }
-
- DWORD dwPath = MAX_LONGPATH;
-
-#ifndef CROSSGEN_COMPILE
- _ASSERTE(g_pMSCorEE != NULL);
-#endif
-
- dwPath = WszGetModuleFileName(g_pMSCorEE, pPath, dwPath);
-
- if(dwPath == 0)
- {
- hr = HRESULT_FROM_GetLastErrorNA();
- }
- else
- {
- DWORD dwLength;
- hr = CopySystemDirectory(pPath, pbuffer, cchBuffer, &dwLength);
- }
-
- delete [] pPath;
-
- return (hr == S_OK);
-}
-
-BOOL PAL_GetPALDirectoryW(__out_ecount(cchBuffer) LPWSTR pbuffer,
- DWORD cchBuffer)
-{
- return PAL_GetPALDirectory(pbuffer, cchBuffer);
-}
-
-#endif // FEATURE_PAL
-
-#endif // FEATURE_CORECLR || CROSSGEN_COMPILE
// Note that there are currently two callers of this function: code:CCompRC.LoadLibrary
@@ -838,7 +733,7 @@ STDAPI GetRequestedRuntimeInfoInternal(LPCWSTR pExe,
LPCWSTR pConfigurationFile,
DWORD startupFlags,
DWORD runtimeInfoFlags,
- __out_ecount_opt(dwDirectory) LPWSTR pDirectory,
+ __out_ecount_opt(dwDirectory) LPWSTR pDirectory,
DWORD dwDirectory,
__out_opt DWORD *pdwDirectoryLength,
__out_ecount_opt(cchBuffer) LPWSTR pVersion,
@@ -850,18 +745,37 @@ STDAPI GetRequestedRuntimeInfoInternal(LPCWSTR pExe,
NOTHROW;
GC_NOTRIGGER;
ENTRY_POINT;
- PRECONDITION(pDirectory != NULL && pVersion != NULL && cchBuffer > 0);
+ PRECONDITION( pVersion != NULL && cchBuffer > 0);
} CONTRACTL_END;
// for simplicity we will cheat and return the entire system directory in pDirectory
pVersion[0] = 0;
if (pdwLength != NULL)
*pdwLength = 0;
+ HRESULT hr;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return COR_E_STACKOVERFLOW;)
+ EX_TRY
+ {
- if (pdwDirectoryLength == NULL)
- pdwDirectoryLength = &dwDirectory;
+ PathString pDirectoryPath;
+
+ hr = GetCORSystemDirectoryInternaL(pDirectoryPath);
+ *pdwLength = pDirectoryPath.GetCount() + 1;
+ if (dwDirectory >= *pdwLength)
+ {
+ wcscpy_s(pDirectory, pDirectoryPath.GetCount() + 1, pDirectoryPath);
+ }
+ else
+ {
+ hr = E_FAIL;
+ }
+
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
- return GetCORSystemDirectoryInternal(pDirectory, dwDirectory, pdwDirectoryLength);
+ return hr;
}
// Replacement for legacy shim API GetCORRequiredVersion(...) used in linked libraries.
@@ -890,31 +804,31 @@ CLRRuntimeHostInternal_GetImageVersionString(
return hr;
} // CLRRuntimeHostInternal_GetImageVersionString
-
-STDAPI GetCORSystemDirectoryInternal(__out_ecount_part_opt(cchBuffer, *pdwLength) LPWSTR pBuffer,
- DWORD cchBuffer,
- __out_opt DWORD* pdwLength)
+ //LONGPATH:TODO: Remove this once Desktop usage has been removed
+#if !defined(FEATURE_CORECLR)
+STDAPI GetCORSystemDirectoryInternal(__out_ecount_part_opt(cchBuffer, *pdwLength) LPWSTR pBuffer,
+ DWORD cchBuffer,
+ __out_opt DWORD* pdwLength)
{
-#if defined(FEATURE_CORECLR) || defined(CROSSGEN_COMPILE)
+#if defined(CROSSGEN_COMPILE)
- CONTRACTL {
+ CONTRACTL{
NOTHROW;
- GC_NOTRIGGER;
- ENTRY_POINT;
- PRECONDITION(CheckPointer(pBuffer, NULL_OK));
- PRECONDITION(CheckPointer(pdwLength, NULL_OK));
+ GC_NOTRIGGER;
+ ENTRY_POINT;
+ PRECONDITION(CheckPointer(pBuffer, NULL_OK));
+ PRECONDITION(CheckPointer(pdwLength, NULL_OK));
} CONTRACTL_END;
HRESULT hr = S_OK;
BEGIN_ENTRYPOINT_NOTHROW;
-
- if(pdwLength == NULL)
+
+ if (pdwLength == NULL)
IfFailGo(E_POINTER);
if (pBuffer == NULL)
IfFailGo(E_POINTER);
-#ifdef CROSSGEN_COMPILE
if (WszGetModuleFileName(NULL, pBuffer, cchBuffer) == 0)
{
IfFailGo(HRESULT_FROM_GetLastError());
@@ -926,20 +840,15 @@ STDAPI GetCORSystemDirectoryInternal(__out_ecount_part_opt(cchBuffer, *pdwLength
IfFailGo(HRESULT_FROM_WIN32(ERROR_PATH_NOT_FOUND));
}
*pSeparator = W('\0');
-#else
- if (!PAL_GetPALDirectory(pBuffer, cchBuffer)) {
- IfFailGo(HRESULT_FROM_GetLastError());
- }
-#endif
// Include the null terminator in the length
- *pdwLength = (DWORD)wcslen(pBuffer)+1;
+ *pdwLength = (DWORD)wcslen(pBuffer) + 1;
ErrExit:
END_ENTRYPOINT_NOTHROW;
return hr;
-#else // FEATURE_CORECLR || CROSSGEN_COMPILE
+#else // CROSSGEN_COMPILE
// Simply forward the call to the ICLRRuntimeInfo implementation.
STATIC_CONTRACT_WRAPPER;
@@ -953,8 +862,8 @@ ErrExit:
{
// not invoked via shim (most probably loaded by Fusion)
WCHAR wszPath[_MAX_PATH];
- DWORD dwLength = WszGetModuleFileName(g_hThisInst, wszPath,NumItems(wszPath));
-
+ DWORD dwLength = WszGetModuleFileName(g_hThisInst, wszPath, NumItems(wszPath));
+
if (dwLength == 0 || (dwLength == NumItems(wszPath) && GetLastError() == ERROR_INSUFFICIENT_BUFFER))
{
@@ -968,7 +877,7 @@ ErrExit:
}
pwzSeparator[1] = W('\0'); // after '\'
- LPWSTR pwzDirectoryName = wszPath;
+ LPWSTR pwzDirectoryName = wszPath;
size_t cchLength = wcslen(pwzDirectoryName) + 1;
@@ -982,9 +891,9 @@ ErrExit:
{
// all look good, copy the string over
wcscpy_s(pBuffer,
- cchLength,
- pwzDirectoryName
- );
+ cchLength,
+ pwzDirectoryName
+ );
}
}
@@ -993,6 +902,70 @@ ErrExit:
}
return hr;
+#endif // CROSSGEN_COMPILE
+}
+#endif // !FEATURE_CORECLR
+
+STDAPI GetCORSystemDirectoryInternaL(SString& pBuffer)
+{
+#if defined(FEATURE_CORECLR) || defined(CROSSGEN_COMPILE)
+
+ CONTRACTL {
+ NOTHROW;
+ GC_NOTRIGGER;
+ ENTRY_POINT;
+ } CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BEGIN_ENTRYPOINT_NOTHROW;
+
+
+#ifdef CROSSGEN_COMPILE
+
+ if (WszGetModuleFileName(NULL, pBuffer) > 0)
+ {
+ hr = CopySystemDirectory(pBuffer, pBuffer);
+ }
+ else {
+ hr = HRESULT_FROM_GetLastError();
+ }
+
+#else
+
+ if (!PAL_GetPALDirectoryWrapper(pBuffer)) {
+ hr = HRESULT_FROM_GetLastError();
+ }
+#endif
+
+ END_ENTRYPOINT_NOTHROW;
+ return hr;
+
+#else // FEATURE_CORECLR || CROSSGEN_COMPILE
+ DWORD cchBuffer;
+ // Simply forward the call to the ICLRRuntimeInfo implementation.
+ STATIC_CONTRACT_WRAPPER;
+ HRESULT hr = S_OK;
+ if (g_pCLRRuntime)
+ {
+ WCHAR* temp = pBuffer.OpenUnicodeBuffer(MAX_PATH - 1);
+ hr = g_pCLRRuntime->GetRuntimeDirectory(temp, &cchBuffer);
+ pBuffer.CloseBuffer(cchBuffer - 1);
+ }
+ else
+ {
+ // not invoked via shim (most probably loaded by Fusion)
+ DWORD dwLength = WszGetModuleFileName(g_hThisInst, pBuffer);
+
+
+ if (dwLength == 0 || ((dwLength == pBuffer.GetCount() + 1) && GetLastError() == ERROR_INSUFFICIENT_BUFFER))
+ {
+ return E_UNEXPECTED;
+ }
+
+ CopySystemDirectory(pBuffer, pBuffer);
+ }
+ return hr;
+
#endif // FEATURE_CORECLR || CROSSGEN_COMPILE
}
@@ -1227,34 +1200,33 @@ HRESULT SetInternalSystemDirectory()
} CONTRACTL_END;
HRESULT hr = S_OK;
-
if(g_dwSystemDirectory == 0) {
- DWORD len;
- // use local buffer for thread safety
- NewArrayHolder<WCHAR> wzSystemDirectory(new (nothrow) WCHAR[MAX_LONGPATH+1]);
- if (wzSystemDirectory == NULL)
- {
- return HRESULT_FROM_WIN32(ERROR_NOT_ENOUGH_MEMORY);
- }
-
- hr = GetCORSystemDirectoryInternal(wzSystemDirectory, MAX_LONGPATH+1, &len);
+ DWORD len = 0;
+ NewArrayHolder<WCHAR> pSystemDirectory;
+ EX_TRY{
+
+ // use local buffer for thread safety
+ PathString wzSystemDirectory;
+
+ hr = GetCORSystemDirectoryInternaL(wzSystemDirectory);
+
+ if (FAILED(hr)) {
+ wzSystemDirectory.Set(W('\0'));
+ }
+
+ pSystemDirectory = wzSystemDirectory.GetCopyOfUnicodeString();
+ if (pSystemDirectory == NULL)
+ {
+ hr = HRESULT_FROM_WIN32(ERROR_NOT_ENOUGH_MEMORY);
+ }
+ len = wzSystemDirectory.GetCount() + 1;
- if(FAILED(hr)) {
- *wzSystemDirectory = W('\0');
- len = 1;
- }
-
- WCHAR * pSystemDirectory = new (nothrow) WCHAR[len];
- if (pSystemDirectory == NULL)
- {
- return HRESULT_FROM_WIN32(ERROR_NOT_ENOUGH_MEMORY);
}
-
- wcscpy_s(pSystemDirectory, len, wzSystemDirectory);
-
+ EX_CATCH_HRESULT(hr);
+
// publish results idempotently with correct memory ordering
- g_pSystemDirectory = pSystemDirectory;
+ g_pSystemDirectory = pSystemDirectory.Extract();
(void)InterlockedExchange((LONG *)&g_dwSystemDirectory, len);
}
diff --git a/src/dlls/mscorpe/ceefilegenwriter.cpp b/src/dlls/mscorpe/ceefilegenwriter.cpp
index 67031484ed..cfd1ebb644 100644
--- a/src/dlls/mscorpe/ceefilegenwriter.cpp
+++ b/src/dlls/mscorpe/ceefilegenwriter.cpp
@@ -225,8 +225,8 @@ CeeFileGenWriter::CeeFileGenWriter() // ctor is protected
#ifdef ENC_DELTA_HACK
// for EnC we want the RVA to be right at the front of the IL stream
- WCHAR szFileName[256];
- DWORD len = WszGetEnvironmentVariable(W("COMP_ENC_EMIT"), szFileName, NumItems(szFileName));
+ PathString szFileName;
+ DWORD len = WszGetEnvironmentVariable(W("COMP_ENC_EMIT"), szFileName);
if (len > 0)
g_EnCMode = TRUE;
#endif
@@ -941,64 +941,25 @@ HRESULT CeeFileGenWriter::emitExeMain()
return S_OK;
} // HRESULT CeeFileGenWriter::emitExeMain()
-// Like CreateProcess(), but waits for execution to finish
-// Returns true if successful, false on failure.
-// dwExitCode set to process' exitcode
-HRESULT CopySystemDirectory(__in WCHAR* pPath,
- __out_ecount_part(cchBuffer, *pdwLength) LPWSTR pbuffer,
- DWORD cchBuffer,
- __out DWORD* pdwLength)
-{
- if (pdwLength == NULL)
- return E_POINTER;
-
- HRESULT hr = S_OK;
- if(pPath == NULL)
- return HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND);
-
- SIZE_T dwPath = wcslen(pPath);
- LPWSTR pSep = wcsrchr(pPath, L'\\');
- if(pSep) {
- dwPath = (DWORD)(pSep-pPath+1);
- pPath[dwPath] = L'\0';
- }
-
- dwPath++; // Add back in the null
- *pdwLength = (DWORD)dwPath;
- if(dwPath > cchBuffer || pbuffer == NULL)
- hr = HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
- else {
- CopyMemory(pbuffer,
- pPath,
- dwPath*sizeof(WCHAR));
- }
- return hr;
-}
-
-HRESULT GetClrSystemDirectory(__out_ecount_part(cchBuffer, *pdwLength) LPWSTR pbuffer,
- DWORD cchBuffer,
- __out DWORD* pdwLength)
+HRESULT GetClrSystemDirectory(SString& pbuffer)
{
HRESULT hr = S_OK;
- if(pdwLength == NULL)
- return E_POINTER;
- WCHAR pPath[MAX_PATH];
- DWORD dwPath = MAX_PATH;
+ PathString pPath;
+ DWORD dwPath;
-
_ASSERTE (g_hThisInst);
- dwPath = WszGetModuleFileName(g_hThisInst, pPath, dwPath);
+ dwPath = WszGetModuleFileName(g_hThisInst, pPath);
if(dwPath == 0)
{
hr = HRESULT_FROM_GetLastErrorNA();
return (hr);
}
- else
- return CopySystemDirectory(pPath, pbuffer, cchBuffer, pdwLength);
+
+ return CopySystemDirectory(pPath, pbuffer);
}
#ifndef FEATURE_PAL
@@ -1008,10 +969,8 @@ BOOL RunProcess(LPCWSTR tempResObj, LPCWSTR pszFilename, DWORD* pdwExitCode, PEW
PROCESS_INFORMATION pi;
- DWORD cchSystemDir = MAX_PATH + 1;
- DWORD dwLen;
- WCHAR wszSystemDir[MAX_PATH + 1];
- if (FAILED(GetClrSystemDirectory(wszSystemDir, cchSystemDir, &dwLen)))
+ PathString wszSystemDir;
+ if (FAILED(GetClrSystemDirectory(wszSystemDir)))
return FALSE;
WCHAR* wzMachine;
@@ -1031,7 +990,7 @@ BOOL RunProcess(LPCWSTR tempResObj, LPCWSTR pszFilename, DWORD* pdwExitCode, PEW
if(*ext == NULL)
{
ssCmdLine.Printf(L"%scvtres.exe /NOLOGO /READONLY /MACHINE:%s \"/OUT:%s\" \"%s.\"",
- wszSystemDir,
+ wszSystemDir.GetUnicode(),
wzMachine,
tempResObj,
pszFilename);
@@ -1039,7 +998,7 @@ BOOL RunProcess(LPCWSTR tempResObj, LPCWSTR pszFilename, DWORD* pdwExitCode, PEW
else
{
ssCmdLine.Printf(L"%scvtres.exe /NOLOGO /READONLY /MACHINE:%s \"/OUT:%s\" \"%s\"",
- wszSystemDir,
+ wszSystemDir.GetUnicode(),
wzMachine,
tempResObj,
pszFilename);
@@ -1115,11 +1074,11 @@ HRESULT ConvertResource(const WCHAR * pszFilename, __in_ecount(cchTempFilename)
return S_OK;
}
- WCHAR tempResObj[MAX_PATH+1];
- WCHAR tempResPath[MAX_PATH+1];
+ PathString tempResObj;
+ PathString tempResPath;
// Create the temp file where the temp path is at rather than where the application is at.
- if (!WszGetTempPath(MAX_PATH, tempResPath))
+ if (!WszGetTempPath( tempResPath))
{
return HRESULT_FROM_GetLastError();
}
diff --git a/src/dlls/mscorpe/pewriter.cpp b/src/dlls/mscorpe/pewriter.cpp
index 6ad67609ae..f3b5fb194d 100644
--- a/src/dlls/mscorpe/pewriter.cpp
+++ b/src/dlls/mscorpe/pewriter.cpp
@@ -2181,14 +2181,14 @@ HRESULT PEWriter::write(__in LPCWSTR fileName) {
HRESULT hr;
#ifdef ENC_DELTA_HACK
- WCHAR szFileName[256];
- DWORD len = WszGetEnvironmentVariable(L"COMP_ENC_EMIT", szFileName, NumItems(szFileName));
+ PathString szFileName;
+ DWORD len = WszGetEnvironmentVariable(L"COMP_ENC_EMIT", szFileName);
_ASSERTE(len < sizeof(szFileName));
if (len > 0)
{
_ASSERTE(!m_pSeedFileDecoder);
-
- wcscat_s(szFileName, sizeof(szFileName)/sizeof(szFileName[0]), L".dil");
+ szFileName.Append(L".dil");
+
HANDLE pDelta = WszCreateFile(szFileName,
GENERIC_WRITE,
FILE_SHARE_READ | FILE_SHARE_WRITE,
diff --git a/src/ilasm/grammar_after.cpp b/src/ilasm/grammar_after.cpp
index 61de517e0e..c8634801c7 100644
--- a/src/ilasm/grammar_after.cpp
+++ b/src/ilasm/grammar_after.cpp
@@ -858,23 +858,19 @@ Its_An_Id:
if((parser->wzIncludePath != NULL)
&&(wcschr(wzFile,'\\')==NULL)&&(wcschr(wzFile,':')==NULL))
{
- WCHAR* wzFullName = new WCHAR[MAX_FILENAME_LENGTH+1];
- if(wzFullName != NULL)
+ PathString wzFullName;
+
+ WCHAR* pwz;
+ DWORD dw = WszSearchPath(parser->wzIncludePath,wzFile,NULL,
+ TRUE, wzFullName,&pwz);
+ if(dw != 0)
{
- WCHAR* pwz;
- DWORD dw = WszSearchPath(parser->wzIncludePath,wzFile,NULL,
- MAX_FILENAME_LENGTH+1,wzFullName,&pwz);
- if(dw != 0)
- {
- wzFullName[dw] = 0;
- delete [] wzFile;
- wzFile = wzFullName;
- }
- else
- {
- delete [] wzFullName;
- }
+ wzFullName.CloseBuffer((COUNT_T)(dw));
+ delete [] wzFile;
+
+ wzFile = wzFullName.GetCopyOfUnicodeString();
}
+
}
if(PASM->m_fReportProgress)
parser->msg("\nIncluding '%S'\n",wzFile);
diff --git a/src/ilasm/main.cpp b/src/ilasm/main.cpp
index 50131b2b01..811c65640e 100644
--- a/src/ilasm/main.cpp
+++ b/src/ilasm/main.cpp
@@ -95,7 +95,7 @@ WCHAR *pwzDeltaFiles[1024];
char szInputFilename[MAX_FILENAME_LENGTH*3];
WCHAR wzInputFilename[MAX_FILENAME_LENGTH];
WCHAR wzOutputFilename[MAX_FILENAME_LENGTH];
-WCHAR wzIncludePathBuffer[MAX_FILENAME_LENGTH];
+
#ifdef _PREFAST_
#pragma warning(push)
@@ -628,8 +628,12 @@ extern "C" int _cdecl wmain(int argc, __in WCHAR **argv)
}
if(wzIncludePath == NULL)
{
- if(0!=WszGetEnvironmentVariable(W("ILASM_INCLUDE"),wzIncludePathBuffer,MAX_FILENAME_LENGTH))
- wzIncludePath = wzIncludePathBuffer;
+ PathString wzIncludePathBuffer;
+ if (0 != WszGetEnvironmentVariable(W("ILASM_INCLUDE"), wzIncludePathBuffer))
+ {
+ wzIncludePath = wzIncludePathBuffer.GetCopyOfUnicodeString();
+
+ }
}
//------------ Assembler initialization done. Now, to business -----------------------
if((pParser = new AsmParse(NULL, pAsm)))
diff --git a/src/inc/corpriv.h b/src/inc/corpriv.h
index f90d2ab470..1a8f671701 100644
--- a/src/inc/corpriv.h
+++ b/src/inc/corpriv.h
@@ -641,10 +641,16 @@ STDAPI LoadLibraryShimInternal(
LPVOID pvReserved,
HMODULE *phModDll);
+STDAPI GetCORSystemDirectoryInternaL(
+ SString& pBuffer
+ );
+
+//LONGPATH:TODO: Remove this once Desktop usage has been removed
STDAPI GetCORSystemDirectoryInternal(
- __out_ecount_part_opt(cchBuffer, *pdwLength) LPWSTR pBuffer,
- DWORD cchBuffer,
- __out_opt DWORD* pdwLength);
+ __out_ecount_part_opt(cchBuffer, *pdwLength) LPWSTR pBuffer,
+ DWORD cchBuffer,
+ __out_opt DWORD* pdwLength
+ );
STDAPI GetCORVersionInternal(
__out_ecount_z_opt(cchBuffer) LPWSTR pBuffer,
@@ -656,7 +662,7 @@ STDAPI GetRequestedRuntimeInfoInternal(LPCWSTR pExe,
LPCWSTR pConfigurationFile,
DWORD startupFlags,
DWORD runtimeInfoFlags,
- __out_ecount_opt(dwDirectory) LPWSTR pDirectory,
+ __out_ecount_opt(dwDirectory) LPWSTR pDirectory,
DWORD dwDirectory,
__out_opt DWORD *pdwDirectoryLength,
__out_ecount_opt(cchBuffer) LPWSTR pVersion,
diff --git a/src/inc/longfilepathwrappers.h b/src/inc/longfilepathwrappers.h
new file mode 100644
index 0000000000..b3fc6ad1db
--- /dev/null
+++ b/src/inc/longfilepathwrappers.h
@@ -0,0 +1,277 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+#ifndef _WIN_PATH_APIS_WRAPPER_
+#define _WIN_PATH_APIS_WRAPPER_
+class SString;
+
+HMODULE
+LoadLibraryExWrapper(
+ _In_ LPCWSTR lpLibFileName,
+ _Reserved_ HANDLE hFile = NULL,
+ _In_ DWORD dwFlags = 0
+ );
+
+HANDLE
+CreateFileWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ DWORD dwDesiredAccess,
+ _In_ DWORD dwShareMode,
+ _In_opt_ LPSECURITY_ATTRIBUTES lpSecurityAttributes,
+ _In_ DWORD dwCreationDisposition,
+ _In_ DWORD dwFlagsAndAttributes,
+ _In_opt_ HANDLE hTemplateFile
+ );
+
+BOOL
+SetFileAttributesWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ DWORD dwFileAttributes
+ );
+
+DWORD
+GetFileAttributesWrapper(
+ _In_ LPCWSTR lpFileName
+ );
+
+BOOL
+GetFileAttributesExWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ GET_FILEEX_INFO_LEVELS fInfoLevelId,
+ _Out_writes_bytes_(sizeof(WIN32_FILE_ATTRIBUTE_DATA)) LPVOID lpFileInformation
+ );
+BOOL
+DeleteFileWrapper(
+ _In_ LPCWSTR lpFileName
+ );
+
+HANDLE
+FindFirstFileExWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ FINDEX_INFO_LEVELS fInfoLevelId,
+ _Out_writes_bytes_(sizeof(WIN32_FIND_DATAW)) LPVOID lpFindFileData,
+ _In_ FINDEX_SEARCH_OPS fSearchOp,
+ _Reserved_ LPVOID lpSearchFilter,
+ _In_ DWORD dwAdditionalFlags
+ );
+
+BOOL
+CopyFileWrapper(
+ _In_ LPCWSTR lpExistingFileName,
+ _In_ LPCWSTR lpNewFileName,
+ _In_ BOOL bFailIfExists
+ );
+
+#ifndef FEATURE_PAL
+BOOL
+CopyFileExWrapper(
+ _In_ LPCWSTR lpExistingFileName,
+ _In_ LPCWSTR lpNewFileName,
+ _In_opt_ LPPROGRESS_ROUTINE lpProgressRoutine,
+ _In_opt_ LPVOID lpData,
+ _When_(pbCancel != NULL, _Pre_satisfies_(*pbCancel == FALSE))
+ _Inout_opt_ LPBOOL pbCancel,
+ _In_ DWORD dwCopyFlags
+ );
+#endif //FEATURE_PAL
+
+BOOL
+MoveFileWrapper(
+ _In_ LPCWSTR lpExistingFileName,
+ _In_ LPCWSTR lpNewFileName
+ );
+
+BOOL
+MoveFileExWrapper(
+ _In_ LPCWSTR lpExistingFileName,
+ _In_opt_ LPCWSTR lpNewFileName,
+ _In_ DWORD dwFlags
+ );
+
+BOOL
+CreateDirectoryWrapper(
+ _In_ LPCWSTR lpPathName,
+ _In_opt_ LPSECURITY_ATTRIBUTES lpSecurityAttributes
+ );
+
+BOOL
+RemoveDirectoryWrapper(
+ _In_ LPCWSTR lpPathName
+ );
+
+BOOL
+CreateHardLinkWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ LPCWSTR lpExistingFileName,
+ _Reserved_ LPSECURITY_ATTRIBUTES lpSecurityAttributes
+ );
+
+DWORD
+SearchPathWrapper(
+ _In_opt_ LPCWSTR lpPath,
+ _In_ LPCWSTR lpFileName,
+ _In_opt_ LPCWSTR lpExtension,
+ _In_ BOOL getPath,
+ SString& lpBuffer,
+ _Out_opt_ LPWSTR * lpFilePart
+ );
+
+
+DWORD
+GetShortPathNameWrapper(
+ _In_ LPCWSTR lpszLongPath,
+ SString& lpszShortPath
+ );
+
+DWORD
+GetLongPathNameWrapper(
+ _In_ LPCWSTR lpszShortPath,
+ SString& lpszLongPath
+ );
+
+UINT GetTempFileNameWrapper(
+ _In_ LPCTSTR lpPathName,
+ _In_ LPCTSTR lpPrefixString,
+ _In_ UINT uUnique,
+ SString& lpTempFileName
+ );
+
+DWORD GetTempPathWrapper(
+ SString& lpBuffer
+ );
+
+DWORD GetCurrentDirectoryWrapper(
+ SString& lpBuffer
+ );
+
+DWORD
+GetModuleFileNameWrapper(
+ _In_opt_ HMODULE hModule,
+ SString& buffer
+ );
+
+DWORD GetEnvironmentVariableWrapper(
+ _In_opt_ LPCTSTR lpName,
+ _Out_opt_ SString& lpBuffer
+ );
+
+BOOL PAL_GetPALDirectoryWrapper(SString& pbuffer);
+
+#ifndef FEATURE_CORECLR
+//Temporarily providing direct OS Calls Till All of the Desktop CLR start using the above format
+inline DWORD
+SearchPathWrapper(
+ _In_opt_ LPCWSTR lpPath,
+ _In_ LPCWSTR lpFileName,
+ _In_opt_ LPCWSTR lpExtension,
+ _In_ BOOL getPath,
+ _Out_ LPWSTR lpBuffer,
+ _Out_opt_ LPWSTR * lpFilePart
+ )
+{
+ return SearchPathW(
+ lpPath,
+ lpFileName,
+ lpExtension,
+ getPath,
+ lpBuffer,
+ lpFilePart
+ );
+}
+
+
+inline DWORD
+GetShortPathNameWrapper(
+ _In_ LPCWSTR lpszLongPath,
+ _Out_ LPWSTR lpszShortPath,
+ _In_ DWORD cchBuffer
+ )
+{
+ return GetShortPathNameW(
+ lpszLongPath,
+ lpszShortPath,
+ cchBuffer
+ );
+}
+
+inline DWORD
+GetLongPathNameWrapper(
+ _In_ LPCWSTR lpszShortPath,
+ _Out_ LPWSTR lpszLongPath,
+ _In_ DWORD cchBuffer
+ )
+{
+ return GetLongPathNameW(
+ lpszShortPath,
+ lpszLongPath,
+ cchBuffer
+ );
+}
+
+inline UINT GetTempFileNameWrapper(
+ _In_ LPCWSTR lpPathName,
+ _In_ LPCWSTR lpPrefixString,
+ _In_ UINT uUnique,
+ _Out_ LPWSTR lpTempFileName
+ )
+{
+ return GetTempFileNameW(
+ lpPathName,
+ lpPrefixString,
+ uUnique,
+ lpTempFileName
+ );
+}
+
+inline DWORD GetTempPathWrapper(
+ _In_ DWORD nBufferLength,
+ _Out_ LPWSTR lpBuffer
+ )
+{
+ return GetTempPathW(
+ nBufferLength,
+ lpBuffer
+ );
+}
+
+inline DWORD GetCurrentDirectoryWrapper(
+ _In_ DWORD nBufferLength,
+ _Out_ LPWSTR lpBuffer
+ )
+{
+ return GetCurrentDirectoryW(
+ nBufferLength,
+ lpBuffer
+ );
+}
+
+inline DWORD
+GetModuleFileNameWrapper(
+ _In_opt_ HMODULE hModule,
+ _Out_ LPWSTR lpFilename,
+ _In_ DWORD nSize
+ )
+{
+ return GetModuleFileNameW(
+ hModule,
+ lpFilename,
+ nSize
+ );
+}
+
+inline DWORD GetEnvironmentVariableWrapper(
+ _In_opt_ LPCWSTR lpName,
+ _Out_opt_ LPWSTR lpBuffer,
+ _In_ DWORD nSize
+ )
+{
+ return GetEnvironmentVariableW(
+ lpName,
+ lpBuffer,
+ nSize
+ );
+}
+#endif //FEATURE_CORECLR
+#endif //_WIN_PATH_APIS_WRAPPER_
+
diff --git a/src/inc/sstring.h b/src/inc/sstring.h
index 3c5107a06c..bfbaa81429 100644
--- a/src/inc/sstring.h
+++ b/src/inc/sstring.h
@@ -625,6 +625,9 @@ private:
UTF8 *OpenUTF8Buffer(COUNT_T maxSingleCharCount);
ANSI *OpenANSIBuffer(COUNT_T maxSingleCharCount);
+ //Returns the unicode string, the caller is reponsible for lifetime of the string
+ WCHAR *GetCopyOfUnicodeString();
+
// Get the max size that can be passed to OpenUnicodeBuffer without causing allocations.
COUNT_T GetUnicodeAllocation();
@@ -1009,9 +1012,11 @@ typedef InlineSString<32> SmallStackSString;
#ifdef _DEBUG
// This is a smaller version for debug builds to exercise the buffer allocation path
typedef InlineSString<32> PathString;
+typedef InlineSString<2 * 32> LongPathString;
#else
// Set it to the current MAX_PATH
typedef InlineSString<260> PathString;
+typedef InlineSString<2 * 260> LongPathString;
#endif
// ================================================================================
diff --git a/src/inc/sstring.inl b/src/inc/sstring.inl
index b9c689548b..6b587e17ba 100644
--- a/src/inc/sstring.inl
+++ b/src/inc/sstring.inl
@@ -1257,7 +1257,7 @@ inline WCHAR *SString::GetRawUnicode() const
LIMITED_METHOD_CONTRACT;
SUPPORTS_DAC_HOST_ONLY;
- return (WCHAR *) m_buffer;
+ return (WCHAR *)m_buffer;
}
// Private helper:
@@ -1690,6 +1690,28 @@ inline WCHAR *SString::OpenUnicodeBuffer(COUNT_T countChars)
}
//----------------------------------------------------------------------------
+// Return a copy of the underlying buffer, the caller is responsible for managing
+// the returned memory
+//----------------------------------------------------------------------------
+inline WCHAR *SString::GetCopyOfUnicodeString()
+{
+ SS_CONTRACT(WCHAR*)
+ {
+ GC_NOTRIGGER;
+ PRECONDITION(CheckPointer(this));
+ SS_POSTCONDITION(CheckPointer(buffer));
+ THROWS;
+ }
+ SS_CONTRACT_END;
+ NewArrayHolder<WCHAR> buffer = NULL;
+
+ buffer = new WCHAR[GetCount() +1];
+ wcscpy_s(buffer, GetCount() + 1, GetUnicode());
+
+ SS_RETURN buffer.Extract();
+}
+
+//----------------------------------------------------------------------------
// Return a writeable buffer that can store 'countChars'+1 ansi characters.
// Call CloseBuffer when done.
//----------------------------------------------------------------------------
diff --git a/src/inc/utilcode.h b/src/inc/utilcode.h
index 78dc438ddb..a9cb0077fc 100644
--- a/src/inc/utilcode.h
+++ b/src/inc/utilcode.h
@@ -843,7 +843,8 @@ private:
HRESULT GetLibrary(LocaleID langId, HRESOURCEDLL* phInst);
#ifndef DACCESS_COMPILE
HRESULT LoadLibraryHelper(HRESOURCEDLL *pHInst,
- __out_ecount(rcPathSize) WCHAR *rcPath, const DWORD rcPathSize);
+ SString& rcPath);
+ HRESULT LoadLibraryThrows(HRESOURCEDLL * pHInst);
HRESULT LoadLibrary(HRESOURCEDLL * pHInst);
HRESULT LoadResourceFile(HRESOURCEDLL * pHInst, LPCWSTR lpFileName);
#endif
@@ -4467,7 +4468,7 @@ BOOL GetRegistryLongValue(HKEY hKeyParent, // Parent key.
long *pValue, // Put value here, if found.
BOOL fReadNonVirtualizedKey); // Whether to read 64-bit hive on WOW64
-HRESULT GetCurrentModuleFileName(__out_ecount(*pcchBuffer) LPWSTR pBuffer, __inout DWORD *pcchBuffer);
+HRESULT GetCurrentModuleFileName(SString& pBuffer);
//*****************************************************************************
// Retrieve information regarding what registered default debugger
@@ -5309,7 +5310,7 @@ BOOL IsIPInModule(HMODULE_TGT hModule, PCODE ip);
struct CoreClrCallbacks
{
typedef IExecutionEngine* (__stdcall * pfnIEE_t)();
- typedef HRESULT (__stdcall * pfnGetCORSystemDirectory_t)(LPWSTR pbuffer, DWORD cchBuffer, DWORD* pdwlength);
+ typedef HRESULT (__stdcall * pfnGetCORSystemDirectory_t)(SString& pbuffer);
typedef void* (__stdcall * pfnGetCLRFunction_t)(LPCSTR functionName);
HINSTANCE m_hmodCoreCLR;
@@ -5543,8 +5544,8 @@ inline T* InterlockedCompareExchangeT(
// Returns the directory for HMODULE. So, if HMODULE was for "C:\Dir1\Dir2\Filename.DLL",
// then this would return "C:\Dir1\Dir2\" (note the trailing backslash).
-HRESULT GetHModuleDirectory(HMODULE hMod, __out_z __out_ecount(cchPath) LPWSTR wszPath, size_t cchPath);
-SString & GetHModuleDirectory(HMODULE hMod, SString &ssDir);
+HRESULT GetHModuleDirectory(HMODULE hMod, SString& wszPath);
+HRESULT CopySystemDirectory(const SString& pPathString, SString& pbuffer);
HMODULE LoadLocalizedResourceDLLForSDK(_In_z_ LPCWSTR wzResourceDllName, _In_opt_z_ LPCWSTR modulePath=NULL, bool trySelf=true);
// This is a slight variation that can be used for anything else
diff --git a/src/inc/winwrap.h b/src/inc/winwrap.h
index 6896accab9..89a3220c67 100644
--- a/src/inc/winwrap.h
+++ b/src/inc/winwrap.h
@@ -6,9 +6,9 @@
//
// This file contains wrapper functions for Win32 API's that take strings.
//
-// The Common Language Runtime internally uses UNICODE as the internal state
-// and string format. This file will undef the mapping macros so that one
-// cannot mistakingly call a method that isn't going to work. Instead, you
+// The Common Language Runtime internally uses UNICODE as the internal state
+// and string format. This file will undef the mapping macros so that one
+// cannot mistakingly call a method that isn't going to work. Instead, you
// have to call the correct wrapper API.
//
//*****************************************************************************
@@ -16,7 +16,6 @@
#ifndef __WIN_WRAP_H__
#define __WIN_WRAP_H__
-
//********** Macros. **********************************************************
#if !defined(WIN32_LEAN_AND_MEAN)
#define WIN32_LEAN_AND_MEAN
@@ -48,6 +47,7 @@
#include <specstrings.h>
#include "registrywrapper.h"
+#include "longfilepathwrappers.h"
#ifdef _PREFAST_
//
@@ -75,288 +75,288 @@
#undef GetBinaryType
#undef GetShortPathName
#undef GetLongPathName
-#undef GetEnvironmentStrings
-#undef FreeEnvironmentStrings
-#undef FormatMessage
-#undef CreateMailslot
-#undef EncryptFile
-#undef DecryptFile
-#undef OpenRaw
-#undef QueryRecoveryAgents
-#undef lstrcmp
-#undef lstrcmpi
-#undef lstrcpyn
-#undef lstrcpy
-#undef lstrcat
-#undef lstrlen
-#undef CreateMutex
-#undef OpenMutex
-#undef CreateEvent
-#undef OpenEvent
-#undef CreateSemaphore
-#undef OpenSemaphore
-#undef CreateWaitableTimer
-#undef OpenWaitableTimer
-#undef CreateFileMapping
-#undef OpenFileMapping
-#undef GetLogicalDriveStrings
-#undef LoadLibrary
-#undef LoadLibraryEx
-#undef GetModuleFileName
-#undef GetModuleHandle
+#undef GetEnvironmentStrings
+#undef FreeEnvironmentStrings
+#undef FormatMessage
+#undef CreateMailslot
+#undef EncryptFile
+#undef DecryptFile
+#undef OpenRaw
+#undef QueryRecoveryAgents
+#undef lstrcmp
+#undef lstrcmpi
+#undef lstrcpyn
+#undef lstrcpy
+#undef lstrcat
+#undef lstrlen
+#undef CreateMutex
+#undef OpenMutex
+#undef CreateEvent
+#undef OpenEvent
+#undef CreateSemaphore
+#undef OpenSemaphore
+#undef CreateWaitableTimer
+#undef OpenWaitableTimer
+#undef CreateFileMapping
+#undef OpenFileMapping
+#undef GetLogicalDriveStrings
+#undef LoadLibrary
+#undef LoadLibraryEx
+#undef GetModuleFileName
+#undef GetModuleHandle
#undef GetModuleHandleEx
-#undef CreateProcess
-#undef FatalAppExit
-#undef GetStartupInfo
-#undef GetCommandLine
-#undef GetEnvironmentVariable
-#undef SetEnvironmentVariable
-#undef ExpandEnvironmentStrings
-#undef OutputDebugString
-#undef FindResource
-#undef FindResourceEx
-#undef EnumResourceTypes
-#undef EnumResourceNames
-#undef EnumResourceLanguages
-#undef BeginUpdateResource
-#undef UpdateResource
-#undef EndUpdateResource
-#undef GlobalAddAtom
-#undef GlobalFindAtom
-#undef GlobalGetAtomName
-#undef AddAtom
-#undef FindAtom
-#undef GetAtomName
-#undef GetProfileInt
-#undef GetProfileString
-#undef WriteProfileString
-#undef GetProfileSection
-#undef WriteProfileSection
-#undef GetPrivateProfileInt
-#undef GetPrivateProfileString
-#undef WritePrivateProfileString
-#undef GetPrivateProfileSection
-#undef WritePrivateProfileSection
-#undef GetPrivateProfileSectionNames
-#undef GetPrivateProfileStruct
-#undef WritePrivateProfileStruct
-#undef GetDriveType
-#undef GetSystemDirectory
-#undef GetTempPath
-#undef GetTempFileName
-#undef GetWindowsDirectory
-#undef SetCurrentDirectory
-#undef GetCurrentDirectory
-#undef GetDiskFreeSpace
-#undef GetDiskFreeSpaceEx
-#undef CreateDirectory
-#undef CreateDirectoryEx
-#undef RemoveDirectory
-#undef GetFullPathName
-#undef DefineDosDevice
-#undef QueryDosDevice
-#undef CreateFile
-#undef SetFileAttributes
-#undef GetFileAttributes
+#undef CreateProcess
+#undef FatalAppExit
+#undef GetStartupInfo
+#undef GetCommandLine
+#undef GetEnvironmentVariable
+#undef SetEnvironmentVariable
+#undef ExpandEnvironmentStrings
+#undef OutputDebugString
+#undef FindResource
+#undef FindResourceEx
+#undef EnumResourceTypes
+#undef EnumResourceNames
+#undef EnumResourceLanguages
+#undef BeginUpdateResource
+#undef UpdateResource
+#undef EndUpdateResource
+#undef GlobalAddAtom
+#undef GlobalFindAtom
+#undef GlobalGetAtomName
+#undef AddAtom
+#undef FindAtom
+#undef GetAtomName
+#undef GetProfileInt
+#undef GetProfileString
+#undef WriteProfileString
+#undef GetProfileSection
+#undef WriteProfileSection
+#undef GetPrivateProfileInt
+#undef GetPrivateProfileString
+#undef WritePrivateProfileString
+#undef GetPrivateProfileSection
+#undef WritePrivateProfileSection
+#undef GetPrivateProfileSectionNames
+#undef GetPrivateProfileStruct
+#undef WritePrivateProfileStruct
+#undef GetDriveType
+#undef GetSystemDirectory
+#undef GetTempPath
+#undef GetTempFileName
+#undef GetWindowsDirectory
+#undef SetCurrentDirectory
+#undef GetCurrentDirectory
+#undef GetDiskFreeSpace
+#undef GetDiskFreeSpaceEx
+#undef CreateDirectory
+#undef CreateDirectoryEx
+#undef RemoveDirectory
+#undef GetFullPathName
+#undef DefineDosDevice
+#undef QueryDosDevice
+#undef CreateFile
+#undef SetFileAttributes
+#undef GetFileAttributes
#undef GetFileAttributesEx
-#undef GetCompressedFileSize
-#undef DeleteFile
-#undef FindFirstFileEx
-#undef FindFirstFile
-#undef FindNextFile
-#undef SearchPath
-#undef CopyFile
-#undef CopyFileEx
-#undef MoveFile
-#undef MoveFileEx
-#undef MoveFileWithProgress
-#undef CreateSymbolicLink
-#undef QuerySymbolicLink
-#undef CreateHardLink
-#undef CreateNamedPipe
-#undef GetNamedPipeHandleState
-#undef CallNamedPipe
-#undef WaitNamedPipe
-#undef SetVolumeLabel
-#undef GetVolumeInformation
-#undef ClearEventLog
-#undef BackupEventLog
-#undef OpenEventLog
-#undef RegisterEventSource
-#undef OpenBackupEventLog
-#undef ReadEventLog
-#undef ReportEvent
-#undef AccessCheckAndAuditAlarm
-#undef AccessCheckByTypeAndAuditAlarm
-#undef AccessCheckByTypeResultListAndAuditAlarm
-#undef ObjectOpenAuditAlarm
-#undef ObjectPrivilegeAuditAlarm
-#undef ObjectCloseAuditAlarm
-#undef ObjectDeleteAuditAlarm
-#undef PrivilegedServiceAuditAlarm
-#undef SetFileSecurity
-#undef GetFileSecurity
-#undef FindFirstChangeNotification
-#undef IsBadStringPtr
+#undef GetCompressedFileSize
+#undef DeleteFile
+#undef FindFirstFileEx
+#undef FindFirstFile
+#undef FindNextFile
+#undef SearchPath
+#undef CopyFile
+#undef CopyFileEx
+#undef MoveFile
+#undef MoveFileEx
+#undef MoveFileWithProgress
+#undef CreateSymbolicLink
+#undef QuerySymbolicLink
+#undef CreateHardLink
+#undef CreateNamedPipe
+#undef GetNamedPipeHandleState
+#undef CallNamedPipe
+#undef WaitNamedPipe
+#undef SetVolumeLabel
+#undef GetVolumeInformation
+#undef ClearEventLog
+#undef BackupEventLog
+#undef OpenEventLog
+#undef RegisterEventSource
+#undef OpenBackupEventLog
+#undef ReadEventLog
+#undef ReportEvent
+#undef AccessCheckAndAuditAlarm
+#undef AccessCheckByTypeAndAuditAlarm
+#undef AccessCheckByTypeResultListAndAuditAlarm
+#undef ObjectOpenAuditAlarm
+#undef ObjectPrivilegeAuditAlarm
+#undef ObjectCloseAuditAlarm
+#undef ObjectDeleteAuditAlarm
+#undef PrivilegedServiceAuditAlarm
+#undef SetFileSecurity
+#undef GetFileSecurity
+#undef FindFirstChangeNotification
+#undef IsBadStringPtr
#undef LookupAccountSid
-#undef LookupAccountName
-#undef LookupPrivilegeValue
-#undef LookupPrivilegeName
-#undef LookupPrivilegeDisplayName
-#undef BuildCommDCB
-#undef BuildCommDCBAndTimeouts
-#undef CommConfigDialog
-#undef GetDefaultCommConfig
-#undef SetDefaultCommConfig
-#undef GetComputerName
-#undef SetComputerName
-#undef GetUserName
-#undef LogonUser
-#undef CreateProcessAsUser
-#undef GetCurrentHwProfile
-#undef GetVersionEx
-#undef CreateJobObject
-#undef OpenJobObject
-
+#undef LookupAccountName
+#undef LookupPrivilegeValue
+#undef LookupPrivilegeName
+#undef LookupPrivilegeDisplayName
+#undef BuildCommDCB
+#undef BuildCommDCBAndTimeouts
+#undef CommConfigDialog
+#undef GetDefaultCommConfig
+#undef SetDefaultCommConfig
+#undef GetComputerName
+#undef SetComputerName
+#undef GetUserName
+#undef LogonUser
+#undef CreateProcessAsUser
+#undef GetCurrentHwProfile
+#undef GetVersionEx
+#undef CreateJobObject
+#undef OpenJobObject
+#undef SetDllDirectory
// winuser.h
-#undef MAKEINTRESOURCE
-#undef wvsprintf
-#undef wsprintf
-#undef LoadKeyboardLayout
-#undef GetKeyboardLayoutName
-#undef CreateDesktop
-#undef OpenDesktop
-#undef EnumDesktops
-#undef CreateWindowStation
-#undef OpenWindowStation
+#undef MAKEINTRESOURCE
+#undef wvsprintf
+#undef wsprintf
+#undef LoadKeyboardLayout
+#undef GetKeyboardLayoutName
+#undef CreateDesktop
+#undef OpenDesktop
+#undef EnumDesktops
+#undef CreateWindowStation
+#undef OpenWindowStation
#undef EnumWindowStations
#undef GetUserObjectInformation
#undef SetUserObjectInformation
#undef RegisterWindowMessage
#undef SIZEZOOMSHOW
-#undef WS_TILEDWINDOW
-#undef GetMessage
-#undef DispatchMessage
-#undef PeekMessage
+#undef WS_TILEDWINDOW
+#undef GetMessage
+#undef DispatchMessage
+#undef PeekMessage
#undef SendMessage
-#undef SendMessageTimeout
-#undef SendNotifyMessage
-#undef SendMessageCallback
-#undef BroadcastSystemMessage
-#undef RegisterDeviceNotification
-#undef PostMessage
-#undef PostThreadMessage
-#undef PostAppMessage
-#undef DefWindowProc
-#undef CallWindowProc
-#undef RegisterClass
-#undef UnregisterClass
-#undef GetClassInfo
-#undef RegisterClassEx
-#undef GetClassInfoEx
-#undef CreateWindowEx
-#undef CreateWindow
-#undef CreateDialogParam
-#undef CreateDialogIndirectParam
-#undef CreateDialog
-#undef CreateDialogIndirect
-#undef DialogBoxParam
-#undef DialogBoxIndirectParam
-#undef DialogBox
-#undef DialogBoxIndirect
-#undef SetDlgItemText
-#undef GetDlgItemText
-#undef SendDlgItemMessage
-#undef DefDlgProc
-#undef CallMsgFilter
-#undef RegisterClipboardFormat
-#undef GetClipboardFormatName
-#undef CharToOem
-#undef OemToChar
-#undef CharToOemBuff
-#undef OemToCharBuff
-#undef CharUpper
-#undef CharUpperBuff
-#undef CharLower
-#undef CharLowerBuff
-#undef CharNext
-#undef IsCharAlpha
-#undef IsCharAlphaNumeric
-#undef IsCharUpper
-#undef IsCharLower
-#undef GetKeyNameText
-#undef VkKeyScan
-#undef VkKeyScanEx
-#undef MapVirtualKey
-#undef MapVirtualKeyEx
-#undef LoadAccelerators
-#undef CreateAcceleratorTable
-#undef CopyAcceleratorTable
-#undef TranslateAccelerator
-#undef LoadMenu
-#undef LoadMenuIndirect
-#undef ChangeMenu
-#undef GetMenuString
-#undef InsertMenu
-#undef AppendMenu
-#undef ModifyMenu
-#undef InsertMenuItem
-#undef GetMenuItemInfo
-#undef SetMenuItemInfo
-#undef DrawText
-#undef DrawTextEx
-#undef GrayString
-#undef DrawState
-#undef TabbedTextOut
-#undef GetTabbedTextExtent
-#undef SetProp
-#undef GetProp
-#undef RemoveProp
-#undef EnumPropsEx
-#undef EnumProps
-#undef SetWindowText
-#undef GetWindowText
-#undef GetWindowTextLength
-#undef MessageBox
-#undef MessageBoxEx
-#undef MessageBoxIndirect
-#undef COLOR_3DSHADOW
-#undef GetWindowLong
-#undef SetWindowLong
-#undef GetClassLong
-#undef SetClassLong
-#undef FindWindow
-#undef FindWindowEx
-#undef GetClassName
-#undef SetWindowsHook
-#undef SetWindowsHook
-#undef SetWindowsHookEx
-#undef MFT_OWNERDRAW
-#undef LoadBitmap
-#undef LoadCursor
-#undef LoadCursorFromFile
-#undef LoadIcon
-#undef LoadImage
-#undef LoadString
-#undef IsDialogMessage
-#undef DlgDirList
-#undef DlgDirSelectEx
-#undef DlgDirListComboBox
-#undef DlgDirSelectComboBoxEx
-#undef DefFrameProc
-#undef DefMDIChildProc
-#undef CreateMDIWindow
-#undef WinHelp
-#undef ChangeDisplaySettings
-#undef ChangeDisplaySettingsEx
-#undef EnumDisplaySettings
-#undef EnumDisplayDevices
-#undef SystemParametersInfo
-#undef GetMonitorInfo
-#undef GetWindowModuleFileName
-#undef RealGetWindowClass
+#undef SendMessageTimeout
+#undef SendNotifyMessage
+#undef SendMessageCallback
+#undef BroadcastSystemMessage
+#undef RegisterDeviceNotification
+#undef PostMessage
+#undef PostThreadMessage
+#undef PostAppMessage
+#undef DefWindowProc
+#undef CallWindowProc
+#undef RegisterClass
+#undef UnregisterClass
+#undef GetClassInfo
+#undef RegisterClassEx
+#undef GetClassInfoEx
+#undef CreateWindowEx
+#undef CreateWindow
+#undef CreateDialogParam
+#undef CreateDialogIndirectParam
+#undef CreateDialog
+#undef CreateDialogIndirect
+#undef DialogBoxParam
+#undef DialogBoxIndirectParam
+#undef DialogBox
+#undef DialogBoxIndirect
+#undef SetDlgItemText
+#undef GetDlgItemText
+#undef SendDlgItemMessage
+#undef DefDlgProc
+#undef CallMsgFilter
+#undef RegisterClipboardFormat
+#undef GetClipboardFormatName
+#undef CharToOem
+#undef OemToChar
+#undef CharToOemBuff
+#undef OemToCharBuff
+#undef CharUpper
+#undef CharUpperBuff
+#undef CharLower
+#undef CharLowerBuff
+#undef CharNext
+#undef IsCharAlpha
+#undef IsCharAlphaNumeric
+#undef IsCharUpper
+#undef IsCharLower
+#undef GetKeyNameText
+#undef VkKeyScan
+#undef VkKeyScanEx
+#undef MapVirtualKey
+#undef MapVirtualKeyEx
+#undef LoadAccelerators
+#undef CreateAcceleratorTable
+#undef CopyAcceleratorTable
+#undef TranslateAccelerator
+#undef LoadMenu
+#undef LoadMenuIndirect
+#undef ChangeMenu
+#undef GetMenuString
+#undef InsertMenu
+#undef AppendMenu
+#undef ModifyMenu
+#undef InsertMenuItem
+#undef GetMenuItemInfo
+#undef SetMenuItemInfo
+#undef DrawText
+#undef DrawTextEx
+#undef GrayString
+#undef DrawState
+#undef TabbedTextOut
+#undef GetTabbedTextExtent
+#undef SetProp
+#undef GetProp
+#undef RemoveProp
+#undef EnumPropsEx
+#undef EnumProps
+#undef SetWindowText
+#undef GetWindowText
+#undef GetWindowTextLength
+#undef MessageBox
+#undef MessageBoxEx
+#undef MessageBoxIndirect
+#undef COLOR_3DSHADOW
+#undef GetWindowLong
+#undef SetWindowLong
+#undef GetClassLong
+#undef SetClassLong
+#undef FindWindow
+#undef FindWindowEx
+#undef GetClassName
+#undef SetWindowsHook
+#undef SetWindowsHook
+#undef SetWindowsHookEx
+#undef MFT_OWNERDRAW
+#undef LoadBitmap
+#undef LoadCursor
+#undef LoadCursorFromFile
+#undef LoadIcon
+#undef LoadImage
+#undef LoadString
+#undef IsDialogMessage
+#undef DlgDirList
+#undef DlgDirSelectEx
+#undef DlgDirListComboBox
+#undef DlgDirSelectComboBoxEx
+#undef DefFrameProc
+#undef DefMDIChildProc
+#undef CreateMDIWindow
+#undef WinHelp
+#undef ChangeDisplaySettings
+#undef ChangeDisplaySettingsEx
+#undef EnumDisplaySettings
+#undef EnumDisplayDevices
+#undef SystemParametersInfo
+#undef GetMonitorInfo
+#undef GetWindowModuleFileName
+#undef RealGetWindowClass
#undef GetAltTabInfo
#undef GetCalendarInfo
#undef GetDateFormat
@@ -369,10 +369,8 @@
// Win32 Fusion API's
#undef QueryActCtxW
-
#endif // !defined(__TODO_PORT_TO_WRAPPERS__)
-
//
// NT supports the wide entry points. So we redefine the wrappers right back
// to the *W entry points as macros. This way no client code needs a wrapper on NT.
@@ -385,9 +383,6 @@
#define WszCryptVerifySignature CryptVerifySignatureW
// winbase.h
-#define WszGetBinaryType GetBinaryTypeW
-#define WszGetShortPathName GetShortPathNameW
-#define WszGetLongPathName GetLongPathNameW
#define WszGetEnvironmentStrings GetEnvironmentStringsW
#define WszFreeEnvironmentStrings FreeEnvironmentStringsW
#ifndef USE_FORMATMESSAGE_WRAPPER
@@ -396,8 +391,6 @@
#define WszFormatMessage CCompRC::FormatMessage
#endif
#define WszCreateMailslot CreateMailslotW
-#define WszEncryptFile EncryptFileW
-#define WszDecryptFile DecryptFileW
#define WszOpenRaw OpenRawW
#define WszQueryRecoveryAgents QueryRecoveryAgentsW
#define Wszlstrcmp lstrcmpW
@@ -413,16 +406,11 @@
#define WszCreateFileMapping CreateFileMappingW
#define WszOpenFileMapping OpenFileMappingW
#define WszGetLogicalDriveStrings GetLogicalDriveStringsW
-#define WszLoadLibrary(_filename) LoadLibraryExW((_filename), NULL, 0)
-#define WszLoadLibraryEx LoadLibraryExW
-#define WszSetDllDirectory SetDllDirectoryW
-#define WszGetModuleFileName GetModuleFileNameW
#define WszGetModuleHandle GetModuleHandleW
#define WszGetModuleHandleEx GetModuleHandleExW
#define WszFatalAppExit FatalAppExitW
#define WszGetStartupInfo GetStartupInfoW
#define WszGetCommandLine GetCommandLineW
-#define WszGetEnvironmentVariable GetEnvironmentVariableW
#define WszSetEnvironmentVariable SetEnvironmentVariableW
#define WszExpandEnvironmentStrings ExpandEnvironmentStringsW
#define WszOutputDebugString OutputDebugStringW
@@ -455,37 +443,12 @@
#define WszWritePrivateProfileStruct WritePrivateProfileStructW
#define WszGetDriveType GetDriveTypeW
#define WszGetSystemDirectory GetSystemDirectoryW
-#define WszGetTempPath GetTempPathW
-#define WszGetTempFileName GetTempFileNameW
#define WszGetWindowsDirectory GetWindowsDirectoryW
-#define WszSetCurrentDirectory SetCurrentDirectoryW
-#define WszGetCurrentDirectory GetCurrentDirectoryW
#define WszGetDiskFreeSpace GetDiskFreeSpaceW
#define WszGetDiskFreeSpaceEx GetDiskFreeSpaceExW
-#define WszCreateDirectory CreateDirectoryW
-#define WszCreateDirectoryEx CreateDirectoryExW
-#define WszRemoveDirectory RemoveDirectoryW
-#define WszGetFullPathName GetFullPathNameW
#define WszDefineDosDevice DefineDosDeviceW
#define WszQueryDosDevice QueryDosDeviceW
-#define WszCreateFile CreateFileW
-#define WszSetFileAttributes SetFileAttributesW
-#define WszGetFileAttributes GetFileAttributesW
-#define WszGetFileAttributesEx GetFileAttributesExW
-#define WszGetCompressedFileSize GetCompressedFileSizeW
-#define WszDeleteFile DeleteFileW
-#define WszFindFirstFileEx FindFirstFileExW
-#define WszFindFirstFile FindFirstFileW
-#define WszFindNextFile FindNextFileW
-#define WszSearchPath SearchPathW
-#define WszCopyFile CopyFileW
-#define WszCopyFileEx CopyFileExW
-#define WszMoveFile MoveFileW
-#define WszMoveFileEx MoveFileExW
-#define WszMoveFileWithProgress MoveFileWithProgressW
-#define WszCreateSymbolicLink CreateSymbolicLinkW
#define WszQuerySymbolicLink QuerySymbolicLinkW
-#define WszCreateHardLink CreateHardLinkW
#define WszCreateNamedPipe CreateNamedPipeW
#define WszGetNamedPipeHandleState GetNamedPipeHandleStateW
#define WszCallNamedPipe CallNamedPipeW
@@ -507,9 +470,6 @@
#define WszObjectCloseAuditAlarm ObjectCloseAuditAlarmW
#define WszObjectDeleteAuditAlarm ObjectDeleteAuditAlarmW
#define WszPrivilegedServiceAuditAlarm PrivilegedServiceAuditAlarmW
-#define WszSetFileSecurity SetFileSecurityW
-#define WszGetFileSecurity GetFileSecurityW
-#define WszFindFirstChangeNotification FindFirstChangeNotificationW
#define WszIsBadStringPtr __DO_NOT_USE__WszIsBadStringPtr__
#if !defined(FEATURE_CORESYSTEM) || defined(CROSSGEN_COMPILE)
#define WszLookupAccountSid LookupAccountSidW
@@ -678,7 +638,6 @@
#define WszRegQueryValueExTrue RegQueryValueExW
#define WszRegQueryStringValueEx RegQueryValueExW
-
#ifndef FEATURE_CORECLR
#define WszRegDeleteKey RegDeleteKeyW
#define WszRegCreateKeyEx ClrRegCreateKeyEx
@@ -723,13 +682,66 @@
#define _T(str) W(str)
#endif
-
// on win98 and higher
#define Wszlstrlen lstrlenW
#define Wszlstrcpy lstrcpyW
#define Wszlstrcat lstrcatW
-
+//File and Directory Functions which need special handling for LongFile Names
+//Note only the functions which are currently used are defined
+#define WszLoadLibrary LoadLibraryExWrapper
+#define WszLoadLibraryEx LoadLibraryExWrapper
+#define WszCreateFile CreateFileWrapper
+#define WszSetFileAttributes SetFileAttributesWrapper
+#define WszGetFileAttributes GetFileAttributesWrapper
+#define WszGetFileAttributesEx GetFileAttributesExWrapper
+#define WszDeleteFile DeleteFileWrapper
+#define WszFindFirstFileEx FindFirstFileExWrapper
+#define WszFindNextFile FindNextFileW
+#define WszCopyFile CopyFileWrapper
+#define WszCopyFileEx CopyFileExWrapper
+#define WszMoveFile MoveFileWrapper
+#define WszMoveFileEx MoveFileExWrapper
+#define WszCreateDirectory CreateDirectoryWrapper
+#define WszRemoveDirectory RemoveDirectoryWrapper
+#define WszCreateHardLink CreateHardLinkWrapper
+
+//Can not use extended syntax
+#define WszGetFullPathName GetFullPathNameW
+
+//Long Files will not work on these till redstone
+#define WszGetCurrentDirectory GetCurrentDirectoryWrapper
+#define WszGetTempFileName GetTempFileNameWrapper
+#define WszGetTempPath GetTempPathWrapper
+
+//APIS which have a buffer as an out parameter
+#define WszGetEnvironmentVariable GetEnvironmentVariableWrapper
+#define WszSearchPath SearchPathWrapper
+#define WszGetShortPathName GetShortPathNameWrapper
+#define WszGetLongPathName GetLongPathNameWrapper
+#define WszGetModuleFileName GetModuleFileNameWrapper
+
+//NOTE: IF the following API's are enabled ensure that they can work with LongFile Names
+//See the usage and implementation of above API's
+//
+//#define WszGetCompressedFileSize GetCompressedFileSizeW
+//#define WszMoveFileWithProgress MoveFileWithProgressW
+//#define WszEncryptFile EncryptFileW
+//#define WszDecryptFile DecryptFileW
+//#define WszSetFileSecurity SetFileSecurityW
+//#define WszGetFileSecurity GetFileSecurityW
+//#define WszFindFirstChangeNotification FindFirstChangeNotificationW
+//#define WszSetDllDirectory SetDllDirectoryW
+//#define WszSetCurrentDirectory SetCurrentDirectoryW
+//#define WszCreateDirectoryEx CreateDirectoryExW
+//#define WszCreateSymbolicLink CreateSymbolicLinkW
+//#define WszGetBinaryType GetBinaryTypeWrapper //Coresys does not seem to have this API
+
+#if FEATURE_PAL
+#define WszFindFirstFile FindFirstFileW
+#else
+#define WszFindFirstFile(_lpFileName_, _lpFindData_) FindFirstFileExWrapper(_lpFileName_, FindExInfoStandard, _lpFindData_, FindExSearchNameMatch, NULL, 0)
+#endif //FEATURE_PAL
//*****************************************************************************
// Prototypes for API's.
//*****************************************************************************
@@ -746,7 +758,7 @@ inline DWORD GetMaxDBCSCharByteSize()
EnsureCharSetInfoInitialized();
_ASSERTE(g_dwMaxDBCSCharByteSize != 0);
- return (g_dwMaxDBCSCharByteSize);
+ return (g_dwMaxDBCSCharByteSize);
#else // FEATURE_PAL
return 3;
#endif // FEATURE_PAL
@@ -758,7 +770,7 @@ BOOL RunningInteractive();
#define RunningInteractive() FALSE
#endif // !FEATURE_PAL
-// Determines if the process is running as Local System or as a service. Note that this function uses the
+// Determines if the process is running as Local System or as a service. Note that this function uses the
// process' identity and not the thread's (if the thread is impersonating).
//
// If the function succeeds, it returns ERROR_SUCCESS, else it returns the error code returned by GetLastError()
@@ -768,7 +780,6 @@ DWORD RunningAsLocalSystemOrService(OUT BOOL& fIsLocalSystemOrService);
#define Wsz_mbstowcs(szOut, szIn, iSize) WszMultiByteToWideChar(CP_ACP, 0, szIn, -1, szOut, iSize)
#endif
-
#ifndef Wsz_wcstombs
#define Wsz_wcstombs(szOut, szIn, iSize) WszWideCharToMultiByte(CP_ACP, 0, szIn, -1, szOut, iSize, 0, 0)
#endif
@@ -815,11 +826,11 @@ DWORD WszGetProcessHandleCount();
#define InterlockedOr _InterlockedOr
//
-// There is no _InterlockedCompareExchangePointer intrinsic in VC++ for x86.
+// There is no _InterlockedCompareExchangePointer intrinsic in VC++ for x86.
// winbase.h #defines InterlockedCompareExchangePointer as __InlineInterlockedCompareExchangePointer,
// which calls the Win32 InterlockedCompareExchange, not the intrinsic _InterlockedCompareExchange.
// We want the intrinsic, so we #undef the Windows version of this API, and define our own.
-//
+//
#ifdef InterlockedCompareExchangePointer
#undef InterlockedCompareExchangePointer
#endif
@@ -850,7 +861,7 @@ InterlockedCompareExchangePointer (
#if defined(_X86_) & !defined(InterlockedIncrement64)
-// Interlockedxxx64 that do not have intrinsics are only supported on Windows Server 2003
+// Interlockedxxx64 that do not have intrinsics are only supported on Windows Server 2003
// or higher for X86 so define our own portable implementation
#undef InterlockedIncrement64
@@ -918,7 +929,7 @@ __forceinline LONGLONG __InterlockedExchangeAdd64(LONGLONG volatile * Addend, LO
//
// RtlVerifyVersionInfo() type mask bits
-// Making our copy of type mask bits as the original
+// Making our copy of type mask bits as the original
// macro name are redefined in public\internal\NDP\inc\product_version.h
//
//
@@ -970,11 +981,11 @@ inline int LateboundMessageBoxW(HWND hWnd,
#if defined(FEATURE_CORESYSTEM) && !defined(CROSSGEN_COMPILE)
// Some CoreSystem OSs will support MessageBoxW via an extension library. The following technique is what
// was recommeded by Philippe Joubert from the CoreSystem team.
- HMODULE hGuiExtModule = LoadLibraryExW(W("ext-ms-win-ntuser-gui-l1"), NULL, 0);
+ HMODULE hGuiExtModule = WszLoadLibrary(W("ext-ms-win-ntuser-gui-l1"), NULL, 0);
#else
// Outside of CoreSystem, MessageBoxW lives in User32
HMODULE hGuiExtModule = WszLoadLibrary(W("user32"));
-#endif
+#endif
if (hGuiExtModule)
{
int result = IDCANCEL;
diff --git a/src/md/compiler/disp.cpp b/src/md/compiler/disp.cpp
index 742cf1cfbc..0f0bf88e6d 100644
--- a/src/md/compiler/disp.cpp
+++ b/src/md/compiler/disp.cpp
@@ -78,7 +78,9 @@ Disp::DefineScope(
{
#ifdef FEATURE_METADATA_EMIT
HRESULT hr = S_OK;
-
+ PathString szFileName(PathString::Literal, W("file:"));
+ PathString szFileNameSuffix;
+ DWORD len;
BEGIN_ENTRYPOINT_NOTHROW;
RegMeta *pMeta = 0;
@@ -111,13 +113,13 @@ Disp::DefineScope(
#ifdef ENC_DELTA_HACK
// Testers need this flag for their tests.
- const int prefixLen = 5;
- WCHAR szFileName[256 + prefixLen];
- wcscpy_s(szFileName, 256 + prefixLen, W("file:"));
- WCHAR *szFileNamePrefix = szFileName + prefixLen;
- DWORD cchFileNamePrefix = (DWORD) ((sizeof(szFileName)/sizeof(WCHAR))-prefixLen);
- DWORD len = WszGetEnvironmentVariable(W("COMP_ENC_OPENSCOPE"), szFileNamePrefix, cchFileNamePrefix);
- _ASSERTE(len < cchFileNamePrefix);
+
+ EX_TRY{
+ len = WszGetEnvironmentVariable(W("COMP_ENC_OPENSCOPE"), szFileNameSuffix);
+ szFileName.Append(szFileNameSuffix);
+ }
+ EX_CATCH_HRESULT(hr);
+
if (len > 0)
{
// _ASSERTE(!"ENC override on DefineScope");
@@ -150,7 +152,7 @@ Disp::DefineScope(
BOOL fResult = SUCCEEDED(hr);
// print out a message so people know what's happening
printf("Defining scope for EnC using %S %s\n",
- szFileName+prefixLen, fResult ? "succeeded" : "failed");
+ szFileNameSuffix, fResult ? "succeeded" : "failed");
goto ErrExit;
}
diff --git a/src/md/compiler/mdutil.cpp b/src/md/compiler/mdutil.cpp
index 691cd793c9..2e01258bea 100644
--- a/src/md/compiler/mdutil.cpp
+++ b/src/md/compiler/mdutil.cpp
@@ -473,20 +473,18 @@ HRESULT CORPATHService::GetClassFromCORPath(
IUnknown **ppIScope, // [OUT] Scope in which the TypeRef resolves.
mdTypeDef *ptd) // [OUT] typedef corresponding the typeref
{
- WCHAR rcCorPath[1024] = {W('\0')}; // The CORPATH environment variable.
- LPWSTR szCorPath = rcCorPath; // Used to parse CORPATH.
+ PathString rcCorPath; // The CORPATH environment variable.
+ LPWSTR szCorPath; // Used to parse CORPATH.
int iLen; // Length of the directory.
- WCHAR rcCorDir[_MAX_PATH]; // Buffer for the directory.
+ PathString rcCorDir; // Buffer for the directory.
WCHAR *temp; // Used as a parsing temp.
WCHAR *szSemiCol;
// Get the CORPATH environment variable.
- if (WszGetEnvironmentVariable(W("CORPATH"), rcCorPath,
- sizeof(rcCorPath) / sizeof(WCHAR)))
+ if (WszGetEnvironmentVariable(W("CORPATH"), rcCorPath))
{
- // Force nul termination.
- rcCorPath[lengthof(rcCorPath)-1] = 0;
-
+ NewArrayHolder<WCHAR> szCorPathHolder = rcCorPath.GetCopyOfUnicodeString();
+ szCorPath = szCorPathHolder.GetValue();
// Try each directory in the path.
for(;*szCorPath != W('\0');)
{
@@ -502,12 +500,11 @@ HRESULT CORPATHService::GetClassFromCORPath(
temp = szCorPath;
szCorPath += wcslen(temp);
}
- if ((iLen = (int)wcslen(temp)) >= _MAX_PATH)
- continue;
- wcscpy_s(rcCorDir, COUNTOF(rcCorDir), temp);
+
+ rcCorDir.Set(temp);
// Check if we can find the class in the directory.
- if (CORPATHService::GetClassFromDir(wzClassname, rcCorDir, iLen, tr, pCommon, riid, ppIScope, ptd) == S_OK)
+ if (CORPATHService::GetClassFromDir(wzClassname, rcCorDir, tr, pCommon, riid, ppIScope, ptd) == S_OK)
return S_OK;
}
}
@@ -516,24 +513,20 @@ HRESULT CORPATHService::GetClassFromCORPath(
// some headaches right now, so we'll give them a little time to transition.</TODO>
// Try the current directory first.
- if ((iLen = WszGetCurrentDirectory(_MAX_PATH, rcCorDir)) > 0 &&
- CORPATHService::GetClassFromDir(wzClassname, rcCorDir, iLen, tr, pCommon, riid, ppIScope, ptd) == S_OK)
+ if ((iLen = WszGetCurrentDirectory( rcCorDir)) > 0 &&
+ CORPATHService::GetClassFromDir(wzClassname, rcCorDir, tr, pCommon, riid, ppIScope, ptd) == S_OK)
{
return S_OK;
}
-
+
// Try the app directory next.
- if ((iLen = WszGetModuleFileName(NULL, rcCorDir, _MAX_PATH)) > 0)
+ if ((iLen = WszGetModuleFileName(NULL, rcCorDir)) > 0)
{
- // Back up to the last path separator.
- while (--iLen >= 0 && rcCorDir[iLen] != W('\\') && rcCorDir[iLen] != W('/'))
- {
- }
- if (iLen > 0 &&
- CORPATHService::GetClassFromDir(
+
+ if(SUCCEEDED(CopySystemDirectory(rcCorDir, rcCorDir)) &&
+ CORPATHService::GetClassFromDir(
wzClassname,
rcCorDir,
- iLen,
tr,
pCommon,
riid,
@@ -550,15 +543,11 @@ HRESULT CORPATHService::GetClassFromCORPath(
//*****************************************************************************
// This is used in conjunction with GetClassFromCORPath. See it for details
-// of the algorithm. One thing to note is that the dir passed here must be
-// _MAX_PATH size and will be written to by this routine. This routine will
-// frequently leave junk at the end of the directory string and dir[iLen] may
-// not be '\0' on return.
+// of the algorithm.
//*****************************************************************************
HRESULT CORPATHService::GetClassFromDir(
__in __in_z LPWSTR wzClassname, // Fully qualified class name.
- __in __in_z LPWSTR dir, // Directory to try.
- int iLen, // Length of the directory.
+ __in SString& directory, // Directory to try. at most appended with a '\\'
mdTypeRef tr, // TypeRef to resolve.
IMetaModelCommon *pCommon, // Scope in which the TypeRef is defined.
REFIID riid,
@@ -569,58 +558,48 @@ HRESULT CORPATHService::GetClassFromDir(
int iTmp;
bool bContinue; // Flag to check if the for loop should end.
LPWSTR wzSaveClassname = NULL; // Saved offset into the class name string.
- int iSaveLen = 0; // Saved length of the dir string.
-
- PREFIX_ASSUME(iLen >= 0);
// Process the class name appending each segment of the name to the
// directory until we find a DLL.
+ PathString dir;
+ if (!directory.EndsWith(DIRECTORY_SEPARATOR_CHAR_W))
+ {
+ directory.Append(DIRECTORY_SEPARATOR_CHAR_W);
+ }
+
for(;;)
{
bContinue = false;
+ dir.Set(directory);
+
if ((temp = wcschr(wzClassname, NAMESPACE_SEPARATOR_WCHAR)) != NULL)
{
- iTmp = (int) (temp - wzClassname);
- // Check for buffer overflow with correct integer overflow check.
- // "if (iLen + 5 + iTmp >= _MAX_PATH)"
- if (ovadd_ge(iLen, iTmp, (_MAX_PATH - 5)))
- break;
+ *temp = W('\0'); //terminate with null so that it can be appended
+ dir.Append(wzClassname);
+ *temp = NAMESPACE_SEPARATOR_WCHAR; //recover the '.'
- // Append the next segment from the class spec to the directory.
- dir[iLen++] = W('\\');
- wcsncpy_s(dir+iLen, iTmp+1, wzClassname, iTmp);
- iLen += iTmp;
- dir[iLen] = W('\0');
wzClassname = temp+1;
-
// Check if a directory by this name exists.
DWORD iAttrs = WszGetFileAttributes(dir);
if (iAttrs != 0xffffffff && (iAttrs & FILE_ATTRIBUTE_DIRECTORY))
{
// Next element in the class spec.
bContinue = true;
- iSaveLen = iLen;
wzSaveClassname = wzClassname;
}
}
else
{
- iTmp = (int)wcslen(wzClassname);
- // Check for buffer overflow with correct integer overflow check.
- // "if (iLen + 5 + iTmp >= _MAX_PATH)"
- if (ovadd_ge(iLen, iTmp, (_MAX_PATH - 5)))
- break;
- dir[iLen++] = W('\\');
- wcscpy_s(dir+iLen, iTmp+1, wzClassname);
+ dir.Append(wzClassname);
// Advance past the class name.
- iLen += iTmp;
+ iTmp = (int)wcslen(wzClassname);
wzClassname += iTmp;
}
// Try to load the image.
- wcscpy_s(dir+iLen, 5, W(".dll"));
-
+ dir.Append(W(".dll"));
+
// OpenScope given the dll name and make sure that the class is defined in the module.
if ( SUCCEEDED( CORPATHService::FindTypeDef(dir, tr, pCommon, riid, ppIScope, ptd) ) )
{
@@ -632,21 +611,25 @@ HRESULT CORPATHService::GetClassFromDir(
{
// Find the length of the next class name element.
if ((temp = wcschr(wzClassname, NAMESPACE_SEPARATOR_WCHAR)) == NULL)
+ {
temp = wzClassname + wcslen(wzClassname);
-
- iTmp = (int) (temp - wzClassname);
- // Check for buffer overflow.
- if ((iLen + 5 + iTmp) >= _MAX_PATH)
- break;
+ }
// Tack on ".element.dll"
- dir[iLen++] = W('.');
- wcsncpy_s(dir+iLen, iTmp+1, wzClassname, iTmp);
- iLen += iTmp;
-
+ SString::Iterator iter = dir.End();
+ BOOL findperiod = dir.FindBack(iter, NAMESPACE_SEPARATOR_WCHAR);
+ _ASSERTE(findperiod);
+ iter++;
+ dir.Truncate(iter);
+
+ WCHAR save = *temp;
+ *temp = W('\0');
+ dir.Append(wzClassname); //element
+ *temp = save;
+
// Try to load the image.
- wcscpy_s(dir+iLen, 5, W(".dll"));
-
+ dir.Append(W(".dll"));
+
// OpenScope given the dll name and make sure that the class is defined in the module.
if ( SUCCEEDED( CORPATHService::FindTypeDef(dir, tr, pCommon, riid, ppIScope, ptd) ) )
{
@@ -660,7 +643,7 @@ HRESULT CORPATHService::GetClassFromDir(
}
if (bContinue)
{
- iLen = iSaveLen;
+
wzClassname = wzSaveClassname;
}
else
@@ -679,7 +662,7 @@ HRESULT CORPATHService::GetClassFromDir(
//
//*************************************************************
HRESULT CORPATHService::FindTypeDef(
- __in __in_z LPWSTR wzModule, // name of the module that we are going to open
+ __in __in_z LPCWSTR wzModule, // name of the module that we are going to open
mdTypeRef tr, // TypeRef to resolve.
IMetaModelCommon * pCommon, // Scope in which the TypeRef is defined.
REFIID riid,
diff --git a/src/md/compiler/mdutil.h b/src/md/compiler/mdutil.h
index eda2bca877..58cdbf108a 100644
--- a/src/md/compiler/mdutil.h
+++ b/src/md/compiler/mdutil.h
@@ -43,9 +43,8 @@ public:
mdTypeDef *ptd); // [OUT] typedef corresponding the typeref
static HRESULT GetClassFromDir(
- __in __in_z LPWSTR wzClassname, // Fully qualified class name.
- __in __in_z LPWSTR dir, // Directory to try.
- int iLen, // Length of the directory.
+ __in __in_z LPWSTR wzClassname, // Fully qualified class name.
+ __in SString& dir, // Directory to try.
mdTypeRef tr, // TypeRef to resolve.
IMetaModelCommon *pCommon, // Scope in which the TypeRef is defined.
REFIID riid,
@@ -53,7 +52,7 @@ public:
mdTypeDef *ptd); // [OUT] typedef
static HRESULT FindTypeDef(
- __in __in_z LPWSTR wzModule, // name of the module that we are going to open
+ __in __in_z LPCWSTR wzModule, // name of the module that we are going to open
mdTypeRef tr, // TypeRef to resolve.
IMetaModelCommon *pCommon, // Scope in which the TypeRef is defined.
REFIID riid,
diff --git a/src/pal/inc/pal.h b/src/pal/inc/pal.h
index cb39a885a5..b5f62742a4 100644
--- a/src/pal/inc/pal.h
+++ b/src/pal/inc/pal.h
@@ -1172,6 +1172,19 @@ typedef enum _GET_FILEEX_INFO_LEVELS {
GetFileExInfoStandard
} GET_FILEEX_INFO_LEVELS;
+typedef enum _FINDEX_INFO_LEVELS {
+ FindExInfoStandard,
+ FindExInfoBasic,
+ FindExInfoMaxInfoLevel
+} FINDEX_INFO_LEVELS;
+
+typedef enum _FINDEX_SEARCH_OPS {
+ FindExSearchNameMatch,
+ FindExSearchLimitToDirectories,
+ FindExSearchLimitToDevices,
+ FindExSearchMaxSearchOp
+} FINDEX_SEARCH_OPS;
+
typedef struct _WIN32_FILE_ATTRIBUTE_DATA {
DWORD dwFileAttributes;
FILETIME ftCreationTime;
diff --git a/src/pal/src/loader/module.cpp b/src/pal/src/loader/module.cpp
index e380e2ed0e..d05e272227 100644
--- a/src/pal/src/loader/module.cpp
+++ b/src/pal/src/loader/module.cpp
@@ -541,6 +541,7 @@ GetModuleFileNameW(
if (name_length >= (INT)nSize)
{
TRACE("Buffer too small (%u) to copy module's file name (%u).\n", nSize, name_length);
+ retval = (INT)nSize;
SetLastError(ERROR_INSUFFICIENT_BUFFER);
goto done;
}
diff --git a/src/strongname/api/strongnamecoreclr.cpp b/src/strongname/api/strongnamecoreclr.cpp
index 1b81ff6252..1ed7f0e10c 100644
--- a/src/strongname/api/strongnamecoreclr.cpp
+++ b/src/strongname/api/strongnamecoreclr.cpp
@@ -47,10 +47,10 @@ IExecutionEngine * __stdcall SnIEE()
return ApiShim<IEEFn_t>("IEE")();
}
-STDAPI SnGetCorSystemDirectory(_In_z_ LPWSTR pbuffer, DWORD cchBuffer, DWORD* dwLength)
+STDAPI SnGetCorSystemDirectory(SString& pbuffer)
{
- typedef HRESULT (__stdcall *GetCorSystemDirectoryFn_t)(LPWSTR, DWORD, DWORD *);
- return ApiShim<GetCorSystemDirectoryFn_t>("GetCORSystemDirectory")(pbuffer, cchBuffer, dwLength);
+ typedef HRESULT (__stdcall *GetCorSystemDirectoryFn_t)(SString&);
+ return ApiShim<GetCorSystemDirectoryFn_t>("GetCORSystemDirectory")(pbuffer);
}
//
diff --git a/src/tools/crossgen/crossgen.cpp b/src/tools/crossgen/crossgen.cpp
index 1d136b684f..93d52661fb 100644
--- a/src/tools/crossgen/crossgen.cpp
+++ b/src/tools/crossgen/crossgen.cpp
@@ -282,7 +282,7 @@ bool StringEndsWith(LPCWSTR pwzString, LPCWSTR pwzCandidate)
// When using the Phone binding model (TrustedPlatformAssemblies), automatically
// detect which path mscorlib.[ni.]dll lies in.
//
-bool ComputeMscorlibPathFromTrustedPlatformAssemblies(_In_z_ LPWSTR pwzMscorlibPath, DWORD cbMscorlibPath, LPCWSTR pwzTrustedPlatformAssemblies)
+bool ComputeMscorlibPathFromTrustedPlatformAssemblies(SString& pwzMscorlibPath, LPCWSTR pwzTrustedPlatformAssemblies)
{
LPWSTR wszTrustedPathCopy = new WCHAR[wcslen(pwzTrustedPlatformAssemblies) + 1];
wcscpy_s(wszTrustedPathCopy, wcslen(pwzTrustedPlatformAssemblies) + 1, pwzTrustedPlatformAssemblies);
@@ -302,18 +302,17 @@ bool ComputeMscorlibPathFromTrustedPlatformAssemblies(_In_z_ LPWSTR pwzMscorlibP
if (StringEndsWith(wszSingleTrustedPath, DIRECTORY_SEPARATOR_STR_W W("mscorlib.dll")) ||
StringEndsWith(wszSingleTrustedPath, DIRECTORY_SEPARATOR_STR_W W("mscorlib.ni.dll")))
{
- wcscpy_s(pwzMscorlibPath, cbMscorlibPath, wszSingleTrustedPath);
+ pwzMscorlibPath.Set(wszSingleTrustedPath);
+ SString::Iterator pwzSeparator = pwzMscorlibPath.End();
+ bool retval = true;
- LPWSTR pwzSeparator = wcsrchr(pwzMscorlibPath, DIRECTORY_SEPARATOR_CHAR_W);
- if (pwzSeparator == NULL)
+ if (!SUCCEEDED(CopySystemDirectory(pwzMscorlibPath, pwzMscorlibPath)))
{
- delete [] wszTrustedPathCopy;
- return false;
+ retval = false;
}
- pwzSeparator[1] = W('\0'); // after '\'
delete [] wszTrustedPathCopy;
- return true;
+ return retval;
}
wszSingleTrustedPath = wcstok_s(NULL, PATH_SEPARATOR_STR_W, &context);
@@ -961,7 +960,7 @@ int _cdecl wmain(int argc, __in_ecount(argc) WCHAR **argv)
PrintLogoHelper();
}
- WCHAR wzTrustedPathRoot[MAX_LONGPATH];
+ PathString wzTrustedPathRoot;
#ifdef FEATURE_CORECLR
SString ssTPAList;
@@ -985,9 +984,9 @@ int _cdecl wmain(int argc, __in_ecount(argc) WCHAR **argv)
if (pwzTrustedPlatformAssemblies != nullptr)
{
- if (ComputeMscorlibPathFromTrustedPlatformAssemblies(wzTrustedPathRoot, MAX_LONGPATH, pwzTrustedPlatformAssemblies))
+ if (ComputeMscorlibPathFromTrustedPlatformAssemblies(wzTrustedPathRoot, pwzTrustedPlatformAssemblies))
{
- pwzPlatformAssembliesPaths = wzTrustedPathRoot;
+ pwzPlatformAssembliesPaths = wzTrustedPathRoot.GetUnicode();
SetMscorlibPath(pwzPlatformAssembliesPaths);
}
}
@@ -995,21 +994,23 @@ int _cdecl wmain(int argc, __in_ecount(argc) WCHAR **argv)
if (pwzPlatformAssembliesPaths == NULL)
{
- if (!WszGetModuleFileName(NULL, wzTrustedPathRoot, MAX_LONGPATH))
+ if (!WszGetModuleFileName(NULL, wzTrustedPathRoot))
{
ERROR_WIN32(W("Error: GetModuleFileName failed (%d)\n"), GetLastError());
exit(CLR_INIT_ERROR);
}
-
- wchar_t* pszSep = wcsrchr(wzTrustedPathRoot, DIRECTORY_SEPARATOR_CHAR_W);
- if (pszSep == NULL)
+
+ if (SUCCEEDED(CopySystemDirectory(wzTrustedPathRoot, wzTrustedPathRoot)))
+ {
+ pwzPlatformAssembliesPaths = wzTrustedPathRoot.GetUnicode();
+ }
+ else
{
ERROR_HR(W("Error: wcsrchr returned NULL; GetModuleFileName must have given us something bad\n"), E_UNEXPECTED);
exit(CLR_INIT_ERROR);
}
- *pszSep = '\0';
-
- pwzPlatformAssembliesPaths = wzTrustedPathRoot;
+
+
}
// Initialize the logger
diff --git a/src/utilcode/CMakeLists.txt b/src/utilcode/CMakeLists.txt
index 117d4790f0..9aeb243790 100644
--- a/src/utilcode/CMakeLists.txt
+++ b/src/utilcode/CMakeLists.txt
@@ -60,6 +60,7 @@ set(UTILCODE_COMMON_SOURCES
debug.cpp
pedecoder.cpp
winfix.cpp
+ longfilepathwrappers.cpp
)
# These source file do not yet compile on Linux.
diff --git a/src/utilcode/UtilCode.vcproj b/src/utilcode/UtilCode.vcproj
index 3f147725b8..d43c2a02c3 100644
--- a/src/utilcode/UtilCode.vcproj
+++ b/src/utilcode/UtilCode.vcproj
@@ -600,6 +600,10 @@
RelativePath=".\winfix.cpp"
>
</File>
+ <File
+ RelativePath=".\longfilepathwrappers.cpp"
+ >
+ </File>
</Files>
<Globals>
</Globals>
diff --git a/src/utilcode/UtilCode.vcxproj b/src/utilcode/UtilCode.vcxproj
index d0926fd8c6..b0cca8dd70 100644
--- a/src/utilcode/UtilCode.vcxproj
+++ b/src/utilcode/UtilCode.vcxproj
@@ -435,6 +435,7 @@
<ClCompile Include="utilmessagebox.cpp" />
<ClCompile Include="UTSEM.cpp" />
<ClCompile Include="winfix.cpp" />
+ <ClCompile Include="longfilepathwrappers.cpp" />
</ItemGroup>
<ItemGroup>
<ClInclude Include="hostimpl.h" />
@@ -444,4 +445,4 @@
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>
-</Project> \ No newline at end of file
+</Project>
diff --git a/src/utilcode/ccomprc.cpp b/src/utilcode/ccomprc.cpp
index eccf42d98c..a4c79fc127 100644
--- a/src/utilcode/ccomprc.cpp
+++ b/src/utilcode/ccomprc.cpp
@@ -918,13 +918,13 @@ HRESULT CCompRC::LoadResourceFile(HRESOURCEDLL * pHInst, LPCWSTR lpFileName)
// Load the library for this thread's current language
// Called once per language.
// Search order is:
-// 1. Dll in localized path (<dir of this module>\<lang name (en-US format)>\mscorrc.dll)
-// 2. Dll in localized (parent) path (<dir of this module>\<lang name> (en format)\mscorrc.dll)
-// 3. Dll in root path (<dir of this module>\mscorrc.dll)
+// 1. Dll in localized path (<dir passed>\<lang name (en-US format)>\mscorrc.dll)
+// 2. Dll in localized (parent) path (<dir passed>\<lang name> (en format)\mscorrc.dll)
+// 3. Dll in root path (<dir passed>\mscorrc.dll)
// 4. Dll in current path (<current dir>\mscorrc.dll)
//*****************************************************************************
HRESULT CCompRC::LoadLibraryHelper(HRESOURCEDLL *pHInst,
- __out_ecount(rcPathSize) __out_z WCHAR *rcPath, const DWORD rcPathSize)
+ SString& rcPath)
{
CONTRACTL
{
@@ -937,19 +937,11 @@ HRESULT CCompRC::LoadLibraryHelper(HRESOURCEDLL *pHInst,
CONTRACTL_END;
HRESULT hr = E_FAIL;
-
- WCHAR rcDrive[_MAX_DRIVE]; // Volume name.
- WCHAR rcDir[_MAX_PATH]; // Directory.
-
- size_t rcDriveLen;
- size_t rcDirLen;
size_t rcPartialPathLen;
-
+
_ASSERTE(m_pResourceFile != NULL);
- size_t rcMscorrcLen = wcslen(m_pResourceFile);
-
// must initialize before calling SString::Empty()
SString::Startup();
@@ -972,58 +964,43 @@ HRESULT CCompRC::LoadLibraryHelper(HRESOURCEDLL *pHInst,
if (hr == E_OUTOFMEMORY)
return hr;
-
- rcDir[0] = W('\0');
- rcDrive[0] = W('\0');
- rcPath[rcPathSize - 1] = 0;
-
- SplitPath(rcPath, rcDrive, _MAX_DRIVE, rcDir, _MAX_PATH, 0, 0, 0, 0);
- rcDriveLen = wcslen(rcDrive);
- rcDirLen = wcslen(rcDir);
-
- // Length that does not include culture name length
- rcPartialPathLen = rcDriveLen + rcDirLen + rcMscorrcLen + 1;
-
-
- for (DWORD i=0; i< cultureNames.GetCount();i++)
+ EX_TRY
{
- SString& sLang = cultureNames[i];
- if (rcPartialPathLen + sLang.GetCount() <= rcPathSize)
+ for (DWORD i=0; i< cultureNames.GetCount();i++)
{
- wcscpy_s(rcPath, rcDriveLen+1, rcDrive);
- WCHAR *rcPathPtr = rcPath + rcDriveLen;
+ SString& sLang = cultureNames[i];
+
+ PathString rcPathName(rcPath);
- wcscpy_s(rcPathPtr, rcDirLen+1, rcDir);
- rcPathPtr += rcDirLen;
+ if (!rcPathName.EndsWith(W("\\")))
+ {
+ rcPathName.Append(W("\\"));
+ }
- if(!sLang.IsEmpty())
+ if (!sLang.IsEmpty())
{
- wcscpy_s(rcPathPtr, sLang.GetCount()+1, sLang);
- wcscpy_s(rcPathPtr+ sLang.GetCount(), rcMscorrcLen+1, W("\\"));
- wcscpy_s(rcPathPtr + sLang.GetCount()+1, rcMscorrcLen+1, m_pResourceFile);
+ rcPathName.Append(sLang);
+ rcPathName.Append(W("\\"));
+ rcPathName.Append(m_pResourceFile);
}
else
{
- wcscpy_s(rcPathPtr + sLang.GetCount(), rcMscorrcLen+1, m_pResourceFile);
+ rcPathName.Append(m_pResourceFile);
}
// Feedback for debugging to eliminate unecessary loads.
- DEBUG_STMT(DbgWriteEx(W("Loading %s to load strings.\n"), rcPath));
+ DEBUG_STMT(DbgWriteEx(W("Loading %s to load strings.\n"), rcPath.GetUnicode()));
// Load the resource library as a data file, so that the OS doesn't have
// to allocate it as code. This only works so long as the file contains
// only strings.
- hr = LoadResourceFile(pHInst, rcPath);
+ hr = LoadResourceFile(pHInst, rcPathName);
if (SUCCEEDED(hr))
break;
- }
- else
- {
- _ASSERTE(!"Buffer not big enough");
- hr = E_FAIL;
-
- }
- };
+
+ }
+ }
+ EX_CATCH_HRESULT(hr);
// Last ditch search effort in current directory
if (FAILED(hr)) {
@@ -1035,12 +1012,12 @@ HRESULT CCompRC::LoadLibraryHelper(HRESOURCEDLL *pHInst,
// Two-stage approach:
// First try module directory, then try CORSystemDirectory for default resource
-HRESULT CCompRC::LoadLibrary(HRESOURCEDLL * pHInst)
+HRESULT CCompRC::LoadLibraryThrows(HRESOURCEDLL * pHInst)
{
CONTRACTL
{
GC_NOTRIGGER;
- NOTHROW;
+ THROWS;
#ifdef MODE_PREEMPTIVE
MODE_PREEMPTIVE;
#endif
@@ -1055,26 +1032,28 @@ HRESULT CCompRC::LoadLibrary(HRESOURCEDLL * pHInst)
// The resources are embeded into the .exe itself for crossgen
*pHInst = GetModuleInst();
#else
- WCHAR rcPath[_MAX_PATH]; // Path to resource DLL.
+ PathString rcPath; // Path to resource DLL.
// Try first in the same directory as this dll.
#if defined(FEATURE_CORECLR)
VALIDATECORECLRCALLBACKS();
- DWORD length = 0;
- hr = g_CoreClrCallbacks.m_pfnGetCORSystemDirectory(rcPath, NumItems(rcPath), &length);
+
+ hr = g_CoreClrCallbacks.m_pfnGetCORSystemDirectory(rcPath);
if (FAILED(hr))
return hr;
- hr = LoadLibraryHelper(pHInst, rcPath, NumItems(rcPath));
+ hr = LoadLibraryHelper(pHInst, rcPath);
#else // FEATURE_CORECLR
- if (!WszGetModuleFileName(GetModuleInst(), rcPath, NumItems(rcPath)))
+ if (!WszGetModuleFileName(GetModuleInst(), rcPath))
return HRESULT_FROM_GetLastError();
-
- hr = LoadLibraryHelper(pHInst, rcPath, NumItems(rcPath));
+
+ CopySystemDirectory(rcPath, rcPath);
+
+ hr = LoadLibraryHelper(pHInst, rcPath);
if (hr == E_OUTOFMEMORY)
return hr;
@@ -1096,36 +1075,39 @@ HRESULT CCompRC::LoadLibrary(HRESOURCEDLL * pHInst)
// The reason for using GetRequestedRuntimeInfo is the ability to suppress message boxes
// with RUNTIME_INFO_DONT_SHOW_ERROR_DIALOG.
+ COUNT_T size = MAX_PATH;
hr = LegacyActivationShim::GetRequestedRuntimeInfo(
NULL,
W("v")VER_PRODUCTVERSION_NO_QFE_STR_L,
NULL,
0,
RUNTIME_INFO_UPGRADE_VERSION|RUNTIME_INFO_DONT_SHOW_ERROR_DIALOG|RUNTIME_INFO_CONSIDER_POST_2_0,
- rcPath,
- NumItems(rcPath),
+ rcPath.OpenUnicodeBuffer(size-1),
+ size,
&corSystemPathSize,
rcVersion,
NumItems(rcVersion),
&rcVersionSize);
+ rcPath.CloseBuffer(corSystemPathSize);
+
if (SUCCEEDED(hr))
{
if (rcVersionSize > 0)
{
- wcscat_s(rcPath, NumItems(rcPath), rcVersion) ;
- wcscat_s(rcPath, NumItems(rcPath), W("\\")) ;
+ rcPath.Append(rcVersion);
+ rcPath.Append(W("\\"));
}
}
#else
// If we're hosted, we have the advantage of a CoreClrCallbacks reference.
// More importantly, we avoid calling back to mscoree.dll.
- DWORD cchPath;
- hr = GetClrCallbacks().m_pfnGetCORSystemDirectory(rcPath, NumItems(rcPath), &cchPath);
+
+ hr = GetClrCallbacks().m_pfnGetCORSystemDirectory(rcPath);
#endif
if (SUCCEEDED(hr))
{
- hr = LoadLibraryHelper(pHInst, rcPath, NumItems(rcPath));
+ hr = LoadLibraryHelper(pHInst, rcPath);
}
}
#endif // !DACCESS_COMPILE
@@ -1136,7 +1118,27 @@ HRESULT CCompRC::LoadLibrary(HRESOURCEDLL * pHInst)
return hr;
}
+HRESULT CCompRC::LoadLibrary(HRESOURCEDLL * pHInst)
+{
+ CONTRACTL
+ {
+ GC_NOTRIGGER;
+ NOTHROW;
+#ifdef MODE_PREEMPTIVE
+ MODE_PREEMPTIVE;
+#endif
+ }
+ CONTRACTL_END;
+ HRESULT hr = S_OK;
+ EX_TRY
+ {
+ hr = LoadLibraryThrows(pHInst);
+ }
+ EX_CATCH_HRESULT(hr);
+
+ return hr;
+}
#endif // DACCESS_COMPILE
diff --git a/src/utilcode/debug.cpp b/src/utilcode/debug.cpp
index b1fb16524b..a96aca148a 100644
--- a/src/utilcode/debug.cpp
+++ b/src/utilcode/debug.cpp
@@ -239,8 +239,8 @@ VOID LogAssert(
GetSystemTime(&st);
#endif
- WCHAR exename[300];
- WszGetModuleFileName(NULL, exename, sizeof(exename)/sizeof(WCHAR));
+ PathString exename;
+ WszGetModuleFileName(NULL, exename);
LOG((LF_ASSERT,
LL_FATALERROR,
@@ -259,7 +259,7 @@ VOID LogAssert(
szFile,
iLine,
szExpr));
- LOG((LF_ASSERT, LL_FATALERROR, "RUNNING EXE: %ws\n", exename));
+ LOG((LF_ASSERT, LL_FATALERROR, "RUNNING EXE: %ws\n", exename.GetUnicode()));
}
//*****************************************************************************
diff --git a/src/utilcode/jitperf.cpp b/src/utilcode/jitperf.cpp
index a1b29d5e17..808a10ccde 100644
--- a/src/utilcode/jitperf.cpp
+++ b/src/utilcode/jitperf.cpp
@@ -8,6 +8,7 @@
#include "clrhost.h"
#include "contract.h"
#include "utilcode.h"
+#include "sstring.h"
//=============================================================================
// ALL THE JIT PERF STATS GATHERING CODE IS COMPILED ONLY IF THE ENABLE_JIT_PERF WAS DEFINED.
@@ -62,10 +63,8 @@ void InitJitPerf(void)
CANNOT_TAKE_LOCK;
} CONTRACTL_END;
- wchar_t lpszValue[2];
- DWORD cchValue = 2;
-
- g_fJitPerfOn = WszGetEnvironmentVariable (W("JIT_PERF_OUTPUT"), lpszValue, cchValue);
+ InlineSString<4> lpszValue;
+ g_fJitPerfOn = WszGetEnvironmentVariable (W("JIT_PERF_OUTPUT"), lpszValue);
if (g_fJitPerfOn)
{
g_csJit = ClrCreateCriticalSection(CrstJitPerf,CRST_UNSAFE_ANYMODE);
diff --git a/src/utilcode/longfilepathwrappers.cpp b/src/utilcode/longfilepathwrappers.cpp
new file mode 100644
index 0000000000..0bb473095a
--- /dev/null
+++ b/src/utilcode/longfilepathwrappers.cpp
@@ -0,0 +1,1464 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+#include "stdafx.h"
+#include "windows.h"
+#include "longfilepathwrappers.h"
+#include "sstring.h"
+#include "ex.h"
+
+class LongFile
+{
+private:
+#ifndef FEATURE_PAL
+ static const WCHAR* ExtendedPrefix;
+ static const WCHAR* DevicePathPrefix;
+ static const WCHAR* UNCPathPrefix;
+ static const WCHAR* UNCExtendedPathPrefix;
+ static const WCHAR VolumeSeparatorChar;
+#endif //FEATURE_PAL
+ static const WCHAR LongFile::DirectorySeparatorChar;
+ static const WCHAR LongFile::AltDirectorySeparatorChar;
+public:
+ static BOOL IsExtended(SString & path);
+ static BOOL IsUNCExtended(SString & path);
+ static BOOL ContainsDirectorySeparator(SString & path);
+ static BOOL IsDirectorySeparator(WCHAR c);
+ static BOOL IsPathNotFullyQualified(SString & path);
+ static BOOL IsDevice(SString & path);
+
+ static HRESULT NormalizePath(SString& path);
+};
+
+HMODULE
+LoadLibraryExWrapper(
+ LPCWSTR lpLibFileName,
+ HANDLE hFile,
+ DWORD dwFlags
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ HMODULE ret = NULL;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return NULL;)
+ EX_TRY
+ {
+
+ LongPathString path(LongPathString::Literal, lpLibFileName);
+
+ if (LongFile::IsPathNotFullyQualified(path) || SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+#ifndef FEATURE_PAL
+ //Adding the assert to ensure relative paths which are not just filenames are not used for LoadLibrary Calls
+ _ASSERTE(!LongFile::IsPathNotFullyQualified(path) || !LongFile::ContainsDirectorySeparator(path));
+#endif //FEATURE_PAL
+
+ ret = LoadLibraryExW(path.GetUnicode(), hFile, dwFlags);
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
+ }
+ else if(ret == NULL)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+HANDLE
+CreateFileWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ DWORD dwDesiredAccess,
+ _In_ DWORD dwShareMode,
+ _In_opt_ LPSECURITY_ATTRIBUTES lpSecurityAttributes,
+ _In_ DWORD dwCreationDisposition,
+ _In_ DWORD dwFlagsAndAttributes,
+ _In_opt_ HANDLE hTemplateFile
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ DWORD lastError;
+ HANDLE ret = INVALID_HANDLE_VALUE;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return NULL;)
+
+ EX_TRY
+ {
+ LongPathString path(LongPathString::Literal, lpFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+ ret = CreateFileW(path.GetUnicode(),
+ dwDesiredAccess,
+ dwShareMode,
+ lpSecurityAttributes,
+ dwCreationDisposition,
+ dwFlagsAndAttributes,
+ hTemplateFile);
+
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == INVALID_HANDLE_VALUE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+BOOL
+SetFileAttributesWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ DWORD dwFileAttributes
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString path(LongPathString::Literal, lpFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+ ret = SetFileAttributesW(
+ path.GetUnicode(),
+ dwFileAttributes
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+DWORD
+GetFileAttributesWrapper(
+ _In_ LPCWSTR lpFileName
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ DWORD ret = INVALID_FILE_ATTRIBUTES;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return INVALID_FILE_ATTRIBUTES;)
+
+ EX_TRY
+ {
+ LongPathString path(LongPathString::Literal, lpFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+ ret = GetFileAttributesW(
+ path.GetUnicode()
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == INVALID_FILE_ATTRIBUTES)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+BOOL
+GetFileAttributesExWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ GET_FILEEX_INFO_LEVELS fInfoLevelId,
+ _Out_writes_bytes_(sizeof(WIN32_FILE_ATTRIBUTE_DATA)) LPVOID lpFileInformation
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString path(LongPathString::Literal, lpFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+ ret = GetFileAttributesExW(
+ path.GetUnicode(),
+ fInfoLevelId,
+ lpFileInformation
+ );
+
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+BOOL
+DeleteFileWrapper(
+ _In_ LPCWSTR lpFileName
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString path(LongPathString::Literal, lpFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+ ret = DeleteFileW(
+ path.GetUnicode()
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+
+BOOL
+CopyFileWrapper(
+ _In_ LPCWSTR lpExistingFileName,
+ _In_ LPCWSTR lpNewFileName,
+ _In_ BOOL bFailIfExists
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString Existingpath(LongPathString::Literal, lpExistingFileName);
+ LongPathString Newpath(LongPathString::Literal, lpNewFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(Existingpath)) && SUCCEEDED(LongFile::NormalizePath(Newpath)))
+ {
+ ret = CopyFileW(
+ Existingpath.GetUnicode(),
+ Newpath.GetUnicode(),
+ bFailIfExists
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+
+BOOL
+MoveFileWrapper(
+ _In_ LPCWSTR lpExistingFileName,
+ _In_ LPCWSTR lpNewFileName
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString Existingpath(LongPathString::Literal, lpExistingFileName);
+ LongPathString Newpath(LongPathString::Literal, lpNewFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(Existingpath)) && SUCCEEDED(LongFile::NormalizePath(Newpath)))
+ {
+ ret = MoveFileW(
+ Existingpath.GetUnicode(),
+ Newpath.GetUnicode()
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+BOOL
+MoveFileExWrapper(
+ _In_ LPCWSTR lpExistingFileName,
+ _In_opt_ LPCWSTR lpNewFileName,
+ _In_ DWORD dwFlags
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString Existingpath(LongPathString::Literal, lpExistingFileName);
+ LongPathString Newpath(LongPathString::Literal, lpNewFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(Existingpath)) && SUCCEEDED(LongFile::NormalizePath(Newpath)))
+ {
+ ret = MoveFileExW(
+ Existingpath.GetUnicode(),
+ Newpath.GetUnicode(),
+ dwFlags
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+
+}
+
+DWORD
+SearchPathWrapper(
+ _In_opt_ LPCWSTR lpPath,
+ _In_ LPCWSTR lpFileName,
+ _In_opt_ LPCWSTR lpExtension,
+ _In_ BOOL getPath,
+ SString& lpBuffer,
+ _Out_opt_ LPWSTR * lpFilePart
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ DWORD ret = 0;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return 0;)
+
+ EX_TRY
+ {
+ LongPathString Existingpath(LongPathString::Literal, lpPath);
+
+ if (lpPath != NULL)
+ {
+ if (FAILED(LongFile::NormalizePath(Existingpath)))
+ {
+ ret = FALSE;
+ }
+ else
+ {
+ lpPath = Existingpath.GetUnicode();
+ }
+ }
+
+ if (!getPath)
+ {
+ ret = SearchPathW(
+ lpPath,
+ lpFileName,
+ lpExtension,
+ 0,
+ NULL,
+ NULL
+ );
+ }
+ else
+ {
+ COUNT_T size = lpBuffer.GetUnicodeAllocation() + 1;
+
+ ret = SearchPathW(
+ lpPath,
+ lpFileName,
+ lpExtension,
+ size,
+ lpBuffer.OpenUnicodeBuffer(size - 1),
+ lpFilePart
+ );
+
+ if (ret > size)
+ {
+ lpBuffer.CloseBuffer();
+ ret = SearchPathW(
+ lpPath,
+ lpFileName,
+ lpExtension,
+ ret,
+ lpBuffer.OpenUnicodeBuffer(ret - 1),
+ lpFilePart
+ );
+ }
+
+ lpBuffer.CloseBuffer(ret);
+
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
+ }
+ else if (ret == 0)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+
+}
+
+DWORD
+GetShortPathNameWrapper(
+ _In_ LPCWSTR lpszLongPath,
+ SString& lpszShortPath
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ DWORD ret = 0;
+ HRESULT hr = S_OK;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return 0;)
+
+ EX_TRY
+ {
+ LongPathString longPath(LongPathString::Literal, lpszLongPath);
+
+ if (SUCCEEDED(LongFile::NormalizePath(longPath)))
+ {
+ COUNT_T size = lpszShortPath.GetUnicodeAllocation() + 1;
+
+ ret = GetShortPathNameW(
+ longPath.GetUnicode(),
+ lpszShortPath.OpenUnicodeBuffer(size - 1),
+ (DWORD)size
+ );
+
+ if (ret > size)
+ {
+ lpszShortPath.CloseBuffer();
+ ret = GetShortPathNameW(
+ longPath.GetUnicode(),
+ lpszShortPath.OpenUnicodeBuffer(ret -1),
+ ret
+ );
+ }
+
+ lpszShortPath.CloseBuffer(ret);
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == 0)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+DWORD
+GetLongPathNameWrapper(
+ _In_ LPCWSTR lpszShortPath,
+ SString& lpszLongPath
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ DWORD ret = 0;
+ HRESULT hr = S_OK;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return 0;)
+
+ EX_TRY
+ {
+ LongPathString shortPath(LongPathString::Literal, lpszShortPath);
+
+ if (SUCCEEDED(LongFile::NormalizePath(shortPath)))
+ {
+ COUNT_T size = lpszLongPath.GetUnicodeAllocation() + 1;
+
+ ret = GetLongPathNameW(
+ shortPath.GetUnicode(),
+ lpszLongPath.OpenUnicodeBuffer(size - 1),
+ (DWORD)size
+ );
+
+ if (ret > size)
+ {
+ lpszLongPath.CloseBuffer();
+ ret = GetLongPathNameW(
+ shortPath.GetUnicode(),
+ lpszLongPath.OpenUnicodeBuffer(ret - 1),
+ ret
+ );
+
+ }
+
+ lpszLongPath.CloseBuffer(ret);
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == 0)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+BOOL
+CreateDirectoryWrapper(
+ _In_ LPCWSTR lpPathName,
+ _In_opt_ LPSECURITY_ATTRIBUTES lpSecurityAttributes
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString path(LongPathString::Literal, lpPathName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+ ret = CreateDirectoryW(
+ path.GetUnicode(),
+ lpSecurityAttributes
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+BOOL
+RemoveDirectoryWrapper(
+ _In_ LPCWSTR lpPathName
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString path(LongPathString::Literal, lpPathName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+ ret = RemoveDirectoryW(
+ path.GetUnicode()
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+DWORD
+GetModuleFileNameWrapper(
+ _In_opt_ HMODULE hModule,
+ SString& buffer
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ DWORD ret = 0;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return 0;)
+
+ EX_TRY
+ {
+ COUNT_T size = buffer.GetUnicodeAllocation() + 1;
+
+ ret = GetModuleFileNameW(
+ hModule,
+ buffer.OpenUnicodeBuffer(size - 1),
+ (DWORD)size
+ );
+
+
+ while (ret == size )
+ {
+ buffer.CloseBuffer();
+ size = size * 2;
+ ret = GetModuleFileNameW(
+ hModule,
+ buffer.OpenUnicodeBuffer(size - 1),
+ (DWORD)size
+ );
+
+ }
+
+
+ lastError = GetLastError();
+ buffer.CloseBuffer(ret);
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
+ }
+ else if (ret == 0)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+UINT WINAPI GetTempFileNameWrapper(
+ _In_ LPCTSTR lpPathName,
+ _In_ LPCTSTR lpPrefixString,
+ _In_ UINT uUnique,
+ SString& lpTempFileName
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ UINT ret = 0;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return 0;)
+
+ EX_TRY
+ {
+ //Change the behaviour in Redstone to retry
+ COUNT_T size = MAX_LONGPATH;
+ WCHAR* buffer = lpTempFileName.OpenUnicodeBuffer(size - 1);
+ ret = GetTempFileNameW(
+ lpPathName,
+ lpPrefixString,
+ uUnique,
+ buffer
+ );
+
+ lastError = GetLastError();
+ size = (COUNT_T)wcslen(buffer);
+ lpTempFileName.CloseBuffer(size);
+
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
+ }
+ else if (ret == 0)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+DWORD WINAPI GetTempPathWrapper(
+ SString& lpBuffer
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ DWORD ret = 0;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return 0;)
+
+ EX_TRY
+ {
+ //Change the behaviour in Redstone to retry
+ COUNT_T size = MAX_LONGPATH;
+
+ ret = GetTempPathW(
+ size,
+ lpBuffer.OpenUnicodeBuffer(size - 1)
+ );
+
+ lastError = GetLastError();
+ lpBuffer.CloseBuffer(ret);
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
+ }
+ else if (ret == 0)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+DWORD WINAPI GetCurrentDirectoryWrapper(
+ SString& lpBuffer
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ DWORD ret = 0;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return 0;)
+
+ EX_TRY
+ {
+ //Change the behaviour in Redstone to retry
+ COUNT_T size = MAX_LONGPATH;
+
+ ret = GetCurrentDirectoryW(
+ size,
+ lpBuffer.OpenUnicodeBuffer(size - 1)
+ );
+
+ lastError = GetLastError();
+ lpBuffer.CloseBuffer(ret);
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
+ }
+ else if (ret == 0)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+DWORD WINAPI GetEnvironmentVariableWrapper(
+ _In_opt_ LPCTSTR lpName,
+ _Out_opt_ SString& lpBuffer
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ DWORD ret = 0;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return 0;)
+
+ EX_TRY
+ {
+
+ COUNT_T size = lpBuffer.GetUnicodeAllocation() + 1;
+
+ ret = GetEnvironmentVariableW(
+ lpName,
+ lpBuffer.OpenUnicodeBuffer(size - 1),
+ size
+ );
+
+ // We loop round getting the length of the env var and then trying to copy
+ // the value into a the allocated buffer. Usually we'll go through this loop
+ // precisely once, but the caution is ncessary in case the variable mutates
+ // beneath us, as the environment variable can be modified by another thread
+ //between two calls to GetEnvironmentVariableW
+
+ while (ret > size)
+ {
+ size = ret;
+ lpBuffer.CloseBuffer();
+ ret = GetEnvironmentVariableW(
+ lpName,
+ lpBuffer.OpenUnicodeBuffer(size - 1),
+ size);
+ }
+
+ lastError = GetLastError();
+ lpBuffer.CloseBuffer(ret);
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
+ }
+ else if (ret == 0)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+
+#ifndef FEATURE_PAL
+
+BOOL
+CreateHardLinkWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ LPCWSTR lpExistingFileName,
+ _Reserved_ LPSECURITY_ATTRIBUTES lpSecurityAttributes
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString Existingpath(LongPathString::Literal, lpExistingFileName);
+ LongPathString FileName(LongPathString::Literal, lpFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(Existingpath)) && SUCCEEDED(LongFile::NormalizePath(FileName)))
+ {
+ ret = CreateHardLinkW(
+ Existingpath.GetUnicode(),
+ FileName.GetUnicode(),
+ lpSecurityAttributes
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+BOOL
+CopyFileExWrapper(
+ _In_ LPCWSTR lpExistingFileName,
+ _In_ LPCWSTR lpNewFileName,
+ _In_opt_ LPPROGRESS_ROUTINE lpProgressRoutine,
+ _In_opt_ LPVOID lpData,
+ _When_(pbCancel != NULL, _Pre_satisfies_(*pbCancel == FALSE))
+ _Inout_opt_ LPBOOL pbCancel,
+ _In_ DWORD dwCopyFlags
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ BOOL ret = FALSE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString Existingpath(LongPathString::Literal, lpExistingFileName);
+ LongPathString Newpath(LongPathString::Literal, lpNewFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(Existingpath)) && SUCCEEDED(LongFile::NormalizePath(Newpath)))
+ {
+ ret = CopyFileExW(
+ Existingpath.GetUnicode(),
+ Newpath.GetUnicode(),
+ lpProgressRoutine,
+ lpData,
+ pbCancel,
+ dwCopyFlags
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == FALSE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+
+HANDLE
+FindFirstFileExWrapper(
+ _In_ LPCWSTR lpFileName,
+ _In_ FINDEX_INFO_LEVELS fInfoLevelId,
+ _Out_writes_bytes_(sizeof(WIN32_FIND_DATAW)) LPVOID lpFindFileData,
+ _In_ FINDEX_SEARCH_OPS fSearchOp,
+ _Reserved_ LPVOID lpSearchFilter,
+ _In_ DWORD dwAdditionalFlags
+ )
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ SO_TOLERANT;
+ }
+ CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ HANDLE ret = INVALID_HANDLE_VALUE;
+ DWORD lastError;
+
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return FALSE;)
+
+ EX_TRY
+ {
+ LongPathString path(LongPathString::Literal, lpFileName);
+
+ if (SUCCEEDED(LongFile::NormalizePath(path)))
+ {
+ ret = FindFirstFileExW(
+ path.GetUnicode(),
+ fInfoLevelId,
+ lpFindFileData,
+ fSearchOp,
+ lpSearchFilter,
+ dwAdditionalFlags
+ );
+ }
+
+ lastError = GetLastError();
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
+
+ if (hr != S_OK )
+ {
+ SetLastError(hr);
+ }
+ else if(ret == INVALID_HANDLE_VALUE)
+ {
+ SetLastError(lastError);
+ }
+
+ return ret;
+}
+#endif //!FEATURE_PAL
+
+#if defined(FEATURE_CORECLR) || defined(CROSSGEN_COMPILE)
+
+#ifndef FEATURE_PAL
+
+#if ! defined(DACCESS_COMPILE) && !defined(SELF_NO_HOST)
+extern HINSTANCE g_pMSCorEE;
+#endif// ! defined(DACCESS_COMPILE) && !defined(SELF_NO_HOST)
+
+BOOL PAL_GetPALDirectoryWrapper(SString& pbuffer)
+{
+
+ HRESULT hr = S_OK;
+
+ PathString pPath;
+ DWORD dwPath;
+ HINSTANCE hinst = NULL;
+
+#if ! defined(DACCESS_COMPILE) && !defined(SELF_NO_HOST)
+ hinst = g_pMSCorEE;
+#endif// ! defined(DACCESS_COMPILE) && !defined(SELF_NO_HOST)
+
+#ifndef CROSSGEN_COMPILE
+ _ASSERTE(hinst != NULL);
+#endif
+
+ dwPath = WszGetModuleFileName(hinst, pPath);
+
+ if(dwPath == 0)
+ {
+ hr = HRESULT_FROM_GetLastErrorNA();
+ }
+ else
+ {
+ DWORD dwLength;
+ hr = CopySystemDirectory(pPath, pbuffer);
+ }
+
+ return (hr == S_OK);
+}
+
+#else
+
+BOOL PAL_GetPALDirectoryWrapper(SString& pbuffer)
+{
+ BOOL retval;
+ COUNT_T size = MAX_LONGPATH; //Retry once the PAL Api is fixed to return the correct size
+ WCHAR* buffer = pbuffer.OpenUnicodeBuffer(size - 1);
+
+ retval = PAL_GetPALDirectoryW(pbuffer.OpenUnicodeBuffer(size - 1), size);
+ size = (COUNT_T)wcslen(buffer);
+ pbuffer.CloseBuffer(size);
+
+ return retval;
+}
+
+#endif // FEATURE_PAL
+
+#endif // FEATURE_CORECLR || CROSSGEN_COMPILE
+
+//Implementation of LongFile Helpers
+const WCHAR LongFile::DirectorySeparatorChar = W('\\');
+const WCHAR LongFile::AltDirectorySeparatorChar = W('/');
+#ifndef FEATURE_PAL
+const WCHAR LongFile::VolumeSeparatorChar = W(':');
+const WCHAR* LongFile::ExtendedPrefix = W("\\\\?\\");
+const WCHAR* LongFile::DevicePathPrefix = W("\\\\.\\");
+const WCHAR* LongFile::UNCExtendedPathPrefix = W("\\\\?\\UNC\\");
+const WCHAR* LongFile::UNCPathPrefix = W("\\\\");
+
+BOOL LongFile::IsExtended(SString & path)
+{
+ return path.BeginsWith(ExtendedPrefix);
+}
+
+BOOL LongFile::IsUNCExtended(SString & path)
+{
+
+ return path.BeginsWith(UNCExtendedPathPrefix);
+}
+
+// Relative here means it could be relative to current directory on the relevant drive
+// NOTE: Relative segments ( \..\) are not considered relative
+// Returns true if the path specified is relative to the current drive or working directory.
+// Returns false if the path is fixed to a specific drive or UNC path. This method does no
+// validation of the path (URIs will be returned as relative as a result).
+// Handles paths that use the alternate directory separator. It is a frequent mistake to
+// assume that rooted paths (Path.IsPathRooted) are not relative. This isn't the case.
+
+BOOL LongFile::IsPathNotFullyQualified(SString & path)
+{
+ if (path.GetCount() < 2)
+ {
+ return TRUE; // It isn't fixed, it must be relative. There is no way to specify a fixed path with one character (or less).
+ }
+
+ if (IsDirectorySeparator(path[0]))
+ {
+ return !IsDirectorySeparator(path[1]); // There is no valid way to specify a relative path with two initial slashes
+ }
+
+ return !((path.GetCount() >= 3) //The only way to specify a fixed path that doesn't begin with two slashes is the drive, colon, slash format- i.e. C:\
+ && (path[1] == VolumeSeparatorChar)
+ && IsDirectorySeparator(path[2]));
+}
+
+BOOL LongFile::IsDevice(SString & path)
+{
+ return path.BeginsWith(DevicePathPrefix);
+}
+
+// This function will normalize paths if the path length exceeds MAX_PATH
+// The normalization examples are :
+// C:\foo\<long>\bar => \\?\C:\foo\<long>\bar
+// \\server\<long>\bar => \\?\UNC\server\<long>\bar
+HRESULT LongFile::NormalizePath(SString & path)
+{
+ HRESULT hr = S_OK;
+ DWORD ret = 0;
+ COUNT_T prefixLen = 0;
+ if (path.IsEmpty()|| IsDevice(path) || IsExtended(path) || IsUNCExtended(path))
+ return S_OK;
+
+ if (!IsPathNotFullyQualified(path) && path.GetCount() < MAX_LONGPATH)
+ return S_OK;
+
+ //Now the path will be normalized
+
+ SString originalPath(path);
+ SString prefix(ExtendedPrefix);
+ prefixLen = prefix.GetCount();
+
+ if (path.BeginsWith(UNCPathPrefix))
+ {
+ prefix.Set(UNCExtendedPathPrefix);
+ //In this case if path is \\server the extended syntax should be like \\?\UNC\server
+ //The below logic populates the path from prefixLen offset from the start. This ensures that first 2 characters are overwritten
+ //
+ prefixLen = prefix.GetCount() - 2;
+ }
+
+
+ COUNT_T size = path.GetUnicodeAllocation() + 1;
+ WCHAR* buffer = path.OpenUnicodeBuffer(size - 1);
+
+ ret = GetFullPathNameW(
+ originalPath.GetUnicode(),
+ size - prefixLen, //memory avilable for path after reserving for prefix
+ (buffer + prefixLen), //reserve memory for prefix
+ NULL
+ );
+
+ if (ret == 0)
+ {
+ return E_FAIL;
+ }
+
+ if (ret > size - prefixLen)
+ {
+ path.CloseBuffer();
+ size = ret + prefixLen;
+ buffer = path.OpenUnicodeBuffer(size -1);
+
+ ret = GetFullPathNameW(
+ originalPath.GetUnicode(),
+ ret, // memory required for the path
+ (buffer + prefixLen), //reserve memory for prefix
+ NULL
+ );
+
+ _ASSERTE(ret < size - prefixLen);
+
+ if (ret == 0)
+ {
+ return E_FAIL;
+ }
+ }
+
+
+ //wcscpy_s always termintes with NULL, so we are saving the character that will be overwriiten
+ WCHAR temp = buffer[prefix.GetCount()];
+ wcscpy_s(buffer, prefix.GetCount() + 1, prefix.GetUnicode());
+ buffer[prefix.GetCount()] = temp;
+ path.CloseBuffer(ret + prefixLen);
+
+ return S_OK;
+}
+#else
+BOOL LongFile::IsExtended(SString & path)
+{
+ return FALSE;
+}
+
+BOOL LongFile::IsUNCExtended(SString & path)
+{
+ return FALSE;
+}
+
+BOOL LongFile::IsPathNotFullyQualified(SString & path)
+{
+ return TRUE;
+}
+
+BOOL LongFile::IsDevice(SString & path)
+{
+ return FALSE;
+}
+
+//Don't need to do anything For XPlat
+HRESULT LongFile::NormalizePath(SString & path)
+{
+ return S_OK;
+}
+#endif //FEATURE_PAL
+
+BOOL LongFile::ContainsDirectorySeparator(SString & path)
+{
+ return path.Find(path.Begin(), DirectorySeparatorChar) || path.Find(path.Begin(), AltDirectorySeparatorChar);
+}
+
+BOOL LongFile::IsDirectorySeparator(WCHAR c)
+{
+ return c == DirectorySeparatorChar || c == AltDirectorySeparatorChar;
+}
+
+
+
diff --git a/src/utilcode/makepath.cpp b/src/utilcode/makepath.cpp
index ab078a9d12..3d948d53a1 100644
--- a/src/utilcode/makepath.cpp
+++ b/src/utilcode/makepath.cpp
@@ -183,15 +183,28 @@ HRESULT GetProcessExePath(LPCWSTR *pwszProcessExePath)
if (g_wszProcessExePath == NULL)
{
- NewArrayHolder<WCHAR> wszProcName = new (nothrow) WCHAR[_MAX_PATH];
- IfNullRet(wszProcName);
-
- DWORD cchProcName = WszGetModuleFileName(NULL, wszProcName, _MAX_PATH);
- if (cchProcName == 0)
+ DWORD cchProcName = 0;
+ NewArrayHolder<WCHAR> wszProcName;
+ EX_TRY
{
- return HRESULT_FROM_GetLastError();
+ PathString wszProcNameString;
+ cchProcName = WszGetModuleFileName(NULL, wszProcNameString);
+ if (cchProcName == 0)
+ {
+ hr = HRESULT_FROM_GetLastError();
+ }
+ else
+ {
+ wszProcName = wszProcNameString.GetCopyOfUnicodeString();
+ }
}
+ EX_CATCH_HRESULT(hr);
+ if (FAILED(hr))
+ {
+ return hr;
+ }
+
if (InterlockedCompareExchangeT(&g_wszProcessExePath, const_cast<LPCWSTR>(wszProcName.GetValue()), NULL) == NULL)
{
wszProcName.SuppressRelease();
@@ -205,3 +218,66 @@ HRESULT GetProcessExePath(LPCWSTR *pwszProcessExePath)
}
#endif
+// Returns the directory for HMODULE. So, if HMODULE was for "C:\Dir1\Dir2\Filename.DLL",
+// then this would return "C:\Dir1\Dir2\" (note the trailing backslash).
+HRESULT GetHModuleDirectory(
+ __in HMODULE hMod,
+ SString& wszPath)
+{
+ CONTRACTL
+ {
+ NOTHROW;
+ GC_NOTRIGGER;
+ CANNOT_TAKE_LOCK;
+ }
+ CONTRACTL_END;
+
+ DWORD dwRet = WszGetModuleFileName(hMod, wszPath);
+
+ if (dwRet == 0)
+ { // Some other error.
+ return HRESULT_FROM_GetLastError();
+ }
+
+ CopySystemDirectory(wszPath, wszPath);
+
+
+ return S_OK;
+}
+
+//
+// Returns path name from a file name.
+// Example: For input "C:\Windows\System.dll" returns "C:\Windows\".
+// Warning: The input file name string might be destroyed.
+//
+// Arguments:
+// pPathString - [in] SString with file name
+//
+// pBuffer - [out] SString .
+//
+// Return Value:
+// S_OK - Output buffer contains path name.
+// other errors - If Sstring throws.
+//
+HRESULT CopySystemDirectory(const SString& pPathString,
+ SString& pbuffer)
+{
+ HRESULT hr = S_OK;
+ EX_TRY
+ {
+ pbuffer.Set(pPathString);
+ SString::Iterator iter = pbuffer.End();
+ if (pbuffer.FindBack(iter,DIRECTORY_SEPARATOR_CHAR_W))
+ {
+ iter++;
+ pbuffer.Truncate(iter);
+ }
+ else
+ {
+ hr = E_UNEXPECTED;
+ }
+ }
+ EX_CATCH_HRESULT(hr);
+
+ return hr;
+}
diff --git a/src/utilcode/perflog.cpp b/src/utilcode/perflog.cpp
index c84c1df2d4..5e031fe4c5 100644
--- a/src/utilcode/perflog.cpp
+++ b/src/utilcode/perflog.cpp
@@ -6,6 +6,7 @@
#include "perflog.h"
#include "jitperf.h"
#include <limits.h>
+#include "sstring.h"
//=============================================================================
// ALL THE PERF LOG CODE IS COMPILED ONLY IF THE ENABLE_PERF_LOG WAS DEFINED.
@@ -83,9 +84,9 @@ void PerfLog::PerfLogInitialize()
// Special cases considered. Now turn on loggin if any of above want logging
// or if PERF_OUTPUT says so.
- wchar_t lpszValue[2];
+ InlineSString<4> lpszValue;
// Read the env var PERF_OUTPUT and if set continue.
- m_fLogPerfData = WszGetEnvironmentVariable (W("PERF_OUTPUT"), lpszValue, sizeof(lpszValue)/sizeof(lpszValue[0]));
+ m_fLogPerfData = WszGetEnvironmentVariable (W("PERF_OUTPUT"), lpszValue);
#if defined(ENABLE_JIT_PERF)
if (!m_fLogPerfData)
@@ -100,9 +101,9 @@ void PerfLog::PerfLogInitialize()
#endif
// See if we want to output to the database
- wchar_t _lpszValue[11];
+ PathString _lpszValue;
DWORD _cchValue = 10; // 11 - 1
- _cchValue = WszGetEnvironmentVariable (W("PerfOutput"), _lpszValue, _cchValue);
+ _cchValue = WszGetEnvironmentVariable (W("PerfOutput"), _lpszValue);
if (_cchValue && (wcscmp (_lpszValue, W("DBase")) == 0))
m_perfAutomationFormat = true;
if (_cchValue && (wcscmp (_lpszValue, W("CSV")) == 0))
diff --git a/src/utilcode/regutil.cpp b/src/utilcode/regutil.cpp
index 0536cfa828..1cb8990f0c 100644
--- a/src/utilcode/regutil.cpp
+++ b/src/utilcode/regutil.cpp
@@ -16,6 +16,7 @@
#include "utilcode.h"
#include "mscoree.h"
#include "sstring.h"
+#include "ex.h"
#define COMPLUS_PREFIX W("COMPlus_")
#define LEN_OF_COMPLUS_PREFIX 8
@@ -74,34 +75,38 @@ LPWSTR REGUTIL::EnvGetString(LPCWSTR name, BOOL fPrependCOMPLUS)
FAULT_NOT_FATAL(); // We don't report OOM errors here, we return a default value.
- for (;;)
- {
- DWORD len = WszGetEnvironmentVariable(buff, 0, 0);
- if (len == 0)
- {
- return NULL;
- }
-
- // If we can't get memory to return the string, then will simply pretend we didn't find it.
- NewArrayHolder<WCHAR> ret(new (nothrow) WCHAR [len]);
- if (ret == NULL)
- {
- return NULL;
- }
-
- DWORD actualLen = WszGetEnvironmentVariable(buff, ret, len);
- if (actualLen == 0)
- {
- return NULL;
- }
-
- if (actualLen < len)
+
+ NewArrayHolder<WCHAR> ret = NULL;
+ HRESULT hr = S_OK;
+ DWORD Len;
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return NULL;)
+ EX_TRY
+ {
+ PathString temp;
+
+ Len = WszGetEnvironmentVariable(buff, temp);
+ if (Len != 0)
{
- return ret.Extract();
- }
+ ret = temp.GetCopyOfUnicodeString();
+ }
+
+ }
+ EX_CATCH_HRESULT(hr);
+ END_SO_INTOLERANT_CODE
- // Variable was changed by other thread - retry
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
}
+
+ if(ret != NULL)
+ {
+ return ret.Extract();
+ }
+
+ return NULL;
+
+
}
#ifdef ALLOW_REGISTRY
diff --git a/src/utilcode/safewrap.cpp b/src/utilcode/safewrap.cpp
index 0ea7b90e3a..6c17478014 100644
--- a/src/utilcode/safewrap.cpp
+++ b/src/utilcode/safewrap.cpp
@@ -35,27 +35,17 @@ void ClrGetCurrentDirectory(SString & value)
CONTRACTL_END;
// Get size needed
- DWORD lenWithNull = WszGetCurrentDirectory(0, NULL);
+ DWORD len = WszGetCurrentDirectory(value);
- // Now read it for content.
- WCHAR * pCharBuf = value.OpenUnicodeBuffer(lenWithNull);
- DWORD lenWithoutNull = WszGetCurrentDirectory(lenWithNull, pCharBuf);
// An actual API failure in GetCurrentDirectory failure should be very rare, so we'll throw on those.
- if (lenWithoutNull == 0)
+ if (len == 0)
{
value.CloseBuffer(0);
ThrowLastError();
}
- if (lenWithoutNull != (lenWithNull - 1))
- {
- value.CloseBuffer(lenWithoutNull);
- // must have changed underneath us.
- ThrowHR(E_FAIL);
- }
-
- value.CloseBuffer(lenWithoutNull);
+ value.CloseBuffer();
}
// Nothrowing wrapper.
diff --git a/src/utilcode/stacktrace.cpp b/src/utilcode/stacktrace.cpp
index 0b6f3ea293..7bfdb4514a 100644
--- a/src/utilcode/stacktrace.cpp
+++ b/src/utilcode/stacktrace.cpp
@@ -274,9 +274,8 @@ IMGHLPFN_LOAD ailFuncList[] =
#define MAX_SYM_PATH (1024*8)
#define DEFAULT_SYM_PATH W("symsrv*symsrv.dll*\\\\symbols\\symbols;")
#define STR_ENGINE_NAME MAIN_CLR_DLL_NAME_W
-LPSTR FillSymbolSearchPath(CQuickBytes &qb)
+LPSTR FillSymbolSearchPathThrows(CQuickBytes &qb)
{
- STATIC_CONTRACT_NOTHROW;
STATIC_CONTRACT_GC_NOTRIGGER;
STATIC_CONTRACT_CANNOT_TAKE_LOCK;
SCAN_IGNORE_FAULT; // Faults from Wsz funcs are handled.
@@ -287,21 +286,15 @@ LPSTR FillSymbolSearchPath(CQuickBytes &qb)
return NULL;
#endif
- NewArrayHolder<WCHAR> rcBuff = new (nothrow) WCHAR[MAX_SYM_PATH]; // Working buffer
+ InlineSString<MAX_SYM_PATH> rcBuff ; // Working buffer
WCHAR rcVerString[64]; // Extension for install directory.
int chTotal = 0; // How full is working buffer.
int ch;
-
- if (rcBuff == NULL)
- return NULL; // Unable to allocate working buffer - fail
-
- ZeroMemory(rcBuff, MAX_SYM_PATH*sizeof(WCHAR));
-
// If the NT symbol server path vars are there, then use those.
- chTotal = WszGetEnvironmentVariable(W("_NT_SYMBOL_PATH"), rcBuff, MAX_SYM_PATH); // Cannot use NumItems(rcBuff) since NumItems does not work with holders
+ chTotal = WszGetEnvironmentVariable(W("_NT_SYMBOL_PATH"), rcBuff);
if (chTotal + 1 < MAX_SYM_PATH)
- rcBuff[chTotal++] = W(';');
+ rcBuff.Append(W(';'));
// Copy the defacto NT symbol path as well.
size_t sympathLength = chTotal + NumItems(DEFAULT_SYM_PATH) + 1;
@@ -313,13 +306,15 @@ LPSTR FillSymbolSearchPath(CQuickBytes &qb)
if (sympathLength < MAX_SYM_PATH)
{
- wcsncpy_s(&rcBuff[chTotal], MAX_SYM_PATH-chTotal, DEFAULT_SYM_PATH, _TRUNCATE);
- chTotal = (int) wcslen(rcBuff);
+ rcBuff.Append(DEFAULT_SYM_PATH);
+ chTotal = rcBuff.GetCount();
}
// Next, if there is a URTTARGET, add that since that is where ndpsetup places
// your symobls on an install.
- ch = WszGetEnvironmentVariable(W("URTTARGET"), &rcBuff[chTotal], MAX_SYM_PATH - chTotal);
+ PathString rcBuffTemp;
+ ch = WszGetEnvironmentVariable(W("URTTARGET"), rcBuffTemp);
+ rcBuff.Append(rcBuffTemp);
if (ch != 0 && (chTotal + ch + 1 < MAX_SYM_PATH))
{
size_t chNewTotal = chTotal + ch;
@@ -328,7 +323,7 @@ LPSTR FillSymbolSearchPath(CQuickBytes &qb)
return NULL;
}
chTotal += ch;
- rcBuff[chTotal++] = W(';');
+ rcBuff.Append(W(';'));
}
#ifndef SELF_NO_HOST
@@ -336,8 +331,10 @@ LPSTR FillSymbolSearchPath(CQuickBytes &qb)
// in case URTARGET didn't cut it either.
// For no-host builds of utilcode, we don't necessarily have an engine DLL in the
// process, so skip this part.
- ch = WszGetModuleFileName(GetCLRModuleHack(),
- &rcBuff[chTotal], MAX_SYM_PATH - chTotal);
+
+ ch = WszGetModuleFileName(GetCLRModuleHack(), rcBuffTemp);
+
+
size_t pathLocationLength = chTotal + ch + 1;
// integer overflow occurred
if (pathLocationLength < (size_t)chTotal || pathLocationLength < (size_t)ch)
@@ -348,14 +345,10 @@ LPSTR FillSymbolSearchPath(CQuickBytes &qb)
if (ch != 0 && (pathLocationLength < MAX_SYM_PATH))
{
chTotal = chTotal + ch - NumItems(STR_ENGINE_NAME);
- rcBuff[chTotal++] = W(';');
- rcBuff[chTotal] = 0;
+ rcBuff.Append(W(';'));
}
#endif
- // We want to ensure the resulting string is always NULL-terminated.
- rcBuff[MAX_SYM_PATH-1] = W('\0');
-
// Now we have a working buffer with a bunch of interesting stuff. Time
// to convert it back to ansi for the imagehlp api's. Allocate the buffer
// 2x bigger to handle worst case for MBCS.
@@ -366,7 +359,29 @@ LPSTR FillSymbolSearchPath(CQuickBytes &qb)
WszWideCharToMultiByte(CP_ACP, WC_NO_BEST_FIT_CHARS, rcBuff, -1, szRtn, ch+1, 0, 0);
return (szRtn);
}
+LPSTR FillSymbolSearchPath(CQuickBytes &qb)
+{
+ STATIC_CONTRACT_NOTHROW;
+ STATIC_CONTRACT_GC_NOTRIGGER;
+ STATIC_CONTRACT_CANNOT_TAKE_LOCK;
+ SCAN_IGNORE_FAULT; // Faults from Wsz funcs are handled.
+ LPSTR retval;
+ HRESULT hr = S_OK;
+ EX_TRY
+ {
+ retval = FillSymbolSearchPathThrows(qb);
+ }
+ EX_CATCH_HRESULT(hr);
+
+ if (hr != S_OK)
+ {
+ SetLastError(hr);
+ retval = NULL;
+ }
+
+ return retval;
+}
/****************************************************************************
* MagicInit *
diff --git a/src/utilcode/util.cpp b/src/utilcode/util.cpp
index 6c5378e5d9..dcc6b83e21 100644
--- a/src/utilcode/util.cpp
+++ b/src/utilcode/util.cpp
@@ -3238,6 +3238,8 @@ FileLockHolder::~FileLockHolder()
void FileLockHolder::Acquire(LPCWSTR lockName, HANDLE hInterrupt, BOOL* pInterrupted)
{
+ WRAPPER_NO_CONTRACT;
+
DWORD dwErr = 0;
DWORD dwAccessDeniedRetry = 0;
const DWORD MAX_ACCESS_DENIED_RETRIES = 10;
@@ -3557,53 +3559,7 @@ BOOL IsClrHostedLegacyComObject(REFCLSID rclsid)
}
#endif // FEATURE_COMINTEROP
-// Returns the directory for HMODULE. So, if HMODULE was for "C:\Dir1\Dir2\Filename.DLL",
-// then this would return "C:\Dir1\Dir2\" (note the trailing backslash).
-HRESULT GetHModuleDirectory(
- __in HMODULE hMod,
- __out_z __out_ecount(cchPath) LPWSTR wszPath,
- size_t cchPath)
-{
- CONTRACTL
- {
- NOTHROW;
- GC_NOTRIGGER;
- CANNOT_TAKE_LOCK;
- }
- CONTRACTL_END;
-
- DWORD dwRet = WszGetModuleFileName(hMod, wszPath, static_cast<DWORD>(cchPath));
- if (dwRet == cchPath)
- { // If there are cchPath characters in the string, it means that the string
- // itself is longer than cchPath and GetModuleFileName had to truncate at cchPath.
- return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
- }
- else if (dwRet == 0)
- { // Some other error.
- return HRESULT_FROM_GetLastError();
- }
-
- LPWSTR wszEnd = wcsrchr(wszPath, W('\\'));
- if (wszEnd == NULL)
- { // There was no backslash? Not sure what's going on.
- return E_UNEXPECTED;
- }
-
- // Include the backslash in the resulting string.
- *(++wszEnd) = W('\0');
-
- return S_OK;
-}
-
-SString & GetHModuleDirectory(HMODULE hMod, SString &ssDir)
-{
- LPWSTR wzDir = ssDir.OpenUnicodeBuffer(_MAX_PATH);
- HRESULT hr = GetHModuleDirectory(hMod, wzDir, _MAX_PATH);
- ssDir.CloseBuffer(FAILED(hr) ? 0 : static_cast<COUNT_T>(wcslen(wzDir)));
- IfFailThrow(hr);
- return ssDir;
-}
#if !defined(FEATURE_CORECLR) && !defined(SELF_NO_HOST) && !defined(FEATURE_UTILCODE_NO_DEPENDENCIES)
@@ -3936,39 +3892,14 @@ namespace Win32
// Try to use what the SString already has allocated. If it does not have anything allocated
// or it has < 20 characters allocated, then bump the size requested to _MAX_PATH.
- DWORD dwSize = (DWORD)(ssFileName.GetUnicodeAllocation()) + 1;
- dwSize = (dwSize < 20) ? (_MAX_PATH) : (dwSize);
- DWORD dwResult = WszGetModuleFileName(hModule, ssFileName.OpenUnicodeBuffer(dwSize - 1), dwSize);
+
+ DWORD dwResult = WszGetModuleFileName(hModule, ssFileName);
- // if there was a failure, dwResult == 0;
- // if there was insufficient buffer, dwResult == dwSize;
- // if there was sufficient buffer and a successful write, dwResult < dwSize
- ssFileName.CloseBuffer(dwResult < dwSize ? dwResult : 0);
if (dwResult == 0)
ThrowHR(HRESULT_FROM_GetLastError());
- // Ok, we didn't have enough buffer. Let's loop, doubling the buffer each time, until we succeed.
- while (dwResult == dwSize)
- {
- dwSize = dwSize * 2;
- dwResult = WszGetModuleFileName(hModule, ssFileName.OpenUnicodeBuffer(dwSize - 1), dwSize);
- ssFileName.CloseBuffer(dwResult < dwSize ? dwResult : 0);
-
- if (dwResult == 0)
- ThrowHR(HRESULT_FROM_GetLastError());
- }
-
- // Most of the runtime is not able to handle long filenames. fAllowLongFileNames
- // has a default value of false, so that callers will not accidentally get long
- // file names returned.
- if (!fAllowLongFileNames && ssFileName.BeginsWith(SL(LONG_FILENAME_PREFIX_W)))
- {
- ssFileName.Clear();
- ThrowHR(E_UNEXPECTED);
- }
-
- _ASSERTE(dwResult != 0 && dwResult < dwSize);
+ _ASSERTE(dwResult != 0 );
}
// Returns heap-allocated string in *pwszFileName
@@ -4030,16 +3961,6 @@ namespace Win32
if (!(dwLengthWritten < dwLengthRequired))
ThrowHR(E_UNEXPECTED);
- // Most of the runtime is not able to handle long filenames. fAllowLongFileNames
- // has a default value of false, so that callers will not accidentally get long
- // file names returned.
- if (!fAllowLongFileNames && ssFileName.BeginsWith(SL(LONG_FILENAME_PREFIX_W)))
- {
- ssPathName.Clear();
- if (pdwFilePartIdx != NULL)
- *pdwFilePartIdx = 0;
- ThrowHR(E_UNEXPECTED);
- }
}
} // namespace Win32
diff --git a/src/utilcode/util_nodependencies.cpp b/src/utilcode/util_nodependencies.cpp
index 0628637d33..32d1c35509 100644
--- a/src/utilcode/util_nodependencies.cpp
+++ b/src/utilcode/util_nodependencies.cpp
@@ -302,7 +302,6 @@ BOOL GetRegistryLongValue(HKEY hKeyParent,
//
// Arguments:
// pBuffer - output string buffer
-// pcchBuffer - the number of characters of the string buffer
//
// Return Value:
// S_OK on success, else detailed error code.
@@ -310,39 +309,19 @@ BOOL GetRegistryLongValue(HKEY hKeyParent,
// Note:
//
//----------------------------------------------------------------------------
-HRESULT GetCurrentModuleFileName(__out_ecount(*pcchBuffer) LPWSTR pBuffer, __inout DWORD *pcchBuffer)
+HRESULT GetCurrentModuleFileName(SString& pBuffer)
{
LIMITED_METHOD_CONTRACT;
- if ((pBuffer == NULL) || (pcchBuffer == NULL))
- {
- return E_INVALIDARG;
- }
-
- // Get the appname to look up in the exclusion or inclusion list.
- WCHAR appPath[MAX_LONGPATH + 2];
-
- DWORD ret = WszGetModuleFileName(NULL, appPath, NumItems(appPath));
+
+ DWORD ret = WszGetModuleFileName(NULL, pBuffer);
- if ((ret == NumItems(appPath)) || (ret == 0))
+ if (ret == 0)
{
- // The module file name exceeded maxpath, or GetModuleFileName failed.
return E_UNEXPECTED;
}
- // Pick off the part after the path.
- WCHAR* appName = wcsrchr(appPath, W('\\'));
-
- // If no backslash, use the whole name; if there is a backslash, skip it.
- appName = appName ? appName+1 : appPath;
-
- if (*pcchBuffer < wcslen(appName))
- {
- *pcchBuffer = static_cast<DWORD>(wcslen(appName)) + 1;
- return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
- }
-
- wcscpy_s(pBuffer, *pcchBuffer, appName);
+
return S_OK;
}
@@ -383,11 +362,10 @@ BOOL IsCurrentModuleFileNameInAutoExclusionList()
return FALSE;
}
- WCHAR wszAppName[MAX_LONGPATH];
- DWORD cchAppName = NumItems(wszAppName);
-
+ PathString wszAppName;
+
// Get the appname to look up in the exclusion or inclusion list.
- if (GetCurrentModuleFileName(wszAppName, &cchAppName) != S_OK)
+ if (GetCurrentModuleFileName(wszAppName) != S_OK)
{
// Assume it is not on the exclusion list if we cannot find the module's filename.
return FALSE;
@@ -552,12 +530,11 @@ HRESULT GetDebuggerSettingInfoWorker(__out_ecount_part_opt(*pcchDebuggerString,
BOOL fAuto = FALSE;
// Get the appname to look up in DebugApplications key.
- WCHAR wzAppName[MAX_LONGPATH];
- DWORD cchAppName = NumItems(wzAppName);
+ PathString wzAppName;
long iValue;
// Check DebugApplications setting
- if ((SUCCEEDED(GetCurrentModuleFileName(wzAppName, &cchAppName))) &&
+ if ((SUCCEEDED(GetCurrentModuleFileName(wzAppName))) &&
(
GetRegistryLongValue(HKEY_LOCAL_MACHINE, kDebugApplicationsPoliciesKey, wzAppName, &iValue, TRUE) ||
GetRegistryLongValue(HKEY_LOCAL_MACHINE, kDebugApplicationsKey, wzAppName, &iValue, TRUE) ||
diff --git a/src/utilcode/utilcode.settings.targets b/src/utilcode/utilcode.settings.targets
index fcb41dc0a4..690000d402 100644
--- a/src/utilcode/utilcode.settings.targets
+++ b/src/utilcode/utilcode.settings.targets
@@ -38,6 +38,7 @@
<CppCompile Include="$(UtilCodeSrcDir)\SString.cpp" />
<CppCompile Include="$(UtilCodeSrcDir)\SString_COM.cpp" />
<CppCompile Include="$(UtilCodeSrcDir)\FString.cpp" />
+ <CppCompile Include="$(UtilCodeSrcDir)\longfilepathwrappers.cpp" />
<CppCompile Include="$(UtilCodeSrcDir)\NamespaceUtil.cpp" />
<CppCompile Include="$(UtilCodeSrcDir)\MakePath.cpp" />
diff --git a/src/utilcode/utilmessagebox.cpp b/src/utilcode/utilmessagebox.cpp
index e84ff8b2c6..4559d16b7f 100644
--- a/src/utilcode/utilmessagebox.cpp
+++ b/src/utilcode/utilmessagebox.cpp
@@ -354,20 +354,19 @@ int UtilMessageBoxNonLocalizedVA(
StackSString formattedMessage;
StackSString formattedTitle;
SString details(lpDetails);
- StackSString fileName;
+ PathString fileName;
BOOL fDisplayMsgBox = TRUE;
// Format message string using optional parameters
formattedMessage.VPrintf(lpText, args);
// Try to get filename of Module and add it to title
- if (showFileNameInTitle && WszGetModuleFileName(NULL, fileName.OpenUnicodeBuffer(MAX_LONGPATH), MAX_LONGPATH))
+ if (showFileNameInTitle && WszGetModuleFileName(NULL, fileName))
{
LPCWSTR wszName = NULL;
size_t cchName = 0;
- // Close the buffer we opened before the call to WszGetModuleFileName.
- fileName.CloseBuffer();
+
SplitPathInterior(fileName, NULL, NULL, NULL, NULL, &wszName, &cchName, NULL, NULL);
formattedTitle.Printf(W("%s - %s"), wszName, lpTitle);
diff --git a/src/vm/appdomain.cpp b/src/vm/appdomain.cpp
index 9ab8c7dbc0..a841423ace 100644
--- a/src/vm/appdomain.cpp
+++ b/src/vm/appdomain.cpp
@@ -4770,12 +4770,10 @@ void SystemDomain::GetDevpathW(__out_ecount_opt(1) LPWSTR* pDevpath, DWORD* pdwD
if(m_fDevpath == FALSE) {
DWORD dwPath = 0;
- dwPath = WszGetEnvironmentVariable(APPENV_DEVPATH, 0, 0);
+ PathString m_pwDevpathholder;
+ dwPath = WszGetEnvironmentVariable(APPENV_DEVPATH, m_pwDevpathholder);
if(dwPath) {
- m_pwDevpath = (WCHAR*) new WCHAR[dwPath];
- m_dwDevpath = WszGetEnvironmentVariable(APPENV_DEVPATH,
- m_pwDevpath,
- dwPath);
+ m_pwDevpath = m_pwDevpathholder.GetCopyOfUnicodeString();
}
else {
RegKeyHolder userKey;
@@ -13831,14 +13829,30 @@ DWORD* SetupCompatibilityFlags()
SO_TOLERANT;
} CONTRACTL_END;
- WCHAR buf[2] = { '\0', '\0' };
+ LPCWSTR buf;
+ bool return_null = true;
FAULT_NOT_FATAL(); // we can simply give up
- if (WszGetEnvironmentVariable(W("UnsupportedCompatSwitchesEnabled"), buf, COUNTOF(buf)) == 0)
- return NULL;
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return NULL;)
+ InlineSString<4> bufString;
+
+ if (WszGetEnvironmentVariable(W("UnsupportedCompatSwitchesEnabled"), bufString) != 0)
+ {
+ buf = bufString.GetUnicode();
+ if (buf[0] != '1' || buf[1] != '\0')
+ {
+ return_null = true;
+ }
+ else
+ {
+ return_null = false;
+ }
+
+ }
+ END_SO_INTOLERANT_CODE
- if (buf[0] != '1' || buf[1] != '\0')
+ if (return_null)
return NULL;
static const LPCWSTR rgFlagNames[] = {
@@ -13852,17 +13866,21 @@ DWORD* SetupCompatibilityFlags()
return NULL;
ZeroMemory(pFlags, size * sizeof(DWORD));
+ BEGIN_SO_INTOLERANT_CODE_NO_THROW_CHECK_THREAD(SetLastError(COR_E_STACKOVERFLOW); return NULL;)
+ InlineSString<4> bufEnvString;
for (int i = 0; i < COUNTOF(rgFlagNames); i++)
{
- if (WszGetEnvironmentVariable(rgFlagNames[i], buf, COUNTOF(buf)) == 0)
+ if (WszGetEnvironmentVariable(rgFlagNames[i], bufEnvString) == 0)
continue;
+ buf = bufEnvString.GetUnicode();
if (buf[0] != '1' || buf[1] != '\0')
continue;
pFlags[i / 32] |= 1 << (i % 32);
}
-
+ END_SO_INTOLERANT_CODE
+
return pFlags;
}
diff --git a/src/vm/assemblynative.cpp b/src/vm/assemblynative.cpp
index 5720c201ed..c89e927404 100644
--- a/src/vm/assemblynative.cpp
+++ b/src/vm/assemblynative.cpp
@@ -2364,8 +2364,8 @@ void QCALLTYPE AssemblyNative::CreateVersionInfoResource(LPCWSTR pwzFilename,
const void *pvData=0; // Pointer to the resource.
ULONG cbData; // Size of the resource data.
ULONG cbWritten;
- WCHAR szFile[MAX_PATH_FNAME+1]; // File name for resource file.
- WCHAR szPath[MAX_LONGPATH+1]; // Path name for resource file.
+ PathString szFile; // File name for resource file.
+ PathString szPath; // Path name for resource file.
HandleHolder hFile;
res.SetInfo(pwzFilename,
@@ -2387,9 +2387,9 @@ void QCALLTYPE AssemblyNative::CreateVersionInfoResource(LPCWSTR pwzFilename,
// messages including the path/file name</TODO>
// Persist to a file.
- if (!WszGetTempPath(MAX_LONGPATH, szPath))
+ if (!WszGetTempPath(szPath))
COMPlusThrowWin32();
- if (!WszGetTempFileName(szPath, W("RES"), 0, szFile))
+ if (!WszGetTempFileName(szPath.GetUnicode(), W("RES"), 0, szFile))
COMPlusThrowWin32();
hFile = WszCreateFile(szFile, GENERIC_READ|GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL);
diff --git a/src/vm/ceemain.cpp b/src/vm/ceemain.cpp
index d6391056ab..e2419ac88f 100644
--- a/src/vm/ceemain.cpp
+++ b/src/vm/ceemain.cpp
@@ -2978,9 +2978,9 @@ static BOOL CacheCommandLine(__in LPWSTR pCmdLine, __in_opt LPWSTR* ArgvW)
}
if (ArgvW != NULL && ArgvW[0] != NULL) {
- WCHAR wszModuleName[MAX_LONGPATH];
- WCHAR wszCurDir[MAX_LONGPATH];
- if (!WszGetCurrentDirectory(MAX_LONGPATH, wszCurDir))
+ PathString wszModuleName;
+ PathString wszCurDir;
+ if (!WszGetCurrentDirectory(wszCurDir))
return FALSE;
#ifdef _PREFAST_
@@ -2991,17 +2991,17 @@ static BOOL CacheCommandLine(__in LPWSTR pCmdLine, __in_opt LPWSTR* ArgvW)
// usage of PathCombine is safe if we ensure that buffer specified by
// parameter1 can accomodate buffers specified by paramater2, parameter3
// and one path separator
- if (lstrlenW(wszCurDir) + lstrlenW(ArgvW[0]) + 1 >= COUNTOF(wszModuleName))
- return FALSE;
+ COUNT_T wszModuleName_len = wszCurDir.GetCount() + lstrlenW(ArgvW[0]);
+ WCHAR* wszModuleName_buf = wszModuleName.OpenUnicodeBuffer(wszModuleName_len);
- if (PathCombine(wszModuleName, wszCurDir, ArgvW[0]) == NULL)
+ if (PathCombine(wszModuleName_buf, wszCurDir, ArgvW[0]) == NULL)
return FALSE;
-
+ wszModuleName.CloseBuffer();
#ifdef _PREFAST_
#pragma warning(pop)
#endif
- size_t len = wcslen(wszModuleName);
+ size_t len = wszModuleName.GetCount();
_ASSERT(g_pCachedModuleFileName== NULL);
g_pCachedModuleFileName = new WCHAR[len+1];
wcscpy_s(g_pCachedModuleFileName, len+1, wszModuleName);
@@ -3824,7 +3824,7 @@ BOOL STDMETHODCALLTYPE EEDllMain( // TRUE on success, FALSE on error.
CoreClrCallbacks cccallbacks;
cccallbacks.m_hmodCoreCLR = (HINSTANCE)g_pMSCorEE;
cccallbacks.m_pfnIEE = IEE;
- cccallbacks.m_pfnGetCORSystemDirectory = GetCORSystemDirectoryInternal;
+ cccallbacks.m_pfnGetCORSystemDirectory = GetCORSystemDirectoryInternaL;
cccallbacks.m_pfnGetCLRFunction = GetCLRFunction;
InitUtilcode(cccallbacks);
@@ -4279,30 +4279,47 @@ static HRESULT InitializeIPCManager(void)
{
// We failed to create the IPC block because it has already been created. This means that
// two mscoree's have been loaded into the process.
- WCHAR strFirstModule[256];
- WCHAR strSecondModule[256];
-
- // Get the name and path of the first loaded MSCOREE.DLL.
- if (!hInstIPCBlockOwner || !WszGetModuleFileName(hInstIPCBlockOwner, strFirstModule, 256))
- wcscpy_s(strFirstModule, COUNTOF(strFirstModule), W("<Unknown>"));
-
- // Get the name and path of the second loaded MSCOREE.DLL.
- if (!WszGetModuleFileName(g_pMSCorEE, strSecondModule, 256))
- wcscpy_s(strSecondModule, COUNTOF(strSecondModule), W("<Unknown>"));
+ PathString strFirstModule;
+ PathString strSecondModule;
+ EX_TRY
+ {
+ // Get the name and path of the first loaded MSCOREE.DLL.
+ if (!hInstIPCBlockOwner || !WszGetModuleFileName(hInstIPCBlockOwner, strFirstModule))
+ strFirstModule.Set(W("<Unknown>"));
+ // Get the name and path of the second loaded MSCOREE.DLL.
+ if (!WszGetModuleFileName(g_pMSCorEE, strSecondModule))
+ strSecondModule.Set(W("<Unknown>"));
+ }
+ EX_CATCH_HRESULT(hr);
// Load the format strings for the title and the message body.
EEMessageBoxCatastrophic(IDS_EE_TWO_LOADED_MSCOREE_MSG, IDS_EE_TWO_LOADED_MSCOREE_TITLE, strFirstModule, strSecondModule);
goto errExit;
}
else
{
- if (!WszGetModuleFileName(GetModuleInst(), (PWSTR)
- g_pIPCManagerInterface->
- GetInstancePath(),
- MAX_LONGPATH))
+ PathString temp;
+ if (!WszGetModuleFileName(GetModuleInst(),
+ temp
+ ))
{
hr = HRESULT_FROM_GetLastErrorNA();
}
+ else
+ {
+ EX_TRY
+ {
+ if (temp.GetCount() + 1 > MAX_LONGPATH)
+ {
+ hr = E_FAIL;
+ }
+ else
+ {
+ wcscpy_s((PWSTR)g_pIPCManagerInterface->GetInstancePath(),temp.GetCount() + 1,temp);
+ }
+ }
+ EX_CATCH_HRESULT(hr);
+ }
}
// Generate public IPCBlock for our PID.
@@ -4915,11 +4932,12 @@ HRESULT CorCommandLine::ReadClickOnceEnvVariables()
EX_TRY
{
// Find out if this is a ClickOnce application being activated.
- DWORD cAppFullName = WszGetEnvironmentVariable(g_pwzClickOnceEnv_FullName, NULL, 0);
+ PathString m_pwszAppFullNameHolder;
+ DWORD cAppFullName = WszGetEnvironmentVariable(g_pwzClickOnceEnv_FullName, m_pwszAppFullNameHolder);
if (cAppFullName > 0) {
// get the application full name.
- m_pwszAppFullName = new WCHAR[cAppFullName];
- WszGetEnvironmentVariable(g_pwzClickOnceEnv_FullName, m_pwszAppFullName, cAppFullName);
+ m_pwszAppFullName = m_pwszAppFullNameHolder.GetCopyOfUnicodeString();
+
// reset the variable now that we read it so child processes
// do not think they are a clickonce app.
WszSetEnvironmentVariable(g_pwzClickOnceEnv_FullName, NULL);
@@ -4933,7 +4951,8 @@ HRESULT CorCommandLine::ReadClickOnceEnvVariables()
_itow_s(dwManifestPaths, buf.OpenUnicodeBuffer(size), size, 10);
buf.CloseBuffer();
manifestFile.Append(buf);
- if (WszGetEnvironmentVariable(manifestFile.GetUnicode(), NULL, 0) > 0)
+ SString temp;
+ if (WszGetEnvironmentVariable(manifestFile.GetUnicode(), temp) > 0)
dwManifestPaths++;
else
break;
@@ -4946,10 +4965,11 @@ HRESULT CorCommandLine::ReadClickOnceEnvVariables()
_itow_s(i, buf.OpenUnicodeBuffer(size), size, 10);
buf.CloseBuffer();
manifestFile.Append(buf);
- DWORD cManifestPath = WszGetEnvironmentVariable(manifestFile.GetUnicode(), NULL, 0);
+ PathString m_ppwszManifestPathsHolder;
+ DWORD cManifestPath = WszGetEnvironmentVariable(manifestFile.GetUnicode(), m_ppwszManifestPathsHolder);
if (cManifestPath > 0) {
- m_ppwszManifestPaths[i] = new WCHAR[cManifestPath];
- WszGetEnvironmentVariable(manifestFile.GetUnicode(), m_ppwszManifestPaths[i], cManifestPath);
+
+ m_ppwszManifestPaths[i] = m_ppwszManifestPathsHolder.GetCopyOfUnicodeString();
WszSetEnvironmentVariable(manifestFile.GetUnicode(), NULL); // reset the env. variable.
}
}
@@ -4964,7 +4984,8 @@ HRESULT CorCommandLine::ReadClickOnceEnvVariables()
_itow_s(dwActivationData, buf.OpenUnicodeBuffer(size), size, 10);
buf.CloseBuffer();
activationData.Append(buf);
- if (WszGetEnvironmentVariable(activationData.GetUnicode(), NULL, 0) > 0)
+ SString temp;
+ if (WszGetEnvironmentVariable(activationData.GetUnicode(), temp) > 0)
dwActivationData++;
else
break;
@@ -4977,10 +4998,10 @@ HRESULT CorCommandLine::ReadClickOnceEnvVariables()
_itow_s(i, buf.OpenUnicodeBuffer(size), size, 10);
buf.CloseBuffer();
activationData.Append(buf);
- DWORD cActivationData = WszGetEnvironmentVariable(activationData.GetUnicode(), NULL, 0);
+ PathString m_ppwszActivationDataHolder;
+ DWORD cActivationData = WszGetEnvironmentVariable(activationData.GetUnicode(), m_ppwszActivationDataHolder);
if (cActivationData > 0) {
- m_ppwszActivationData[i] = new WCHAR[cActivationData];
- WszGetEnvironmentVariable(activationData.GetUnicode(), m_ppwszActivationData[i], cActivationData);
+ m_ppwszActivationData[i] = m_ppwszActivationDataHolder.GetCopyOfUnicodeString();
WszSetEnvironmentVariable(activationData.GetUnicode(), NULL); // reset the env. variable.
}
}
diff --git a/src/vm/codeman.cpp b/src/vm/codeman.cpp
index 9374a2c8a9..4f99539215 100644
--- a/src/vm/codeman.cpp
+++ b/src/vm/codeman.cpp
@@ -1386,10 +1386,12 @@ static void LoadAndInitializeJIT(LPCWSTR pwzJitName, OUT HINSTANCE* phJit, OUT I
HRESULT hr = E_FAIL;
#ifdef FEATURE_MERGE_JIT_AND_ENGINE
- WCHAR CoreClrFolder[MAX_LONGPATH + 1];
+ PathString CoreClrFolderHolder;
extern HINSTANCE g_hThisInst;
- if (WszGetModuleFileName(g_hThisInst, CoreClrFolder, MAX_LONGPATH))
+ if (WszGetModuleFileName(g_hThisInst, CoreClrFolderHolder))
{
+ DWORD len = CoreClrFolderHolder.GetCount();
+ WCHAR* CoreClrFolder = CoreClrFolderHolder.OpenUnicodeBuffer(len);
WCHAR *filePtr = wcsrchr(CoreClrFolder, DIRECTORY_SEPARATOR_CHAR_W);
if (filePtr)
{
@@ -1401,6 +1403,7 @@ static void LoadAndInitializeJIT(LPCWSTR pwzJitName, OUT HINSTANCE* phJit, OUT I
hr = S_OK;
}
}
+ CoreClrFolderHolder.CloseBuffer();
}
#else
hr = g_pCLRRuntime->LoadLibrary(pwzJitName, phJit);
diff --git a/src/vm/corhost.cpp b/src/vm/corhost.cpp
index 2a7cf45249..f0e90291b7 100644
--- a/src/vm/corhost.cpp
+++ b/src/vm/corhost.cpp
@@ -2471,10 +2471,9 @@ HRESULT CorHost2::ExecuteMain(
AppDomain *pDomain = GetAppDomain();
_ASSERTE(pDomain);
- WCHAR wzExeFileName[_MAX_PATH];
- DWORD cchExeFileName = _MAX_PATH;
- cchExeFileName = WszGetModuleFileName(nullptr, wzExeFileName, cchExeFileName);
- if (cchExeFileName == _MAX_PATH)
+ PathString wzExeFileName;
+
+ if (WszGetModuleFileName(nullptr, wzExeFileName) == 0)
IfFailThrow(E_UNEXPECTED);
LPWSTR wzExeSimpleFileName = nullptr;
diff --git a/src/vm/dwbucketmanager.hpp b/src/vm/dwbucketmanager.hpp
index 48746d4816..a3aef9b2a8 100644
--- a/src/vm/dwbucketmanager.hpp
+++ b/src/vm/dwbucketmanager.hpp
@@ -323,7 +323,6 @@ private:
void FindFaultingMethodInfo();
OBJECTREF GetRealExceptionObject();
WCHAR* GetParamBufferForIndex(BucketParameterIndex paramIndex);
- int CopyStringToBucket(__out_ecount(targetMaxLength) LPWSTR pTargetParam, int targetMaxLength, __in_z LPCWSTR pSource, bool cannonicalize = false);
void LogParam(__in_z LPCWSTR paramValue, BucketParameterIndex paramIndex);
protected:
@@ -349,7 +348,7 @@ protected:
public:
BaseBucketParamsManager(GenericModeBlock* pGenericModeBlock, TypeOfReportedError typeOfError, PCODE initialFaultingPc, Thread* pFaultingThread, OBJECTREF* pThrownException);
-
+ static int CopyStringToBucket(__out_ecount(targetMaxLength) LPWSTR pTargetParam, int targetMaxLength, __in_z LPCWSTR pSource, bool cannonicalize = false);
// function that consumers should call to populate the GMB
virtual void PopulateBucketParameters() = 0;
};
@@ -485,10 +484,10 @@ void BaseBucketParamsManager::GetAppName(__out_ecount(maxLength) WCHAR* targetPa
CONTRACTL_END;
HMODULE hModule = WszGetModuleHandle(NULL);
- WCHAR appPath[MAX_LONGPATH];
- DWORD cchAppPath = NumItems(appPath);
+ PathString appPath;
+
- if (GetCurrentModuleFileName(appPath, &cchAppPath) == S_OK)
+ if (GetCurrentModuleFileName(appPath) == S_OK)
{
CopyStringToBucket(targetParam, maxLength, appPath);
}
@@ -509,13 +508,13 @@ void BaseBucketParamsManager::GetAppVersion(__out_ecount(maxLength) WCHAR* targe
CONTRACTL_END;
HMODULE hModule = WszGetModuleHandle(NULL);
- WCHAR appPath[MAX_LONGPATH];
- DWORD cchAppPath = NumItems(appPath);
+ PathString appPath;
+
WCHAR verBuf[23] = {0};
USHORT major, minor, build, revision;
- if ((GetCurrentModuleFileName(appPath, &cchAppPath) == S_OK) && SUCCEEDED(DwGetFileVersionInfo(appPath, major, minor, build, revision)))
+ if ((GetCurrentModuleFileName(appPath) == S_OK) && SUCCEEDED(DwGetFileVersionInfo(appPath, major, minor, build, revision)))
{
_snwprintf_s(targetParam,
maxLength,
diff --git a/src/vm/dwreport.cpp b/src/vm/dwreport.cpp
index 15a58c0701..77669b2f14 100644
--- a/src/vm/dwreport.cpp
+++ b/src/vm/dwreport.cpp
@@ -214,15 +214,6 @@ BOOL RegisterOutOfProcessWatsonCallbacks()
CONTRACTL_END;
WCHAR wszDACName[] = MAIN_DAC_MODULE_NAME_W W(".dll");
- WCHAR wszDACPath[MAX_LONGPATH];
- DWORD dwSize = 0;
-
- if ((FAILED(::GetCORSystemDirectoryInternal(wszDACPath, NumItems(wszDACPath), &dwSize))) ||
- (wcscat_s(wszDACPath, _countof(wszDACPath), wszDACName) != 0))
- {
- return FALSE;
- }
-
WerModuleHolder hWerModule(WER_MODULE_NAME_W);
#ifdef FEATURE_CORESYSTEM
@@ -250,8 +241,23 @@ BOOL RegisterOutOfProcessWatsonCallbacks()
{
return FALSE;
}
+ HRESULT hr = S_OK;
- HRESULT hr = (*pFnWerRegisterRuntimeExceptionModule)(wszDACPath, (PDWORD)g_pMSCorEE);
+ EX_TRY
+ {
+ PathString wszDACPath;
+ if (SUCCEEDED(::GetCORSystemDirectoryInternaL(wszDACPath)))
+ {
+ wszDACPath.Append(wszDACName);
+ hr = (*pFnWerRegisterRuntimeExceptionModule)(wszDACPath, (PDWORD)g_pMSCorEE);
+ }
+ else {
+ hr = E_FAIL;
+ }
+
+ }
+ EX_CATCH_HRESULT(hr);
+
if (FAILED(hr))
{
STRESS_LOG0(LF_STARTUP,
@@ -562,9 +568,9 @@ HRESULT DwCheckCompany( // S_OK or error.
// None
//------------------------------------------------------------------------------
int DwGetAppDescription( // Number of characters written.
- __in_z LPWSTR wszFilePath, // Path to the executable.
- __inout_ecount(cchBuf) WCHAR *pBuf, // Put description here.
- int cchBuf) // Size of buf, wide chars.
+ __in_z LPCWSTR wszFilePath, // Path to the executable.
+ SString& pBuf // Put description here.
+ ) // Size of buf, wide chars.
{
CONTRACTL
{
@@ -663,8 +669,17 @@ int DwGetAppDescription( // Number of characters written.
}
// Copy back the description.
- size = (int)size > cchBuf-1 ? cchBuf-1 : size;
- wcsncpy_s(pBuf, cchBuf, fileDescription, size);
+ EX_TRY
+ {
+ wcsncpy_s(pBuf.OpenUnicodeBuffer(size), size, fileDescription, size);
+ pBuf.CloseBuffer(size);
+ }
+ EX_CATCH
+ {
+ size = 0;
+ }
+ EX_END_CATCH(SwallowAllExceptions);
+
return size;
} // int DwGetAppDescription()
@@ -685,7 +700,7 @@ int DwGetAppDescription( // Number of characters written.
// None
//------------------------------------------------------------------------------
int DwGetAssemblyVersion( // Number of characters written.
- __in_z LPWSTR wszFilePath, // Path to the executable.
+ __in_z LPCWSTR wszFilePath, // Path to the executable.
__inout_ecount(cchBuf) WCHAR *pBuf, // Put description here.
int cchBuf) // Size of buf, wide chars.
{
@@ -1469,88 +1484,99 @@ BOOL RunWatson(
memset(&startupInfo, 0, sizeof(STARTUPINFOW));
startupInfo.cb = sizeof(STARTUPINFOW);
+ HRESULT hr = S_OK;
+ PathString watsonAppName;
+ PathString watsonCommandLine;
+ EX_TRY
+ {
+ do
+ {
- WCHAR watsonAppName[MAX_LONGPATH];
- WCHAR watsonCommandLine[MAX_LONGPATH+1];
- {
-#if !defined(FEATURE_CORECLR)
- // Use the version of DW20.exe that lives in the system directory.
- DWORD ret;
+
- if (FAILED(GetCORSystemDirectoryInternal(watsonAppName, NumItems(watsonAppName), &ret)))
- {
- return false;
- }
- if (wcsncat_s(watsonAppName, NumItems(watsonAppName), kWatsonImageNameOnVista, _TRUNCATE) != 0)
- {
- return false;
- }
-#else // FEATURE_CORECLR
- HKEYHolder hKey;
- // Look for key \\HKLM\Software\Microsoft\PCHealth\ErrorReporting\DW\Installed"
- DWORD ret = WszRegOpenKeyEx(HKEY_LOCAL_MACHINE,
- kWatsonPath,
- 0,
- KEY_READ | kWatsonRegKeyOptions,
- &hKey);
-
- if (ERROR_SUCCESS != ret)
{
- return false;
- }
+ #if !defined(FEATURE_CORECLR)
+ // Use the version of DW20.exe that lives in the system directory.
+ DWORD ret;
+ if (FAILED(GetCORSystemDirectoryInternaL(watsonAppName)))
+ {
+ hr = E_FAIL;
+ break;
+ }
+ watsonCommandLine.Set(watsonAppName);
+ watsonCommandLine.Append(kWatsonImageNameOnVista);
+
+ #else // FEATURE_CORECLR
+ HKEYHolder hKey;
+ // Look for key \\HKLM\Software\Microsoft\PCHealth\ErrorReporting\DW\Installed"
+ DWORD ret = WszRegOpenKeyEx(HKEY_LOCAL_MACHINE,
+ kWatsonPath,
+ 0,
+ KEY_READ | kWatsonRegKeyOptions,
+ &hKey);
+
+ if (ERROR_SUCCESS != ret)
+ {
+ hr = E_FAIL;
+ break;
+ }
- // Look in ...\DW\Installed for dw0200 (dw0201 on ia64). This will be
- // the full path to the executable.
- DWORD size = NumItems(watsonAppName);
- ret = WszRegQueryValueEx(hKey,
- kWatsonValue,
- NULL,
- NULL,
- reinterpret_cast< LPBYTE >(watsonAppName),
- &size);
-
- if (ERROR_SUCCESS != ret)
- {
- return false;
- }
-#endif // ! FEATURE_CORECLR
+ // Look in ...\DW\Installed for dw0200 (dw0201 on ia64). This will be
+ // the full path to the executable.
+
+ ClrRegReadString(hKey, kWatsonValue, watsonAppName);
+
+ #endif // ! FEATURE_CORECLR
- _snwprintf_s(watsonCommandLine,
- NumItems(watsonCommandLine)-1,
- _TRUNCATE,
- W("dw20.exe -x -s %lu"),
- PtrToUlong(hWatsonSharedMemory));
- watsonCommandLine[NumItems(watsonCommandLine) - 1] = W('\0');
+ COUNT_T len = watsonCommandLine.GetCount();
+ WCHAR* buffer = watsonCommandLine.OpenUnicodeBuffer(len);
+ _snwprintf_s(buffer,
+ len,
+ _TRUNCATE,
+ W("dw20.exe -x -s %lu"),
+ PtrToUlong(hWatsonSharedMemory));
+ watsonCommandLine.CloseBuffer();
+
+ }
+ } while (false);
}
+ EX_CATCH_HRESULT(hr);
+ if (hr != S_OK)
{
- BOOL ret = WszCreateProcess(watsonAppName,
- watsonCommandLine,
- NULL,
- NULL,
- TRUE,
- NULL,
- NULL,
- NULL,
- &startupInfo,
- &processInformation);
+ return false;
+ }
- if (FALSE == ret)
{
- //
- // Watson failed to start up.
- //
- // This can happen if e.g. Watson wasn't installed on the machine.
- //
- HRESULT hr = HRESULT_FROM_GetLastErrorNA();
- return false;
+ BOOL ret = WszCreateProcess(watsonAppName,
+ watsonCommandLine,
+ NULL,
+ NULL,
+ TRUE,
+ NULL,
+ NULL,
+ NULL,
+ &startupInfo,
+ &processInformation);
+
+ if (FALSE == ret)
+ {
+ //
+ // Watson failed to start up.
+ //
+ // This can happen if e.g. Watson wasn't installed on the machine.
+ //
+ return E_FAIL;
+
+ }
+
}
- }
+
// Wait for watson to finish.
//
@@ -2426,9 +2452,11 @@ FaultReportResult DoFaultReportWorker( // Was Watson attempted, successful?
pWatsonSharedMemory->bfmsoctdsLetRun = offerFlags;
{
+ PathString wzModuleFileName;
DWORD dwRet = WszGetModuleFileName(NULL,
- pWatsonSharedMemory->wzModuleFileName,
- NumItems(pWatsonSharedMemory->wzModuleFileName));
+ wzModuleFileName);
+ BaseBucketParamsManager::CopyStringToBucket(pWatsonSharedMemory->wzModuleFileName, NumItems(pWatsonSharedMemory->wzModuleFileName), wzModuleFileName);
+
_ASSERTE(0 != dwRet);
if (0 == dwRet)
{
@@ -2455,24 +2483,24 @@ FaultReportResult DoFaultReportWorker( // Was Watson attempted, successful?
// do this just by using the executable name.
//
{
- WCHAR buf[_MAX_PATH]; // Buffer for path for description.
- WCHAR *pName = buf; // Pointer to filename or description.
+ PathString buf; // Buffer for path for description.
+ LPCWSTR pName ; // Pointer to filename or description.
int size; // Size of description.
HMODULE hModule; // Handle to module.
DWORD result; // Return code
// Get module name.
hModule = WszGetModuleHandle(NULL);
- result = WszGetModuleFileName(hModule, buf, NumItems(buf));
+ result = WszGetModuleFileName(hModule, buf);
if (result == 0)
{ // Couldn't get module name. This should never happen.
- wcscpy_s(buf, COUNTOF(buf), W("<<unknown>>"));
+ pName = W("<<unknown>>");
}
else
{ // re-use the buf for pathname and description.
- size = DwGetAppDescription(buf, buf, NumItems(buf));
-
+ size = DwGetAppDescription(buf, buf);
+ pName = buf.GetUnicode();
// If the returned size was zero, buf wasn't changed, and still contains the path.
// find just the filename part.
if (size == 0)
diff --git a/src/vm/dwreport.h b/src/vm/dwreport.h
index a2750cefe7..44306689ea 100644
--- a/src/vm/dwreport.h
+++ b/src/vm/dwreport.h
@@ -58,7 +58,7 @@ BOOL IsWatsonEnabled();
BOOL RegisterOutOfProcessWatsonCallbacks();
int DwGetAssemblyVersion( // Number of characters written.
- __in_z LPWSTR wszFilePath, // Path to the executable.
+ __in_z LPCWSTR wszFilePath, // Path to the executable.
__inout_ecount(cchBuf) WCHAR *pBuf, // Put description here.
int cchBuf);
diff --git a/src/vm/eeconfig.cpp b/src/vm/eeconfig.cpp
index e322a63f5e..973a4f4235 100644
--- a/src/vm/eeconfig.cpp
+++ b/src/vm/eeconfig.cpp
@@ -835,12 +835,12 @@ HRESULT EEConfig::sync()
{
bGCStressAndHeapVerifyAllowed = false;
- WCHAR wszFileName[_MAX_PATH];
- if (WszGetModuleFileName(NULL, wszFileName, _MAX_PATH) != 0)
+ PathString wszFileName;
+ if (WszGetModuleFileName(NULL, wszFileName) != 0)
{
// just keep the name
- LPWSTR pwszName = wcsrchr(wszFileName, W('\\'));
- pwszName = (pwszName == NULL) ? wszFileName : (pwszName + 1);
+ LPCWSTR pwszName = wcsrchr(wszFileName, W('\\'));
+ pwszName = (pwszName == NULL) ? wszFileName.GetUnicode() : (pwszName + 1);
if (SString::_wcsicmp(pwszName,pszGCStressExe) == 0)
{
@@ -1619,46 +1619,62 @@ HRESULT EEConfig::SetupConfiguration()
// AppX process check to make sure no app.config file
// exists unless launched with AO_DESIGNMODE.
// ----------------------------------------------------
+
+ do
{
- WCHAR wzProcExe[_MAX_PATH];
- size_t cchProcExe = COUNTOF(wzProcExe);
-
- // Get name of file used to create process
- if (g_pCachedModuleFileName)
- {
- IfFailRet(StringCchCopy(wzProcExe, COUNTOF(wzProcExe), g_pCachedModuleFileName));
- IfFailRet(StringCchLength(wzProcExe, COUNTOF(wzProcExe), &cchProcExe));
- }
- else
+ size_t cchProcExe=0;
+ PathString wzProcExe;
+ EX_TRY
{
- cchProcExe = WszGetModuleFileName(NULL, wzProcExe, COUNTOF(wzProcExe));
- if (cchProcExe == 0)
+
+
+ // Get name of file used to create process
+ if (g_pCachedModuleFileName)
{
- return HRESULT_FROM_GetLastError();
+ wzProcExe.Set(g_pCachedModuleFileName);
+ cchProcExe = wzProcExe.GetCount();
}
- }
+ else
+ {
+ cchProcExe = WszGetModuleFileName(NULL, wzProcExe);
- if (cchProcExe != 0)
- {
- IfFailRet(StringCchCat(wzProcExe, COUNTOF(wzProcExe), CONFIGURATION_EXTENSION));
+ if (cchProcExe == 0)
+ {
+ hr = HRESULT_FROM_GetLastError();
+ break;
+ }
+ }
- if (AppX::IsAppXProcess() && !AppX::IsAppXDesignMode())
+ if (cchProcExe != 0)
{
- if (clr::fs::Path::Exists(wzProcExe))
+ wzProcExe.Append(CONFIGURATION_EXTENSION);
+
+ if (AppX::IsAppXProcess() && !AppX::IsAppXDesignMode())
{
- return CLR_E_APP_CONFIG_NOT_ALLOWED_IN_APPX_PROCESS;
+ if (clr::fs::Path::Exists(wzProcExe))
+ {
+ hr = CLR_E_APP_CONFIG_NOT_ALLOWED_IN_APPX_PROCESS;
+ break;
+ }
}
}
-
+ }
+ EX_CATCH_HRESULT(hr);
+ if (cchProcExe != 0)
+ {
IfFailParseError(wzProcExe, true, AppendConfigurationFile(wzProcExe, version));
// We really should return a failure hresult if the app config file is bad, but that
// would be a breaking change. Not sure if it's worth it yet.
hr = S_OK;
+ break;
}
- }
+ } while (false);
+
+ if (hr != S_OK)
+ return hr;
// ----------------------------------------------------
// Import machine.config, if needed.
// ----------------------------------------------------
diff --git a/src/vm/eepolicy.cpp b/src/vm/eepolicy.cpp
index c67d06d596..8c3f2ec625 100644
--- a/src/vm/eepolicy.cpp
+++ b/src/vm/eepolicy.cpp
@@ -530,11 +530,11 @@ void SafeExitProcess(UINT exitCode, BOOL fAbort = FALSE, ShutdownCompleteAction
if (CLRConfig::GetConfigValue(CLRConfig::UNSUPPORTED_BreakOnBadExit))
{
// Workaround for aspnet
- WCHAR wszFilename[_MAX_PATH];
+ PathString wszFilename;
bool bShouldAssert = true;
- if (WszGetModuleFileName(NULL, wszFilename, _MAX_PATH))
+ if (WszGetModuleFileName(NULL, wszFilename))
{
- _wcslwr_s(wszFilename, COUNTOF(wszFilename));
+ wszFilename.LowerCase();
if (wcsstr(wszFilename, W("aspnet_compiler")))
{
diff --git a/src/vm/eventreporter.cpp b/src/vm/eventreporter.cpp
index e07a6401cd..567f4f5d51 100644
--- a/src/vm/eventreporter.cpp
+++ b/src/vm/eventreporter.cpp
@@ -47,8 +47,8 @@ EventReporter::EventReporter(EventReporterType type)
m_eventType = type;
HMODULE hModule = WszGetModuleHandle(NULL);
- WCHAR appPath[MAX_LONGPATH];
- DWORD ret = WszGetModuleFileName(hModule, appPath, NumItems(appPath));
+ PathString appPath;
+ DWORD ret = WszGetModuleFileName(hModule, appPath);
fBufferFull = FALSE;
@@ -65,7 +65,7 @@ EventReporter::EventReporter(EventReporterType type)
if (ret != 0)
{
// If app name has a '\', consider the part after that; otherwise consider whole name.
- WCHAR* appName = wcsrchr(appPath, W('\\'));
+ LPCWSTR appName = wcsrchr(appPath, W('\\'));
appName = appName ? appName+1 : appPath;
m_Description.Append(appName);
m_Description.Append(W("\n"));
@@ -808,8 +808,8 @@ void EventReporter::GetCoreCLRInstanceProductVersion(DWORD * pdwMajor, DWORD * p
_ASSERTE(hModRuntime != NULL);
// Get the path to the runtime
- WCHAR runtimePath[MAX_LONGPATH];
- DWORD ret = WszGetModuleFileName(hModRuntime, runtimePath, NumItems(runtimePath));
+ PathString runtimePath;
+ DWORD ret = WszGetModuleFileName(hModRuntime, runtimePath);
if (ret != 0)
{
// Got the path - get the file version from the path
diff --git a/src/vm/eventtrace.cpp b/src/vm/eventtrace.cpp
index e6a25cc853..5e35f9a2b8 100644
--- a/src/vm/eventtrace.cpp
+++ b/src/vm/eventtrace.cpp
@@ -4869,7 +4869,7 @@ VOID ETW::InfoLog::RuntimeInformation(INT32 type)
PCWSTR szDtraceOutput1=W(""),szDtraceOutput2=W("");
UINT8 startupMode = 0;
UINT startupFlags = 0;
- WCHAR dllPath[MAX_LONGPATH+1] = {0};
+ PathString dllPath;
UINT8 Sku = 0;
_ASSERTE(g_fEEManagedEXEStartup || //CLR started due to a managed exe
g_fEEIJWStartup || //CLR started as a mixed mode Assembly
@@ -4899,7 +4899,7 @@ VOID ETW::InfoLog::RuntimeInformation(INT32 type)
LPCGUID comGUID=&g_EEComObjectGuid;
PCWSTR lpwszCommandLine = W("");
- PCWSTR lpwszRuntimeDllPath = (PCWSTR)dllPath;
+
#ifndef FEATURE_CORECLR
startupFlags = CorHost2::GetStartupFlags();
@@ -4954,12 +4954,12 @@ VOID ETW::InfoLog::RuntimeInformation(INT32 type)
startupMode = ETW::InfoLog::InfoStructs::Other;
}
- _ASSERTE (NumItems(dllPath) > MAX_LONGPATH);
+
// if WszGetModuleFileName fails, we return an empty string
- if (!WszGetModuleFileName(GetCLRModule(), dllPath, MAX_LONGPATH)) {
- dllPath[0] = 0;
+ if (!WszGetModuleFileName(GetCLRModule(), dllPath)) {
+ dllPath.Set(W("\0"));
}
- dllPath[MAX_LONGPATH] = 0;
+
if(type == ETW::InfoLog::InfoStructs::Callback)
{
@@ -4977,7 +4977,7 @@ VOID ETW::InfoLog::RuntimeInformation(INT32 type)
startupMode,
lpwszCommandLine,
comGUID,
- lpwszRuntimeDllPath );
+ dllPath );
}
else
{
@@ -4995,7 +4995,7 @@ VOID ETW::InfoLog::RuntimeInformation(INT32 type)
startupMode,
lpwszCommandLine,
comGUID,
- lpwszRuntimeDllPath );
+ dllPath );
}
}
} EX_CATCH { } EX_END_CATCH(SwallowAllExceptions);
diff --git a/src/vm/mdaassistants.cpp b/src/vm/mdaassistants.cpp
index de81a82f83..cc598c0a6c 100644
--- a/src/vm/mdaassistants.cpp
+++ b/src/vm/mdaassistants.cpp
@@ -995,12 +995,12 @@ void MdaPInvokeLog::LogPInvoke(NDirectMethodDesc* pMD, HINSTANCE hMod)
StackSString sszEntryPoint;
sszEntryPoint.SetUTF8(pMD->GetEntrypointName());
- WCHAR szDllFullName[_MAX_PATH] = {0};
+ PathString szDllFullName ;
WCHAR szDrive[_MAX_PATH] = {0};
WCHAR szPath[_MAX_PATH] = {0};
WCHAR szFileName[_MAX_PATH] = {0};
WCHAR szExt[_MAX_PATH] = {0};
- WszGetModuleFileName(hMod, szDllFullName, _MAX_PATH);
+ WszGetModuleFileName(hMod, szDllFullName);
SplitPath(szDllFullName, szDrive, _MAX_PATH, szPath, _MAX_PATH, szFileName, _MAX_PATH, szExt, _MAX_PATH);
StackSString sszDllName;
@@ -1869,16 +1869,14 @@ void MdaLoaderLock::ReportViolation(HINSTANCE hInst)
MdaXmlMessage msg(this->AsMdaAssistant(), TRUE, &pXml);
DWORD cName = 0;
- WCHAR szName[_MAX_PATH * 2];
+ PathString szName;
if (hInst)
{
- cName = _MAX_PATH * 2 - 1;
- cName = WszGetModuleFileName(hInst, szName, cName);
+ cName = WszGetModuleFileName(hInst, szName);
}
if (cName)
{
- szName[cName] = W('\0');
msg.SendMessagef(MDARC_LOADER_LOCK_DLL, szName);
}
else
diff --git a/src/vm/peimage.cpp b/src/vm/peimage.cpp
index 27904ff476..cb1dd50c9d 100644
--- a/src/vm/peimage.cpp
+++ b/src/vm/peimage.cpp
@@ -422,15 +422,8 @@ void PEImage::GetPathFromDll(HINSTANCE hMod, SString &result)
}
CONTRACTL_END;
- DWORD ret;
- DWORD length = MAX_LONGPATH;
- do
- {
- WCHAR *buffer = result.OpenUnicodeBuffer(length);
- ret = WszGetModuleFileName(hMod, buffer, length);
- result.CloseBuffer(ret);
- length *= 2;
- } while (ret == 0);
+ WszGetModuleFileName(hMod, result);
+
}
#endif // !FEATURE_PAL
diff --git a/src/vm/peimage.inl b/src/vm/peimage.inl
index 343b2bbbd9..c2f6957ba0 100644
--- a/src/vm/peimage.inl
+++ b/src/vm/peimage.inl
@@ -592,25 +592,9 @@ inline PTR_PEImage PEImage::FindByLongPath(LPCWSTR pPath)
}
CONTRACTL_END;
- InlineSString<MAX_PATH> sLongPath;
- // Note: GetLongPathName return the number of characters written NOT INCLUDING the
- // null character on success, and on failure returns the buffer size required
- // INCLUDING the null. This means the result must not be equal to MAX_PATH -
- // it must be greater or less then.
- COUNT_T nLen = WszGetLongPathName(pPath, sLongPath.OpenUnicodeBuffer(MAX_PATH-1), MAX_PATH);
- CONSISTENCY_CHECK(nLen != MAX_PATH);
-
- // If this was insufficient buffer, then try again with a reallocated buffer
- if (nLen > MAX_PATH)
- {
- // Close the buffer before reopening
- sLongPath.CloseBuffer();
- INDEBUG(SIZE_T nOldLen = nLen;)
- nLen = WszGetLongPathName(pPath, sLongPath.OpenUnicodeBuffer(nLen-1), nLen);
- CONSISTENCY_CHECK(nLen == (nOldLen - 1));
- }
- sLongPath.CloseBuffer(nLen);
-
+ PathString sLongPath;
+ COUNT_T nLen = WszGetLongPathName(pPath, sLongPath);
+
// Check for any kind of error other than an insufficient buffer result.
if (nLen == 0)
{
@@ -619,7 +603,7 @@ inline PTR_PEImage PEImage::FindByLongPath(LPCWSTR pPath)
ThrowHR(hr);
return (PEImage*)INVALIDENTRY;
}
- return FindByPath(sLongPath);
+ return FindByPath(sLongPath.GetUnicode());
}
/*static*/
@@ -634,24 +618,8 @@ inline PTR_PEImage PEImage::FindByShortPath(LPCWSTR pPath)
}
CONTRACTL_END;
- InlineSString<MAX_PATH> sShortPath;
- // Note: GetLongPathName return the number of characters written NOT INCLUDING the
- // null character on success, and on failure returns the buffer size required
- // INCLUDING the null. This means the result must not be equal to MAX_PATH -
- // it must be greater or less then.
- COUNT_T nLen = WszGetShortPathName(pPath, sShortPath.OpenUnicodeBuffer(MAX_PATH-1), MAX_PATH);
- CONSISTENCY_CHECK(nLen != MAX_PATH);
-
- // If this was insufficient buffer, then try again with a reallocated buffer
- if (nLen > MAX_PATH)
- {
- // Close the buffer before reopening
- sShortPath.CloseBuffer();
- INDEBUG(SIZE_T nOldLen = nLen;)
- nLen = WszGetShortPathName(pPath, sShortPath.OpenUnicodeBuffer(nLen-1), nLen);
- CONSISTENCY_CHECK(nLen == (nOldLen - 1));
- }
- sShortPath.CloseBuffer(nLen);
+ PathString sShortPath;
+ COUNT_T nLen = WszGetShortPathName(pPath, sShortPath);
// Check for any kind of error other than an insufficient buffer result.
if (nLen == 0)
@@ -661,7 +629,7 @@ inline PTR_PEImage PEImage::FindByShortPath(LPCWSTR pPath)
ThrowHR(hr);
return (PEImage*)INVALIDENTRY;
}
- return FindByPath(sShortPath);
+ return FindByPath(sShortPath.GetUnicode());
}
#endif // !FEATURE_CORECLR
diff --git a/src/vm/peimagelayout.cpp b/src/vm/peimagelayout.cpp
index 3868386860..8fdf554557 100644
--- a/src/vm/peimagelayout.cpp
+++ b/src/vm/peimagelayout.cpp
@@ -319,9 +319,9 @@ RawImageLayout::RawImageLayout(const void *mapped, PEImage* pOwner, BOOL bTakeOw
if (bTakeOwnership)
{
#ifndef FEATURE_PAL
- WCHAR wszDllName[MAX_LONGPATH];
- WszGetModuleFileName((HMODULE)mapped, wszDllName, MAX_LONGPATH);
- wszDllName[MAX_LONGPATH - 1] = W('\0');
+ PathString wszDllName;
+ WszGetModuleFileName((HMODULE)mapped, wszDllName);
+
m_LibraryHolder=CLRLoadLibraryEx(wszDllName,NULL,GetLoadWithAlteredSearchPathFlag());
#else // !FEATURE_PAL
_ASSERTE(!"bTakeOwnership Should not be used on FEATURE_PAL");
diff --git a/src/vm/securitypolicy.cpp b/src/vm/securitypolicy.cpp
index 082be54f88..fe1da90b8d 100644
--- a/src/vm/securitypolicy.cpp
+++ b/src/vm/securitypolicy.cpp
@@ -1,9 +1,6 @@
// Licensed to the .NET Foundation under one or more agreements.
-// The .NET Foundation licenses this file to you under the MIT license.
-// See the LICENSE file in the project root for more information.
-//
-
-//
+//The .NET Foundation licenses this file to you under the MIT license.
+//See the LICENSE file in the project root for more information.
#include "common.h"
@@ -676,12 +673,11 @@ void QCALLTYPE SecurityPolicy::_GetLongPathName(LPCWSTR wszPath, QCall::StringHa
BEGIN_QCALL;
#if !defined(PLATFORM_UNIX)
- WCHAR wszBuffer[MAX_LONGPATH + 1];
- ZeroMemory(wszBuffer, sizeof(wszBuffer));
+ PathString wszBuffer;
- if (SecurityPolicy::GetLongPathNameHelper( wszPath, wszBuffer, MAX_LONGPATH ) != 0)
+ if (SecurityPolicy::GetLongPathNameHelper( wszPath, wszBuffer ) != 0)
{
- retLongPath.Set( wszBuffer );
+ retLongPath.Set( wszBuffer.GetUnicode() );
}
#endif // !PLATFORM_UNIX
@@ -689,15 +685,15 @@ void QCALLTYPE SecurityPolicy::_GetLongPathName(LPCWSTR wszPath, QCall::StringHa
}
#if !defined(PLATFORM_UNIX)
-size_t SecurityPolicy::GetLongPathNameHelper( const WCHAR* wszShortPath, __inout_ecount(cchBuffer) __inout_z WCHAR* wszBuffer, DWORD cchBuffer )
+size_t GetLongPathNameHelperthatThrows(const WCHAR* wszShortPath, SString& wszBuffer)
{
- CONTRACTL {
- NOTHROW;
- GC_NOTRIGGER;
- MODE_ANY;
+ CONTRACTL{
+ THROWS;
+ GC_NOTRIGGER;
+ MODE_ANY;
} CONTRACTL_END;
- DWORD size = WszGetLongPathName(wszShortPath, wszBuffer, cchBuffer);
+ DWORD size = WszGetLongPathName(wszShortPath, wszBuffer);
if (size == 0)
{
@@ -707,66 +703,87 @@ size_t SecurityPolicy::GetLongPathNameHelper( const WCHAR* wszShortPath, __inout
// trying GetLongPathName on every subdirectory until
// it succeeds or we run out of string.
- WCHAR wszIntermediateBuffer[MAX_LONGPATH];
+ size_t len = wcslen(wszShortPath);
+ NewArrayHolder<WCHAR> wszIntermediateBuffer = new (nothrow) WCHAR[len + 1];
- if (wcslen( wszShortPath ) >= MAX_LONGPATH)
+ if (wszIntermediateBuffer == NULL)
+ {
return 0;
+ }
- wcscpy_s( wszIntermediateBuffer, COUNTOF(wszIntermediateBuffer), wszShortPath );
+ wcscpy_s(wszIntermediateBuffer, len + 1, wszShortPath);
- size_t index = wcslen( wszIntermediateBuffer );
+ size_t index = len;
do
{
- while (index > 0 && (wszIntermediateBuffer[index-1] != W('\\') && wszIntermediateBuffer[index-1] != W('/')))
+ while (index > 0 && (wszIntermediateBuffer[index - 1] != W('\\') && wszIntermediateBuffer[index - 1] != W('/')))
--index;
if (index == 0)
break;
- #ifdef _PREFAST_
- #pragma prefast(push)
- #pragma prefast(disable:26001, "suppress prefast warning about underflow by doing index-1 which is checked above.")
- #endif // _PREFAST_
-
- wszIntermediateBuffer[index-1] = W('\0');
+#ifdef _PREFAST_
+#pragma prefast(push)
+#pragma prefast(disable:26001, "suppress prefast warning about underflow by doing index-1 which is checked above.")
+#endif // _PREFAST_
+
+ wszIntermediateBuffer[index - 1] = W('\0');
- #ifdef _PREFAST_
- #pragma prefast(pop)
- #endif
+#ifdef _PREFAST_
+#pragma prefast(pop)
+#endif
- size = WszGetLongPathName(wszIntermediateBuffer, wszBuffer, MAX_LONGPATH);
+ size = WszGetLongPathName(wszIntermediateBuffer, wszBuffer);
if (size != 0)
{
- size_t sizeBuffer = wcslen( wszBuffer );
- if (sizeBuffer + wcslen( &wszIntermediateBuffer[index] ) > MAX_LONGPATH - 2)
- {
- return 0;
- }
- else
- {
- if (wszBuffer[sizeBuffer-1] != W('\\') && wszBuffer[sizeBuffer-1] != W('/'))
- wcscat_s( wszBuffer, cchBuffer, W("\\") );
- wcscat_s( wszBuffer, cchBuffer, &wszIntermediateBuffer[index] );
- return (DWORD)wcslen( wszBuffer );
- }
+ int sizeBuffer = wszBuffer.GetCount();
+
+ if (wszBuffer[sizeBuffer - 1] != W('\\') && wszBuffer[sizeBuffer - 1] != W('/'))
+ wszBuffer.Append(W("\\"));
+
+ wszBuffer.Append(&wszIntermediateBuffer[index]);
+
+
+ return (DWORD)wszBuffer.GetCount();
+
}
- }
- while( true );
+ } while (true);
return 0;
}
- else if (size > MAX_LONGPATH)
+ else
{
- return 0;
+ return (DWORD)wszBuffer.GetCount();
}
- else
+}
+size_t SecurityPolicy::GetLongPathNameHelper(const WCHAR* wszShortPath, SString& wszBuffer)
+{
+ CONTRACTL{
+ NOTHROW;
+ GC_NOTRIGGER;
+ MODE_ANY;
+ } CONTRACTL_END;
+
+ HRESULT hr = S_OK;
+ size_t retval = 0;
+
+ EX_TRY
{
- return wcslen( wszBuffer );
+ retval = GetLongPathNameHelperthatThrows(wszShortPath,wszBuffer);
}
+ EX_CATCH_HRESULT(hr);
+
+ if (hr != S_OK)
+ {
+ retval = 0;
+ }
+
+ return retval;
}
+
#endif // !PLATFORM_UNIX
void QCALLTYPE SecurityPolicy::GetDeviceName(LPCWSTR wszDriveLetter, QCall::StringHandleOnStack retDeviceName)
diff --git a/src/vm/securitypolicy.h b/src/vm/securitypolicy.h
index cf2b10f21c..ba77bcbda8 100644
--- a/src/vm/securitypolicy.h
+++ b/src/vm/securitypolicy.h
@@ -198,7 +198,7 @@ namespace SecurityPolicy
BOOL WasStrongNameEvidenceUsed(OBJECTREF evidence);
#endif
// Like WszGetLongPathName, but it works with nonexistant files too
- size_t GetLongPathNameHelper( const WCHAR* wszShortPath, __inout_ecount(cchBuffer) __inout_z WCHAR* wszBuffer, DWORD cchBuffer );
+ size_t GetLongPathNameHelper( const WCHAR* wszShortPath, SString& wszBuffer);
#ifdef FEATURE_CAS_POLICY
extern CrstStatic s_crstPolicyInit;
diff --git a/src/zap/zapper.cpp b/src/zap/zapper.cpp
index 42589874b1..6d559d377b 100644
--- a/src/zap/zapper.cpp
+++ b/src/zap/zapper.cpp
@@ -730,15 +730,14 @@ void Zapper::LoadAndInitializeJITForNgen(LPCWSTR pwzJitName, OUT HINSTANCE* phJi
HRESULT hr = E_FAIL;
#ifdef FEATURE_MERGE_JIT_AND_ENGINE
- WCHAR CoreClrFolder[MAX_LONGPATH + 1];
+ PathString CoreClrFolder;
extern HINSTANCE g_hThisInst;
- if (WszGetModuleFileName(g_hThisInst, CoreClrFolder, MAX_LONGPATH))
+ if (WszGetModuleFileName(g_hThisInst, CoreClrFolder))
{
- WCHAR *filePtr = wcsrchr(CoreClrFolder, W('\\'));
- if (filePtr)
+ if (SUCCEEDED(CopySystemDirectory(CoreClrFolder, CoreClrFolder)))
{
- filePtr[1] = W('\0');
- wcscat_s(CoreClrFolder, MAX_LONGPATH, pwzJitName);
+ CoreClrFolder.Append(pwzJitName);
+
*phJit = ::WszLoadLibrary(CoreClrFolder);
if (*phJit == NULL)
{