HRESULT FusionBind::AddEnvironmentProperty(LPWSTR variable, LPWSTR pProperty, IApplicationContext* pFusionContext) { _ASSERTE(pProperty); _ASSERTE(variable); DWORD size = _MAX_PATH; WCHAR rcValue[_MAX_PATH]; // Buffer for the directory. WCHAR *pValue = &(rcValue[0]); size = WszGetEnvironmentVariable(variable, pValue, size); if(size > _MAX_PATH) { pValue = (WCHAR*) _alloca(size * sizeof(WCHAR)); size = WszGetEnvironmentVariable(variable, pValue, size); size++; // Add in the null terminator } if(size) { pFusionContext->Set(pProperty, pValue, size * sizeof(WCHAR), 0); return S_OK; } else return S_FALSE; // no variable found }
FCIMPLEND // Note: Arguments checked in IL. FCIMPL1(Object*, SystemNative::_GetEnvironmentVariable, StringObject* strVarUNSAFE) { FCALL_CONTRACT; STRINGREF refRetVal; STRINGREF strVar; refRetVal = NULL; strVar = ObjectToSTRINGREF(strVarUNSAFE); 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; // 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); while (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; } HELPER_METHOD_FRAME_END(); return OBJECTREFToObject(refRetVal); }
FCIMPLEND // Note: Arguments checked in IL. FCIMPL1(Object*, SystemNative::_GetEnvironmentVariable, StringObject* strVarUNSAFE) { FCALL_CONTRACT; STRINGREF refRetVal; STRINGREF strVar; refRetVal = NULL; strVar = ObjectToSTRINGREF(strVarUNSAFE); HELPER_METHOD_FRAME_BEGIN_RET_2(refRetVal, strVar); int len; // Get the length of the environment variable. PathString envPath; // prefix complains if pass a null ptr in, so rely on the final length parm instead len = WszGetEnvironmentVariable(strVar->GetBuffer(), envPath); if (len != 0) { // Allocate the string. refRetVal = StringObject::NewString(len); wcscpy_s(refRetVal->GetBuffer(), len + 1, envPath); } HELPER_METHOD_FRAME_END(); return OBJECTREFToObject(refRetVal); }
// public interface routine void InitWSPerf() { wchar_t lpszValue[2]; DWORD cchValue = 2; #ifdef _WS_PERF_OUTPUT g_fWSPerfOn = WszGetEnvironmentVariable (L"WS_PERF_OUTPUT", lpszValue, cchValue); if (g_fWSPerfOn) { g_hWSPerfLogFile = WszCreateFile (L"WSPerf.log", GENERIC_WRITE, 0, 0, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); if (g_hWSPerfLogFile == INVALID_HANDLE_VALUE) g_fWSPerfOn = 0; #ifdef WS_PERF_DETAIL g_hWSPerfDetailLogFile = WszCreateFile (L"WSPerfDetail.log", GENERIC_WRITE, 0, 0, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); if (g_hWSPerfDetailLogFile == INVALID_HANDLE_VALUE) g_fWSPerfOn = 0; #endif g_HeapAccounts[0][1] = -1; //null list sprintf(szPrintStr, "HPtr\t\tPage Range\t\tReserved Size\n"); WriteFile (g_hWSPerfLogFile, szPrintStr, strlen(szPrintStr), &dwWriteByte, NULL); } #endif }
//***************************************************************************** // This is a routine to try to find a class implementation given its fully // qualified name by using the CORPATH environment variable. CORPATH is a list // of directories (like PATH). Before checking CORPATH, this checks the current // directory, then the directory that the exe lives in. The search is // performed by parsing off one element at a time from the class name, // appending it to the directory and looking for a subdirectory or image with // that name. If the subdirectory exists, it drills down into that subdirectory // and tries the next element of the class name. When it finally bottoms out // but can't find the image it takes the rest of the fully qualified class name // and appends them with intervening '.'s trying to find a matching DLL. // Example: // // CORPATH=c:\bin;c:\prog // classname = namespace.class // // checks the following things in order: // c:\bin\namespace, (if <-exists) c:\bin\namespace\class.dll, // c:\bin\namespace.dll, c:\bin\namespace.class.dll // c:\prog\namespace, (if <-exists) c:\prog\namespace\class.dll, // c:\prog\namespace.dll, c:\prog\namespace.class.dll //***************************************************************************** HRESULT CORPATHService::GetClassFromCORPath( __in __in_z LPWSTR wzClassname, // [IN] fully qualified class name mdTypeRef tr, // [IN] TypeRef to be resolved. IMetaModelCommon *pCommon, // [IN] Scope in which the TypeRef is defined. REFIID riid, // [IN] Interface type to be returned. 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. int iLen; // Length of the directory. WCHAR rcCorDir[_MAX_PATH]; // 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))) { // Force nul termination. rcCorPath[lengthof(rcCorPath)-1] = 0; // Try each directory in the path. for(;*szCorPath != W('\0');) { // Get the next directory off the path. if ((szSemiCol = wcschr(szCorPath, W(';')))) { temp = szCorPath; *szSemiCol = W('\0'); szCorPath = szSemiCol + 1; } else { temp = szCorPath; szCorPath += wcslen(temp); } if ((iLen = (int)wcslen(temp)) >= _MAX_PATH) continue; wcscpy_s(rcCorDir, COUNTOF(rcCorDir), temp); // Check if we can find the class in the directory. if (CORPATHService::GetClassFromDir(wzClassname, rcCorDir, iLen, tr, pCommon, riid, ppIScope, ptd) == S_OK) return S_OK; } } //<TODO>These should go before the path search, but it will cause test // 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) { return S_OK; } // Try the app directory next. if ((iLen = WszGetModuleFileName(NULL, rcCorDir, _MAX_PATH)) > 0) { // Back up to the last path separator. while (--iLen >= 0 && rcCorDir[iLen] != W('\\') && rcCorDir[iLen] != W('/')) { } if (iLen > 0 && CORPATHService::GetClassFromDir( wzClassname, rcCorDir, iLen, tr, pCommon, riid, ppIScope, ptd) == S_OK) { return (S_OK); } } // Couldn't find the class. return S_FALSE; } // CORPATHService::GetClassFromCORPath
LPSTR FillSymbolSearchPathThrows(CQuickBytes &qb) { STATIC_CONTRACT_GC_NOTRIGGER; STATIC_CONTRACT_CANNOT_TAKE_LOCK; SCAN_IGNORE_FAULT; // Faults from Wsz funcs are handled. #ifndef DACCESS_COMPILE // not allowed to do allocation if current thread suspends EE. if (IsSuspendEEThread ()) return NULL; #endif 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 the NT symbol server path vars are there, then use those. chTotal = WszGetEnvironmentVariable(W("_NT_SYMBOL_PATH"), rcBuff); if (chTotal + 1 < MAX_SYM_PATH) rcBuff.Append(W(';')); // Copy the defacto NT symbol path as well. size_t sympathLength = chTotal + NumItems(DEFAULT_SYM_PATH) + 1; // integer overflow occurred if (sympathLength < (size_t)chTotal || sympathLength < NumItems(DEFAULT_SYM_PATH)) { return NULL; } if (sympathLength < MAX_SYM_PATH) { 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. PathString rcBuffTemp; ch = WszGetEnvironmentVariable(W("URTTARGET"), rcBuffTemp); rcBuff.Append(rcBuffTemp); if (ch != 0 && (chTotal + ch + 1 < MAX_SYM_PATH)) { size_t chNewTotal = chTotal + ch; if (chNewTotal < (size_t)chTotal || chNewTotal < (size_t)ch) { // integer overflow occurred return NULL; } chTotal += ch; rcBuff.Append(W(';')); } #ifndef SELF_NO_HOST // Fetch the path location of the engine dll and add that path as well, just // 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(), rcBuffTemp); size_t pathLocationLength = chTotal + ch + 1; // integer overflow occurred if (pathLocationLength < (size_t)chTotal || pathLocationLength < (size_t)ch) { return NULL; } if (ch != 0 && (pathLocationLength < MAX_SYM_PATH)) { chTotal = chTotal + ch - NumItems(STR_ENGINE_NAME); rcBuff.Append(W(';')); } #endif // 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. ch = ::WszWideCharToMultiByte(CP_ACP, WC_NO_BEST_FIT_CHARS, rcBuff, -1, 0, 0, 0, 0); LPSTR szRtn = (LPSTR) qb.AllocNoThrow(ch + 1); if (!szRtn) return NULL; WszWideCharToMultiByte(CP_ACP, WC_NO_BEST_FIT_CHARS, rcBuff, -1, szRtn, ch+1, 0, 0); return (szRtn); }
//----------------------------------------------------------------------------- // Initliaze perf logging. Must be called before calling PERFLOG (x)... void PerfLog::PerfLogInitialize() { LIMITED_METHOD_CONTRACT; // Make sure we are called only once. if (m_perfLogInit) { return; } // First check for special cases: #if defined(ENABLE_JIT_PERF) // Checks the JIT_PERF_OUTPUT env var and sets g_fJitPerfOn. InitJitPerf(); #endif #ifdef WS_PERF // Private working set perf stats InitWSPerf(); #endif // WS_PERF // Put other special cases here. // <TODO>@TODO agk: clean this logic a bit</TODO> // Special cases considered. Now turn on loggin if any of above want logging // or if PERF_OUTPUT says so. InlineSString<4> lpszValue; // Read the env var PERF_OUTPUT and if set continue. m_fLogPerfData = WszGetEnvironmentVariable (W("PERF_OUTPUT"), lpszValue); #if defined(ENABLE_JIT_PERF) if (!m_fLogPerfData) { // Make sure that JIT perf was not requested. if (!g_fJitPerfOn) return; // JIT perf stats are needed so set the flags also. m_fLogPerfData = 1; } #endif // See if we want to output to the database PathString _lpszValue; DWORD _cchValue = 10; // 11 - 1 _cchValue = WszGetEnvironmentVariable (W("PerfOutput"), _lpszValue); if (_cchValue && (wcscmp (_lpszValue, W("DBase")) == 0)) m_perfAutomationFormat = true; if (_cchValue && (wcscmp (_lpszValue, W("CSV")) == 0)) m_commaSeparatedFormat = true; if (PerfAutomationFormat() || CommaSeparatedFormat()) { // Hardcoded file name for spitting the perf auotmation formatted perf data. Open // the file here for writing and close in PerfLogDone(). m_hPerfLogFileHandle = WszCreateFile ( #ifdef PLATFORM_UNIX W("/tmp/PerfData.dat"), #else W("C:\\PerfData.dat"), #endif GENERIC_WRITE, FILE_SHARE_WRITE, 0, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); // check return value if(m_hPerfLogFileHandle == INVALID_HANDLE_VALUE) { m_fLogPerfData = 0; goto ErrExit; } // Make sure we append to the file. <TODO>@TODO agk: Is this necessary?</TODO> if(SetFilePointer (m_hPerfLogFileHandle, 0, NULL, FILE_END) == INVALID_SET_FILE_POINTER ) { CloseHandle (m_hPerfLogFileHandle); m_fLogPerfData = 0; goto ErrExit; } } m_perfLogInit = true; ErrExit: return; }
//***************************************************************************** // This is a routine to try to find a class implementation given its fully // qualified name by using the CORPATH environment variable. CORPATH is a list // of directories (like PATH). Before checking CORPATH, this checks the current // directory, then the directory that the exe lives in. The search is // performed by parsing off one element at a time from the class name, // appending it to the directory and looking for a subdirectory or image with // that name. If the subdirectory exists, it drills down into that subdirectory // and tries the next element of the class name. When it finally bottoms out // but can't find the image it takes the rest of the fully qualified class name // and appends them with intervening '.'s trying to find a matching DLL. // Example: // // CORPATH=c:\bin;c:\prog // classname = namespace.class // // checks the following things in order: // c:\bin\namespace, (if <-exists) c:\bin\namespace\class.dll, // c:\bin\namespace.dll, c:\bin\namespace.class.dll // c:\prog\namespace, (if <-exists) c:\prog\namespace\class.dll, // c:\prog\namespace.dll, c:\prog\namespace.class.dll //***************************************************************************** HRESULT CORPATHService::GetClassFromCORPath( __in __in_z LPWSTR wzClassname, // [IN] fully qualified class name mdTypeRef tr, // [IN] TypeRef to be resolved. IMetaModelCommon *pCommon, // [IN] Scope in which the TypeRef is defined. REFIID riid, // [IN] Interface type to be returned. IUnknown **ppIScope, // [OUT] Scope in which the TypeRef resolves. mdTypeDef *ptd) // [OUT] typedef corresponding the typeref { PathString rcCorPath; // The CORPATH environment variable. LPWSTR szCorPath; // Used to parse CORPATH. int iLen; // Length of 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)) { NewArrayHolder<WCHAR> szCorPathHolder = rcCorPath.GetCopyOfUnicodeString(); szCorPath = szCorPathHolder.GetValue(); // Try each directory in the path. for(;*szCorPath != W('\0');) { // Get the next directory off the path. if ((szSemiCol = wcschr(szCorPath, W(';')))) { temp = szCorPath; *szSemiCol = W('\0'); szCorPath = szSemiCol + 1; } else { temp = szCorPath; szCorPath += wcslen(temp); } rcCorDir.Set(temp); // Check if we can find the class in the directory. if (CORPATHService::GetClassFromDir(wzClassname, rcCorDir, tr, pCommon, riid, ppIScope, ptd) == S_OK) return S_OK; } } //<TODO>These should go before the path search, but it will cause test // some headaches right now, so we'll give them a little time to transition.</TODO> // Try the current directory first. 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)) > 0) { if(SUCCEEDED(CopySystemDirectory(rcCorDir, rcCorDir)) && CORPATHService::GetClassFromDir( wzClassname, rcCorDir, tr, pCommon, riid, ppIScope, ptd) == S_OK) { return (S_OK); } } // Couldn't find the class. return S_FALSE; } // CORPATHService::GetClassFromCORPath