diff options
Diffstat (limited to 'private/sdktools/instaler/ini.c')
-rw-r--r-- | private/sdktools/instaler/ini.c | 382 |
1 files changed, 382 insertions, 0 deletions
diff --git a/private/sdktools/instaler/ini.c b/private/sdktools/instaler/ini.c new file mode 100644 index 000000000..f50a177c7 --- /dev/null +++ b/private/sdktools/instaler/ini.c @@ -0,0 +1,382 @@ +/*++ + +Copyright (c) 1992 Microsoft Corporation + +Module Name: + + ini.c + +Abstract: + + This module implements the functions to save references to .INI file + sections and values for the INSTALER program. Part of each reference is + a a backup copy of sections and values for an .INI file. + +Author: + + Steve Wood (stevewo) 22-Aug-1994 + +Revision History: + +--*/ + +#include "instaler.h" + + +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; +} + + +BOOLEAN +DestroyIniFileReference( + PINI_FILE_REFERENCE p + ) +{ + PLIST_ENTRY Next, Head; + PINI_SECTION_REFERENCE p1; + + Head = &p->SectionReferencesListHead; + Next = Head->Flink; + while (Head != Next) { + p1 = CONTAINING_RECORD( Next, INI_SECTION_REFERENCE, Entry ); + Next = Next->Flink; + DestroyIniSectionReference( p1 ); + } + + RemoveEntryList( &p->Entry ); + FreeMem( &p ); + return TRUE; +} + + +BOOLEAN +DestroyIniSectionReference( + PINI_SECTION_REFERENCE p1 + ) +{ + PLIST_ENTRY Next, Head; + PINI_VARIABLE_REFERENCE p2; + + Head = &p1->VariableReferencesListHead; + Next = Head->Flink; + while (Head != Next) { + p2 = CONTAINING_RECORD( Next, INI_VARIABLE_REFERENCE, Entry ); + Next = Next->Flink; + DestroyIniVariableReference( p2 ); + } + + RemoveEntryList( &p1->Entry ); + FreeMem( &p1 ); + return TRUE; +} + + +BOOLEAN +DestroyIniVariableReference( + PINI_VARIABLE_REFERENCE p2 + ) +{ + RemoveEntryList( &p2->Entry ); + FreeMem( &p2 ); + return TRUE; +} + + +PINI_FILE_REFERENCE +FindIniFileReference( + PWSTR Name + ) +{ + PINI_FILE_REFERENCE p; + PLIST_ENTRY Next, Head; + + Head = &IniReferenceListHead; + Next = Head->Flink; + while (Head != Next) { + p = CONTAINING_RECORD( Next, INI_FILE_REFERENCE, Entry ); + if (p->Name == Name) { + return p; + } + + Next = Next->Flink; + } + + return NULL; +} + +PINI_SECTION_REFERENCE +FindIniSectionReference( + PINI_FILE_REFERENCE p, + PWSTR Name, + BOOLEAN CreateOkay + ) +{ + PLIST_ENTRY Next, Head; + PINI_SECTION_REFERENCE p1; + + Head = &p->SectionReferencesListHead; + Next = Head->Flink; + while (Head != Next) { + p1 = CONTAINING_RECORD( Next, INI_SECTION_REFERENCE, Entry ); + if (p1->Name == Name) { + return p1; + } + + Next = Next->Flink; + } + + if (CreateOkay) { + p1 = AllocMem( sizeof( *p1 ) ); + if (p1 != NULL) { + p1->Created = TRUE; + p1->Name = Name; + InitializeListHead( &p1->VariableReferencesListHead ); + InsertTailList( &p->SectionReferencesListHead, &p1->Entry ); + } + } + else { + p1 = NULL; + } + + return p1; +} + + +PINI_VARIABLE_REFERENCE +FindIniVariableReference( + PINI_SECTION_REFERENCE p1, + PWSTR Name, + BOOLEAN CreateOkay + ) +{ + PLIST_ENTRY Next, Head; + PINI_VARIABLE_REFERENCE p2; + + Head = &p1->VariableReferencesListHead; + Next = Head->Flink; + while (Head != Next) { + p2 = CONTAINING_RECORD( Next, INI_VARIABLE_REFERENCE, Entry ); + if (p2->Name == Name) { + return p2; + } + + Next = Next->Flink; + } + + if (CreateOkay) { + p2 = AllocMem( sizeof( *p2 ) ); + if (p2 != NULL) { + p2->Created = TRUE; + p2->Name = Name; + InsertTailList( &p1->VariableReferencesListHead, &p2->Entry ); + } + } + else { + p2 = NULL; + } + + return p2; +} + + +VOID +DumpIniFileReferenceList( + FILE *LogFile + ) +{ + PINI_FILE_REFERENCE p; + PINI_SECTION_REFERENCE p1; + PINI_VARIABLE_REFERENCE p2; + PLIST_ENTRY Head, Next; + PLIST_ENTRY Head1, Next1; + PLIST_ENTRY Head2, Next2; + POFFSET Variables; + POFFSET Sections; + + + Head = &IniReferenceListHead; + Next = Head->Blink; + while (Head != Next) { + p = CONTAINING_RECORD( Next, INI_FILE_REFERENCE, Entry ); + Sections = 0; + Head1 = &p->SectionReferencesListHead; + Next1 = Head1->Blink; + while (Head1 != Next1) { + p1 = CONTAINING_RECORD( Next1, INI_SECTION_REFERENCE, Entry ); + Variables = 0; + Head2 = &p1->VariableReferencesListHead; + Next2 = Head2->Blink; + while (Head2 != Next2) { + p2 = CONTAINING_RECORD( Next2, INI_VARIABLE_REFERENCE, Entry ); + if (p2->Created || p2->Deleted || p2->Modified) { + ImlAddIniVariableRecord( pImlNew, + p2->Created ? CreateNewVariable : + p2->Deleted ? DeleteOldVariable : ModifyOldVariable, + p2->Name, + p2->OriginalValue, + p2->Value, + &Variables + ); + } + Next2 = Next2->Blink; + } + + if (Variables != 0) { + ImlAddIniSectionRecord( pImlNew, + p1->Created ? CreateNewSection : + p1->Deleted ? DeleteOldSection : ModifySectionVariables, + p1->Name, + Variables, + &Sections + ); + } + + Next1 = Next1->Blink; + } + + if (Sections != 0) { + ImlAddIniRecord( pImlNew, + p->Created ? CreateNewIniFile : ModifyOldIniFile, + p->Name, + &p->BackupLastWriteTime, + Sections + ); + } + + Next = Next->Blink; + } + + return; +} |