/*********************************************************************** * MSACM_RegisterAllDrivers() */ void MSACM_RegisterAllDrivers(void) { static const WCHAR msacm32[] = {'m','s','a','c','m','3','2','.','d','l','l','\0'}; static const WCHAR msacmW[] = {'M','S','A','C','M','.'}; static const WCHAR drv32[] = {'d','r','i','v','e','r','s','3','2','\0'}; static const WCHAR sys[] = {'s','y','s','t','e','m','.','i','n','i','\0'}; static const WCHAR drvkey[] = {'S','o','f','t','w','a','r','e','\\', 'M','i','c','r','o','s','o','f','t','\\', 'W','i','n','d','o','w','s',' ','N','T','\\', 'C','u','r','r','e','n','t','V','e','r','s','i','o','n','\\', 'D','r','i','v','e','r','s','3','2','\0'}; DWORD i, cnt, bufLen, lRet, type; WCHAR buf[2048], valname[64], *name, *s; FILETIME lastWrite; HKEY hKey; /* FIXME: What if the user edits system.ini while the program is running? * Does Windows handle that? */ if (MSACM_pFirstACMDriverID) return; lRet = RegOpenKeyExW(HKEY_LOCAL_MACHINE, drvkey, 0, KEY_QUERY_VALUE, &hKey); if (lRet == ERROR_SUCCESS) { RegQueryInfoKeyW( hKey, 0, 0, 0, &cnt, 0, 0, 0, 0, 0, 0, 0); for (i = 0; i < cnt; i++) { bufLen = sizeof(buf) / sizeof(buf[0]); lRet = RegEnumKeyExW(hKey, i, buf, &bufLen, 0, 0, 0, &lastWrite); if (lRet != ERROR_SUCCESS) continue; if (strncmpiW(buf, msacmW, sizeof(msacmW)/sizeof(msacmW[0]))) continue; if (!(name = strchrW(buf, '='))) continue; *name = 0; MSACM_RegisterDriver(buf, name + 1, 0); } i = 0; cnt = sizeof(valname) / sizeof(*valname); bufLen = sizeof(buf); while(RegEnumValueW(hKey, i, valname, &cnt, 0, &type, (BYTE*)buf, &bufLen) == ERROR_SUCCESS){ if(!strncmpiW(valname, msacmW, sizeof(msacmW) / sizeof(*msacmW))) MSACM_RegisterDriver(valname, buf, 0); ++i; } RegCloseKey( hKey ); } if (GetPrivateProfileSectionW(drv32, buf, sizeof(buf)/sizeof(buf[0]), sys)) { for(s = buf; *s; s += strlenW(s) + 1) { if (strncmpiW(s, msacmW, sizeof(msacmW)/sizeof(msacmW[0]))) continue; if (!(name = strchrW(s, '='))) continue; *name = 0; MSACM_RegisterDriver(s, name + 1, 0); *name = '='; } } MSACM_ReorderDriversByPriority(); MSACM_RegisterDriver(msacm32, msacm32, 0); }
/* Performs the rename operations dictated in %SystemRoot%\Wininit.ini. * Returns FALSE if there was an error, or otherwise if all is ok. */ static BOOL wininit(void) { static const WCHAR nulW[] = {'N','U','L',0}; static const WCHAR renameW[] = {'r','e','n','a','m','e',0}; static const WCHAR wininitW[] = {'w','i','n','i','n','i','t','.','i','n','i',0}; static const WCHAR wininitbakW[] = {'w','i','n','i','n','i','t','.','b','a','k',0}; WCHAR initial_buffer[1024]; WCHAR *str, *buffer = initial_buffer; DWORD size = sizeof(initial_buffer)/sizeof(WCHAR); DWORD res; for (;;) { if (!(res = GetPrivateProfileSectionW( renameW, buffer, size, wininitW ))) return TRUE; if (res < size - 2) break; if (buffer != initial_buffer) HeapFree( GetProcessHeap(), 0, buffer ); size *= 2; if (!(buffer = HeapAlloc( GetProcessHeap(), 0, size * sizeof(WCHAR) ))) return FALSE; } for (str = buffer; *str; str += strlenW(str) + 1) { WCHAR *value; if (*str == ';') continue; /* comment */ if (!(value = strchrW( str, '=' ))) continue; /* split the line into key and value */ *value++ = 0; if (!lstrcmpiW( nulW, str )) { WINE_TRACE("Deleting file %s\n", wine_dbgstr_w(value) ); if( !DeleteFileW( value ) ) WINE_WARN("Error deleting file %s\n", wine_dbgstr_w(value) ); } else { WINE_TRACE("Renaming file %s to %s\n", wine_dbgstr_w(value), wine_dbgstr_w(str) ); if( !MoveFileExW(value, str, MOVEFILE_COPY_ALLOWED | MOVEFILE_REPLACE_EXISTING) ) WINE_WARN("Error renaming %s to %s\n", wine_dbgstr_w(value), wine_dbgstr_w(str) ); } str = value; } if (buffer != initial_buffer) HeapFree( GetProcessHeap(), 0, buffer ); if( !MoveFileExW( wininitW, wininitbakW, MOVEFILE_REPLACE_EXISTING) ) { WINE_ERR("Couldn't rename wininit.ini, error %d\n", GetLastError() ); return FALSE; } return TRUE; }
DWORD CIniFile::GetSection(const wchar_t *const pwchSection, wchar_t *const pwchKeyWordsAndValues, const DWORD dwKeyWordsAndValuesSize) { assert(NULL != pwchSection); assert(NULL != pwchKeyWordsAndValues); assert(dwKeyWordsAndValuesSize > 0); return GetPrivateProfileSectionW(pwchSection, pwchKeyWordsAndValues, dwKeyWordsAndValuesSize, m_wchPath); }
static void loadExeName(std::set<std::wstring, std::less<>>& set, LPCWSTR section, LPCWSTR path) { #define BUFFER_SIZE 4096 wchar_t* buffer = new wchar_t[BUFFER_SIZE]; size_t load = GetPrivateProfileSectionW(section, buffer, BUFFER_SIZE, path); wchar_t* p = buffer; while (load > 0) { size_t len = wcsnlen(p, load); if (len >= load) { break; } set.insert(CharLowerW(p)); p += len + 1; load -= len + 1; } delete[] buffer; #undef BUFFER_SIZE }
BOOL foreach_section(LPCWSTR cat, /* ini 区段 */ WCHAR (*lpdata)[VALUE_LEN+1], /* 二维数组首地址,保存多个段值 */ int line /* 二维数组行数 */ ) { DWORD res = 0; LPWSTR lpstring; LPWSTR strKey; int i = 0; const WCHAR delim[] = L"="; DWORD num = VALUE_LEN*sizeof(WCHAR)*line; if ( profile_path[1] != L':' ) { if (!ini_ready(profile_path,MAX_PATH)) { return res; } } if ( (lpstring = (LPWSTR)SYS_MALLOC(num)) != NULL ) { if ( (res = GetPrivateProfileSectionW(cat, lpstring, num, profile_path)) > 0 ) { fzero(*lpdata,num); strKey = lpstring; while(*strKey != L'\0'&& i < line) { LPWSTR strtmp; WCHAR t_str[VALUE_LEN] = {0}; wcsncpy(t_str,strKey,VALUE_LEN-1); strtmp = StrStrW(t_str, delim); if (strtmp) { wcsncpy(lpdata[i],&strtmp[1],VALUE_LEN-1); } strKey += wcslen(strKey)+1; ++i; } } SYS_FREE(lpstring); } return (BOOL)res; }
static void loadFontSubstitutes(LPCWSTR path) { #define BUFFER_SIZE 4096 wchar_t* buffer = new wchar_t[BUFFER_SIZE]; size_t load = GetPrivateProfileSectionW(L"FontSubstitutes", buffer, BUFFER_SIZE, path); wchar_t* p = buffer; while (load > 0) { size_t len = wcsnlen(p, load); if (len >= load) { break; } wchar_t* p2 = wcschr(p, L'='); if (p2) { *p2++ = L'\0'; FontSubstitutesMap[p] = p2; } p += len + 1; load -= len + 1; } delete[] buffer; #undef BUFFER_SIZE }
/* 必须使用进程依赖crt的wputenv函数追加环境变量 */ unsigned WINAPI SetPluginPath(void * pParam) { typedef int (__cdecl *_pwrite_env)(LPCWSTR envstring); int ret = 0; HMODULE hCrt =NULL; _pwrite_env write_env = NULL; char msvc_crt[CRT_LEN+1] = {0}; LPWSTR lpstring; if ( !find_msvcrt(msvc_crt,CRT_LEN) ) { return (0); } if ( (hCrt = GetModuleHandleA(msvc_crt)) == NULL ) { return (0); } if ( profile_path[1] != L':' ) { if (!ini_ready(profile_path,MAX_PATH)) { return (0); } } write_env = (_pwrite_env)GetProcAddress(hCrt,"_wputenv"); if ( write_env == NULL ) { return (0); } if ( (lpstring = (LPWSTR)SYS_MALLOC(MAX_ENV_SIZE)) == NULL ) { return (0); } if ( (ret = GetPrivateProfileSectionW(L"Env", lpstring, MAX_ENV_SIZE-1, profile_path)) > 0 ) { LPWSTR strKey = lpstring; while(*strKey != L'\0') { if ( stristrW(strKey, L"NpluginPath") ) { WCHAR lpfile[VALUE_LEN+1]; if ( read_appkey(L"Env",L"NpluginPath",lpfile,sizeof(lpfile)) ) { WCHAR env_string[VALUE_LEN+1] = {0}; PathToCombineW(lpfile, VALUE_LEN); if ( _snwprintf(env_string,VALUE_LEN,L"%ls%ls",L"MOZ_PLUGIN_PATH=",lpfile) > 0) { ret = write_env( (LPCWSTR)env_string ); } } } else if ( stristrW(strKey, L"VimpPentaHome") ) { WCHAR lpfile[VALUE_LEN+1]; if ( read_appkey(L"Env",L"VimpPentaHome",lpfile,sizeof(lpfile)) ) { WCHAR env_string[VALUE_LEN+1] = {0}; if (lpfile[1] != L':') { WCHAR vimp_path[VALUE_LEN+1] = {0}; charTochar(lpfile); if ( PathCombineW(vimp_path,portable_data_path,lpfile) ) { int n = _snwprintf(lpfile,VALUE_LEN,L"%ls",vimp_path); lpfile[n] = L'\0'; } } if ( _snwprintf(env_string,VALUE_LEN,L"%ls%ls",L"HOME=",lpfile) > 0) { ret = write_env( (LPCWSTR)env_string ); } } } else if (stristrW(strKey, L"MOZ_GMP_PATH")) { WCHAR lpfile[VALUE_LEN+1]; if ( read_appkey(L"Env",L"MOZ_GMP_PATH",lpfile,sizeof(lpfile)) ) { WCHAR env_string[VALUE_LEN+1] = {0}; PathToCombineW(lpfile, VALUE_LEN); if ( _snwprintf(env_string,VALUE_LEN,L"%ls%ls",L"MOZ_GMP_PATH=",lpfile) > 0) { ret = write_env( (LPCWSTR)env_string ); } } } else if (stristrW(strKey, L"TmpDataPath")) { /* the PATH environment variable does not exist */ } else { ret = write_env( (LPCWSTR)strKey ); } strKey += wcslen(strKey)+1; } } SYS_FREE(lpstring); return (1); }
static BOOL MAIN_LoadSettings(VOID) { LPWSTR lpszTmp; LPWSTR lpszSection; LONG lRet; WCHAR dummy[2]; LPWSTR lpszKeyValue; const LPCWSTR lpszIniFile = L"progman.ini"; WCHAR szWinDir[MAX_PATH]; LPWSTR lpszKey; DWORD Value; HKEY hKey; BOOL bIsIniMigrated; DWORD dwSize; LPWSTR lpszSections; LPWSTR lpszData; DWORD dwRet; DWORD dwType; LPWSTR lpszValue; bIsIniMigrated = FALSE; lpszSections = NULL; lpszData = NULL; /* Try to create/open the Program Manager user key */ if (RegCreateKeyExW(HKEY_CURRENT_USER, L"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Program Manager", 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &Globals.hKeyProgMan, NULL) != ERROR_SUCCESS) { return FALSE; } /* * TODO: Add the explanation for the migration... */ dwSize = sizeof(Value); lRet = RegQueryValueExW(Globals.hKeyProgMan, L"IniMigrated", NULL, &dwType, (LPBYTE)&Value, &dwSize); if (lRet != ERROR_SUCCESS || dwType != REG_DWORD) Value = 0; bIsIniMigrated = !!Value; if (bIsIniMigrated) { /* The migration was already done, just load the settings */ goto LoadSettings; } /* Perform the migration */ bIsIniMigrated = TRUE; dwSize = ARRAYSIZE(dummy); SetLastError(0); GetPrivateProfileSectionW(L"Settings", dummy, dwSize, lpszIniFile); if (GetLastError() == ERROR_FILE_NOT_FOUND) goto MigrationDone; SetLastError(0); GetPrivateProfileSectionW(L"Groups", dummy, dwSize, lpszIniFile); if (GetLastError() == ERROR_FILE_NOT_FOUND) goto MigrationDone; GetWindowsDirectoryW(szWinDir, ARRAYSIZE(szWinDir)); // NOTE: GCC complains we cannot use the "\u2022" (UNICODE Code Point) notation for specifying the bullet character, // because it's only available in C++ or in C99. On the contrary MSVC is fine with it. // Instead we use a hex specification for the character: "\x2022". // Note also that the character "\x07" gives also a bullet, but a larger one. PrintString( L"The Program Manager has detected the presence of a legacy settings file PROGMAN.INI in the directory '%s' " L"and is going to migrate its contents into the current-user Program Manager settings registry key:\n" L"HKCU\\SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Program Manager" L"\n\n" L"\x2022 The migration operation will potentially overwrite all the existing current-user Program Manager settings in the registry by those stored in the PROGMAN.INI file.\n" L"\n" L"\x2022 The migration is done once, so that, at the next launch of the Program Manager, the new migrated settings are directly used.\n" L"\n" L"\x2022 It is possible to trigger later the migration by manually deleting the registry value \"IniMigrated\" under the current-user Program Manager settings registry key (specified above).\n" L"\n" L"Would you like to migrate its contents into the registry?", szWinDir); for (dwSize = BUFFER_SIZE; ; dwSize += BUFFER_SIZE) { lpszSections = Alloc(0, dwSize * sizeof(WCHAR)); dwRet = GetPrivateProfileSectionNamesW(lpszSections, dwSize, lpszIniFile); if (dwRet < dwSize - 2) break; Free(lpszSections); } lpszSection = lpszSections; while (*lpszSection) { lRet = RegCreateKeyExW(Globals.hKeyProgMan, lpszSection, 0, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, &hKey, NULL); if (lRet == ERROR_SUCCESS) { for (dwSize = BUFFER_SIZE; ; dwSize += BUFFER_SIZE) { lpszData = Alloc(0, dwSize * sizeof(WCHAR)); dwRet = GetPrivateProfileSectionW(lpszSection, lpszData, dwSize, lpszIniFile); if (dwRet < dwSize - 2) break; Free(lpszData); } lpszKeyValue = lpszData; while (*lpszKeyValue) { lpszKey = lpszKeyValue; lpszValue = wcschr(lpszKeyValue, L'='); lpszKeyValue += (wcslen(lpszKeyValue) + 1); if (lpszValue) { *lpszValue = '\0'; ++lpszValue; Value = wcstoul(lpszValue, &lpszTmp, 0); if (lpszTmp - lpszValue >= wcslen(lpszValue)) { lpszValue = (LPWSTR)&Value; dwSize = sizeof(Value); dwType = REG_DWORD; } else { dwSize = wcslen(lpszValue) * sizeof(WCHAR); dwType = REG_SZ; } } else { dwSize = 0; dwType = REG_DWORD; } lRet = RegSetValueExW(hKey, lpszKey, 0, dwType, (LPBYTE)lpszValue, dwSize); } Free(lpszData); RegCloseKey(hKey); lpszSection += (wcslen(lpszSection) + 1); } } Free(lpszSections); MigrationDone: Value = TRUE; RegSetValueExW(Globals.hKeyProgMan, L"IniMigrated", 0, REG_DWORD, (LPBYTE)&Value, sizeof(Value)); LoadSettings: /* Create the necessary registry keys for the Program Manager and load its settings from the registry */ lRet = RegCreateKeyExW(Globals.hKeyProgMan, L"Settings", 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &Globals.hKeyPMSettings, NULL); lRet = RegCreateKeyExW(Globals.hKeyProgMan, L"Common Groups", 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &Globals.hKeyPMCommonGroups, NULL); lRet = RegCreateKeyExW(Globals.hKeyProgMan, L"Groups", 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &Globals.hKeyPMAnsiGroups, NULL); lRet = RegCreateKeyExW(Globals.hKeyProgMan, L"UNICODE Groups", 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &Globals.hKeyPMUnicodeGroups, NULL); lRet = RegCreateKeyExW(HKEY_CURRENT_USER, L"Program Groups", 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &Globals.hKeyAnsiGroups, NULL); lRet = RegCreateKeyExW(HKEY_CURRENT_USER, L"UNICODE Program Groups", 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &Globals.hKeyUnicodeGroups, NULL); lRet = RegCreateKeyExW(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Program Groups", 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &Globals.hKeyCommonGroups, NULL); dwSize = sizeof(Globals.bAutoArrange); RegQueryValueExW(Globals.hKeyPMSettings, L"AutoArrange", NULL, &dwType, (LPBYTE)&Globals.bAutoArrange, &dwSize); dwSize = sizeof(Globals.bMinOnRun); RegQueryValueExW(Globals.hKeyPMSettings, L"MinOnRun", NULL, &dwType, (LPBYTE)&Globals.bMinOnRun, &dwSize); dwSize = sizeof(Globals.bSaveSettings); RegQueryValueExW(Globals.hKeyPMSettings, L"SaveSettings", NULL, &dwType, (LPBYTE)&Globals.bSaveSettings, &dwSize); return TRUE; }
BOOLEAN CreateIniFileReference( PWSTR Name, PINI_FILE_REFERENCE *ReturnedReference ) { PINI_FILE_REFERENCE p; PINI_SECTION_REFERENCE p1; PINI_VARIABLE_REFERENCE p2; PWSTR SectionName; PWSTR VariableName; PWSTR VariableValue; UNICODE_STRING UnicodeString; PLIST_ENTRY Head, Next; ULONG n, n1; BOOLEAN Result; HANDLE FindHandle; WIN32_FIND_DATA FindFileData; p = FindIniFileReference( Name ); if (p != NULL) { *ReturnedReference = p; return TRUE; } p = AllocMem( sizeof( *p ) ); if (p == NULL) { return FALSE; } p->Name = Name; InitializeListHead( &p->SectionReferencesListHead ); InsertTailList( &IniReferenceListHead, &p->Entry ); FindHandle = FindFirstFile( Name, &FindFileData ); if (FindHandle == INVALID_HANDLE_VALUE) { p->Created = TRUE; *ReturnedReference = p; return TRUE; } FindClose( FindHandle ); p->BackupLastWriteTime = FindFileData.ftLastWriteTime; GrowTemporaryBuffer( n = 0xF000 ); SectionName = TemporaryBuffer; Result = TRUE; n1 = GetPrivateProfileStringW( NULL, NULL, L"", SectionName, n, Name ); if (n1 == 0 || n1 == n-2) { Result = FALSE; } else { while (*SectionName != UNICODE_NULL) { p1 = AllocMem( sizeof( *p1 ) ); if (p1 == NULL) { Result = FALSE; break; } RtlInitUnicodeString( &UnicodeString, SectionName ); p1->Name = AddName( &UnicodeString ); if (FindIniSectionReference( p, p1->Name, FALSE )) { FreeMem( &p1 ); } else { InitializeListHead( &p1->VariableReferencesListHead ); InsertTailList( &p->SectionReferencesListHead, &p1->Entry ); } while (*SectionName++ != UNICODE_NULL) { } } } VariableName = TemporaryBuffer; Head = &p->SectionReferencesListHead; Next = Head->Flink; while (Result && (Head != Next)) { p1 = CONTAINING_RECORD( Next, INI_SECTION_REFERENCE, Entry ); n1 = GetPrivateProfileSectionW( p1->Name, VariableName, n, Name ); if (n1 == n-2) { Result = FALSE; break; } while (*VariableName != UNICODE_NULL) { VariableValue = VariableName; while (*VariableValue != UNICODE_NULL && *VariableValue != L'=') { VariableValue += 1; } if (*VariableValue != L'=') { Result = FALSE; break; } *VariableValue++ = UNICODE_NULL; p2 = AllocMem( sizeof( *p2 ) + ((wcslen( VariableValue ) + 1) * sizeof( WCHAR )) ); if (p2 == NULL) { Result = FALSE; break; } RtlInitUnicodeString( &UnicodeString, VariableName ); p2->Name = AddName( &UnicodeString ); p2->OriginalValue = (PWSTR)(p2+1); wcscpy( p2->OriginalValue, VariableValue ); InsertTailList( &p1->VariableReferencesListHead, &p2->Entry ); VariableName = VariableValue; while (*VariableName++ != UNICODE_NULL) { } } Next = Next->Flink; } if (Result) { *ReturnedReference = p; } else { DestroyIniFileReference( p ); } return Result; }
/* 必须使用进程依赖crt的wputenv函数追加环境变量 */ unsigned WINAPI SetPluginPath(void * pParam) { typedef int (__cdecl *_pwrite_env)(LPCWSTR envstring); int ret = 0; HMODULE hCrt =NULL; _pwrite_env write_env = NULL; char msvc_crt[CRT_LEN+1] = {0}; LPWSTR lpstring; if ( !find_msvcrt(msvc_crt,CRT_LEN) ) { return ((unsigned)ret); } if ( (hCrt = GetModuleHandleA(msvc_crt)) == NULL ) { return ((unsigned)ret); } if ( profile_path[1] != L':' ) { if (!ini_ready(profile_path,MAX_PATH)) { return ((unsigned)ret); } } write_env = (_pwrite_env)GetProcAddress(hCrt,"_wputenv"); if ( write_env ) { if ( (lpstring = (LPWSTR)SYS_MALLOC(MAX_ENV_SIZE)) != NULL ) { if ( (ret = GetPrivateProfileSectionW(L"Env", lpstring, MAX_ENV_SIZE-1, profile_path)) > 0 ) { LPWSTR strKey = lpstring; while(*strKey != L'\0') { if ( stristrW(strKey, L"NpluginPath") ) { WCHAR lpfile[VALUE_LEN+1]; if ( read_appkey(L"Env",L"NpluginPath",lpfile,sizeof(lpfile)) ) { WCHAR env_string[VALUE_LEN+1] = {0}; PathToCombineW(lpfile, VALUE_LEN); if ( _snwprintf(env_string,VALUE_LEN,L"%ls%ls",L"MOZ_PLUGIN_PATH=",lpfile) > 0) { ret = write_env( (LPCWSTR)env_string ); } } } else if (stristrW(strKey, L"TmpDataPath")) { ; } else { ret = write_env( (LPCWSTR)strKey ); } strKey += wcslen(strKey)+1; } } SYS_FREE(lpstring); } } return ( (unsigned)ret ); }