This Change Adds initial Support for LongFiles in the VM,
authorRama Krishnan Raghupathy <ramarag@microsoft.com>
Fri, 19 Feb 2016 02:21:18 +0000 (18:21 -0800)
committerRama Krishnan Raghupathy <ramarag@microsoft.com>
Sat, 20 Feb 2016 02:09:11 +0000 (18:09 -0800)
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

Commit migrated from https://github.com/dotnet/coreclr/commit/f98fb85e72d0f24c58d9e54b8b3bff2c67f985fb

59 files changed:
src/coreclr/src/classlibnative/bcltype/system.cpp
src/coreclr/src/debug/di/cordb.cpp
src/coreclr/src/debug/di/module.cpp
src/coreclr/src/debug/di/shimprocess.cpp
src/coreclr/src/debug/ee/debugger.cpp
src/coreclr/src/dlls/mscoree/delayload.cpp
src/coreclr/src/dlls/mscoree/mscoree.cpp
src/coreclr/src/dlls/mscorpe/ceefilegenwriter.cpp
src/coreclr/src/dlls/mscorpe/pewriter.cpp
src/coreclr/src/ilasm/grammar_after.cpp
src/coreclr/src/ilasm/main.cpp
src/coreclr/src/inc/corpriv.h
src/coreclr/src/inc/longfilepathwrappers.h [new file with mode: 0644]
src/coreclr/src/inc/sstring.h
src/coreclr/src/inc/sstring.inl
src/coreclr/src/inc/utilcode.h
src/coreclr/src/inc/winwrap.h
src/coreclr/src/md/compiler/disp.cpp
src/coreclr/src/md/compiler/mdutil.cpp
src/coreclr/src/md/compiler/mdutil.h
src/coreclr/src/pal/inc/pal.h
src/coreclr/src/pal/src/loader/module.cpp
src/coreclr/src/strongname/api/strongnamecoreclr.cpp
src/coreclr/src/tools/crossgen/crossgen.cpp
src/coreclr/src/utilcode/CMakeLists.txt
src/coreclr/src/utilcode/UtilCode.vcproj
src/coreclr/src/utilcode/UtilCode.vcxproj
src/coreclr/src/utilcode/ccomprc.cpp
src/coreclr/src/utilcode/debug.cpp
src/coreclr/src/utilcode/jitperf.cpp
src/coreclr/src/utilcode/longfilepathwrappers.cpp [new file with mode: 0644]
src/coreclr/src/utilcode/makepath.cpp
src/coreclr/src/utilcode/perflog.cpp
src/coreclr/src/utilcode/regutil.cpp
src/coreclr/src/utilcode/safewrap.cpp
src/coreclr/src/utilcode/stacktrace.cpp
src/coreclr/src/utilcode/util.cpp
src/coreclr/src/utilcode/util_nodependencies.cpp
src/coreclr/src/utilcode/utilcode.settings.targets
src/coreclr/src/utilcode/utilmessagebox.cpp
src/coreclr/src/vm/appdomain.cpp
src/coreclr/src/vm/assemblynative.cpp
src/coreclr/src/vm/ceemain.cpp
src/coreclr/src/vm/codeman.cpp
src/coreclr/src/vm/corhost.cpp
src/coreclr/src/vm/dwbucketmanager.hpp
src/coreclr/src/vm/dwreport.cpp
src/coreclr/src/vm/dwreport.h
src/coreclr/src/vm/eeconfig.cpp
src/coreclr/src/vm/eepolicy.cpp
src/coreclr/src/vm/eventreporter.cpp
src/coreclr/src/vm/eventtrace.cpp
src/coreclr/src/vm/mdaassistants.cpp
src/coreclr/src/vm/peimage.cpp
src/coreclr/src/vm/peimage.inl
src/coreclr/src/vm/peimagelayout.cpp
src/coreclr/src/vm/securitypolicy.cpp
src/coreclr/src/vm/securitypolicy.h
src/coreclr/src/zap/zapper.cpp

index c950039..e902734 100644 (file)
@@ -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());
     }
index 3a4fdff..497225f 100644 (file)
@@ -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
 
index 700a362..78c7599 100644 (file)
@@ -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));
index f15ab3f..a6fc154 100644 (file)
@@ -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)
index 5905965..c063eb8 100644 (file)
@@ -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
index 40fb247..d74f58b 100644 (file)
@@ -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;
index 11863e9..d42733a 100644 (file)
@@ -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);
     }
index 6703148..cfd1ebb 100644 (file)
@@ -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();
     }
index 6ad6760..f3b5fb1 100644 (file)
@@ -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,
index 61de517..c863480 100644 (file)
@@ -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);
index 50131b2..811c656 100644 (file)
@@ -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)))
index f90d2ab..1a8f671 100644 (file)
@@ -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/coreclr/src/inc/longfilepathwrappers.h b/src/coreclr/src/inc/longfilepathwrappers.h
new file mode 100644 (file)
index 0000000..b3fc6ad
--- /dev/null
@@ -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_
+
index 3c5107a..bfbaa81 100644 (file)
@@ -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
 
 // ================================================================================
index b9c6895..6b587e1 100644 (file)
@@ -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.
 //----------------------------------------------------------------------------
index 78dc438..a9cb007 100644 (file)
@@ -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
index 6896acc..89a3220 100644 (file)
@@ -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_
 //
 #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
 // 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.
 #define WszCryptVerifySignature CryptVerifySignatureW
 
 // winbase.h
-#define WszGetBinaryType GetBinaryTypeW
-#define WszGetShortPathName GetShortPathNameW
-#define WszGetLongPathName GetLongPathNameW
 #define WszGetEnvironmentStrings   GetEnvironmentStringsW
 #define WszFreeEnvironmentStrings   FreeEnvironmentStringsW
 #ifndef USE_FORMATMESSAGE_WRAPPER
 #define WszFormatMessage   CCompRC::FormatMessage
 #endif
 #define WszCreateMailslot   CreateMailslotW
-#define WszEncryptFile   EncryptFileW
-#define WszDecryptFile   DecryptFileW
 #define WszOpenRaw   OpenRawW
 #define WszQueryRecoveryAgents   QueryRecoveryAgentsW
 #define Wszlstrcmp   lstrcmpW
 #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
 #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
 #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
 #define WszRegQueryValueExTrue RegQueryValueExW
 #define WszRegQueryStringValueEx RegQueryValueExW
 
-
 #ifndef FEATURE_CORECLR
 #define WszRegDeleteKey RegDeleteKeyW
 #define WszRegCreateKeyEx ClrRegCreateKeyEx
 #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;
index 742cf1c..0f0bf88 100644 (file)
@@ -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;
     }
index 691cd79..2e01258 100644 (file)
@@ -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, 
index eda2bca..58cdbf1 100644 (file)
@@ -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, 
index cb39a88..b5f6274 100644 (file)
@@ -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;
index e380e2e..d05e272 100644 (file)
@@ -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;
     }
index 1b81ff6..1ed7f0e 100644 (file)
@@ -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);
 }
 
 //
index 1d136b6..93d5266 100644 (file)
@@ -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
index 117d479..9aeb243 100644 (file)
@@ -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.
index 3f14772..d43c2a0 100644 (file)
                        RelativePath=".\winfix.cpp"
                        >
                </File>
+               <File
+                       RelativePath=".\longfilepathwrappers.cpp"
+                       >
+               </File>
        </Files>
        <Globals>
        </Globals>
index d0926fd..b0cca8d 100644 (file)
     <ClCompile Include="utilmessagebox.cpp" />
     <ClCompile Include="UTSEM.cpp" />
     <ClCompile Include="winfix.cpp" />
+    <ClCompile Include="longfilepathwrappers.cpp" />
   </ItemGroup>
   <ItemGroup>
     <ClInclude Include="hostimpl.h" />
   <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
   <ImportGroup Label="ExtensionTargets">
   </ImportGroup>
-</Project>
\ No newline at end of file
+</Project>
index eccf42d..a4c79fc 100644 (file)
@@ -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
 
 
index b1fb165..a96aca1 100644 (file)
@@ -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()));
 }
 
 //*****************************************************************************
index a1b29d5..808a10c 100644 (file)
@@ -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/coreclr/src/utilcode/longfilepathwrappers.cpp b/src/coreclr/src/utilcode/longfilepathwrappers.cpp
new file mode 100644 (file)
index 0000000..0bb4730
--- /dev/null
@@ -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;
+}
+
+
+
index ab078a9..3d948d5 100644 (file)
@@ -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;
+}
index c84c1df..5e031fe 100644 (file)
@@ -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))
index 0536cfa..1cb8990 100644 (file)
@@ -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
index 0ea7b90..6c17478 100644 (file)
@@ -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.
index 0b6f3ea..7bfdb45 100644 (file)
@@ -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 *
index 6c5378e..dcc6b83 100644 (file)
@@ -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
 
index 0628637..32d1c35 100644 (file)
@@ -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) ||
index fcb41dc..690000d 100644 (file)
@@ -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" />
index e84ff8b..4559d16 100644 (file)
@@ -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);
index 9ab8c7d..a841423 100644 (file)
@@ -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;
 }
 
index 5720c20..c89e927 100644 (file)
@@ -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);
index d639105..e2419ac 100644 (file)
@@ -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.
                 }
             }
index 9374a2c..4f99539 100644 (file)
@@ -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);
index 2a7cf45..f0e9029 100644 (file)
@@ -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;
index 48746d4..a3aef9b 100644 (file)
@@ -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,
index 15a58c0..77669b2 100644 (file)
@@ -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)
index a2750ce..4430668 100644 (file)
@@ -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);
 
index e322a63..973a4f4 100644 (file)
@@ -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.
     // ----------------------------------------------------
index c67d06d..8c3f2ec 100644 (file)
@@ -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"))) 
                 {
index e07a640..567f4f5 100644 (file)
@@ -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
index e6a25cc..5e35f9a 100644 (file)
@@ -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);
index de81a82..cc598c0 100644 (file)
@@ -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
index 27904ff..cb1dd50 100644 (file)
@@ -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
 
index 343b2bb..c2f6957 100644 (file)
@@ -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
 
index 3868386..8fdf554 100644 (file)
@@ -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");
index 082be54..fe1da90 100644 (file)
@@ -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)
index cf2b10f..ba77bcb 100644 (file)
@@ -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;
index 4258987..6d559d3 100644 (file)
@@ -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)
             {