ReactOS.org
Sign In
Sign Up
Sign In
Sign Up
Manage this list
×
Keyboard Shortcuts
Thread View
j
: Next unread message
k
: Previous unread message
j a
: Jump to all threads
j l
: Jump to MailingList overview
2024
December
November
October
September
August
July
June
May
April
March
February
January
2023
December
November
October
September
August
July
June
May
April
March
February
January
2022
December
November
October
September
August
July
June
May
April
March
February
January
2021
December
November
October
September
August
July
June
May
April
March
February
January
2020
December
November
October
September
August
July
June
May
April
March
February
January
2019
December
November
October
September
August
July
June
May
April
March
February
January
2018
December
November
October
September
August
July
June
May
April
March
February
January
2017
December
November
October
September
August
July
June
May
April
March
February
January
2016
December
November
October
September
August
July
June
May
April
March
February
January
2015
December
November
October
September
August
July
June
May
April
March
February
January
2014
December
November
October
September
August
July
June
May
April
March
February
January
2013
December
November
October
September
August
July
June
May
April
March
February
January
2012
December
November
October
September
August
July
June
May
April
March
February
January
2011
December
November
October
September
August
July
June
May
April
March
February
January
2010
December
November
October
September
August
July
June
May
April
March
February
January
2009
December
November
October
September
August
July
June
May
April
March
February
January
2008
December
November
October
September
August
July
June
May
April
March
February
January
2007
December
November
October
September
August
July
June
May
April
March
February
January
2006
December
November
October
September
August
July
June
May
April
March
February
January
2005
December
November
October
September
August
July
June
May
April
March
February
January
2004
December
November
October
September
August
July
June
May
April
March
February
List overview
Download
Ros-diffs
September 2014
----- 2024 -----
December 2024
November 2024
October 2024
September 2024
August 2024
July 2024
June 2024
May 2024
April 2024
March 2024
February 2024
January 2024
----- 2023 -----
December 2023
November 2023
October 2023
September 2023
August 2023
July 2023
June 2023
May 2023
April 2023
March 2023
February 2023
January 2023
----- 2022 -----
December 2022
November 2022
October 2022
September 2022
August 2022
July 2022
June 2022
May 2022
April 2022
March 2022
February 2022
January 2022
----- 2021 -----
December 2021
November 2021
October 2021
September 2021
August 2021
July 2021
June 2021
May 2021
April 2021
March 2021
February 2021
January 2021
----- 2020 -----
December 2020
November 2020
October 2020
September 2020
August 2020
July 2020
June 2020
May 2020
April 2020
March 2020
February 2020
January 2020
----- 2019 -----
December 2019
November 2019
October 2019
September 2019
August 2019
July 2019
June 2019
May 2019
April 2019
March 2019
February 2019
January 2019
----- 2018 -----
December 2018
November 2018
October 2018
September 2018
August 2018
July 2018
June 2018
May 2018
April 2018
March 2018
February 2018
January 2018
----- 2017 -----
December 2017
November 2017
October 2017
September 2017
August 2017
July 2017
June 2017
May 2017
April 2017
March 2017
February 2017
January 2017
----- 2016 -----
December 2016
November 2016
October 2016
September 2016
August 2016
July 2016
June 2016
May 2016
April 2016
March 2016
February 2016
January 2016
----- 2015 -----
December 2015
November 2015
October 2015
September 2015
August 2015
July 2015
June 2015
May 2015
April 2015
March 2015
February 2015
January 2015
----- 2014 -----
December 2014
November 2014
October 2014
September 2014
August 2014
July 2014
June 2014
May 2014
April 2014
March 2014
February 2014
January 2014
----- 2013 -----
December 2013
November 2013
October 2013
September 2013
August 2013
July 2013
June 2013
May 2013
April 2013
March 2013
February 2013
January 2013
----- 2012 -----
December 2012
November 2012
October 2012
September 2012
August 2012
July 2012
June 2012
May 2012
April 2012
March 2012
February 2012
January 2012
----- 2011 -----
December 2011
November 2011
October 2011
September 2011
August 2011
July 2011
June 2011
May 2011
April 2011
March 2011
February 2011
January 2011
----- 2010 -----
December 2010
November 2010
October 2010
September 2010
August 2010
July 2010
June 2010
May 2010
April 2010
March 2010
February 2010
January 2010
----- 2009 -----
December 2009
November 2009
October 2009
September 2009
August 2009
July 2009
June 2009
May 2009
April 2009
March 2009
February 2009
January 2009
----- 2008 -----
December 2008
November 2008
October 2008
September 2008
August 2008
July 2008
June 2008
May 2008
April 2008
March 2008
February 2008
January 2008
----- 2007 -----
December 2007
November 2007
October 2007
September 2007
August 2007
July 2007
June 2007
May 2007
April 2007
March 2007
February 2007
January 2007
----- 2006 -----
December 2006
November 2006
October 2006
September 2006
August 2006
July 2006
June 2006
May 2006
April 2006
March 2006
February 2006
January 2006
----- 2005 -----
December 2005
November 2005
October 2005
September 2005
August 2005
July 2005
June 2005
May 2005
April 2005
March 2005
February 2005
January 2005
----- 2004 -----
December 2004
November 2004
October 2004
September 2004
August 2004
July 2004
June 2004
May 2004
April 2004
March 2004
February 2004
ros-diffs@reactos.org
16 participants
413 discussions
Start a n
N
ew thread
[akhaldi] 64320: [BCRYPT_WINETEST] * Sync with Wine 1.7.27. CORE-8540
by akhaldi@svn.reactos.org
Author: akhaldi Date: Sat Sep 27 00:03:58 2014 New Revision: 64320 URL:
http://svn.reactos.org/svn/reactos?rev=64320&view=rev
Log: [BCRYPT_WINETEST] * Sync with Wine 1.7.27. CORE-8540 Modified: trunk/rostests/winetests/bcrypt/bcrypt.c Modified: trunk/rostests/winetests/bcrypt/bcrypt.c URL:
http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/bcrypt/bcrypt.c…
============================================================================== --- trunk/rostests/winetests/bcrypt/bcrypt.c [iso-8859-1] (original) +++ trunk/rostests/winetests/bcrypt/bcrypt.c [iso-8859-1] Sat Sep 27 00:03:58 2014 @@ -27,6 +27,7 @@ static NTSTATUS (WINAPI *pBCryptGenRandom)(BCRYPT_ALG_HANDLE hAlgorithm, PUCHAR pbBuffer, ULONG cbBuffer, ULONG dwFlags); +static NTSTATUS (WINAPI *pBCryptGetFipsAlgorithmMode)(BOOLEAN *enabled); static BOOL Init(void) { @@ -38,6 +39,7 @@ } pBCryptGenRandom = (void *)GetProcAddress(hbcrypt, "BCryptGenRandom"); + pBCryptGetFipsAlgorithmMode = (void *)GetProcAddress(hbcrypt, "BCryptGetFipsAlgorithmMode"); return TRUE; } @@ -78,10 +80,29 @@ ok(memcmp(buffer, buffer + 8, 8), "Expected a random number, got 0\n"); } +static void test_BCryptGetFipsAlgorithmMode(void) +{ + NTSTATUS ret; + BOOLEAN enabled; + + if (!pBCryptGetFipsAlgorithmMode) + { + win_skip("BCryptGetFipsAlgorithmMode is not available\n"); + return; + } + + ret = pBCryptGetFipsAlgorithmMode(&enabled); + ok(ret == STATUS_SUCCESS, "Expected STATUS_SUCCESS, got 0x%x\n", ret); + + ret = pBCryptGetFipsAlgorithmMode(NULL); + ok(ret == STATUS_INVALID_PARAMETER, "Expected STATUS_INVALID_PARAMETER, got 0x%x\n", ret); +} + START_TEST(bcrypt) { if (!Init()) return; test_BCryptGenRandom(); + test_BCryptGetFipsAlgorithmMode(); }
10 years, 3 months
1
0
0
0
[akhaldi] 64319: [BCRYPT] * Sync with Wine 1.7.27. CORE-8540
by akhaldi@svn.reactos.org
Author: akhaldi Date: Sat Sep 27 00:03:33 2014 New Revision: 64319 URL:
http://svn.reactos.org/svn/reactos?rev=64319&view=rev
Log: [BCRYPT] * Sync with Wine 1.7.27. CORE-8540 Modified: trunk/reactos/dll/win32/bcrypt/bcrypt.spec trunk/reactos/dll/win32/bcrypt/bcrypt_main.c trunk/reactos/media/doc/README.WINE Modified: trunk/reactos/dll/win32/bcrypt/bcrypt.spec URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/dll/win32/bcrypt/bcrypt.sp…
============================================================================== --- trunk/reactos/dll/win32/bcrypt/bcrypt.spec [iso-8859-1] (original) +++ trunk/reactos/dll/win32/bcrypt/bcrypt.spec [iso-8859-1] Sat Sep 27 00:03:33 2014 @@ -1,6 +1,6 @@ @ stub BCryptAddContextFunction @ stub BCryptAddContextFunctionProvider -@ stub BCryptCloseAlgorithmProvider +@ stdcall BCryptCloseAlgorithmProvider(ptr long) @ stub BCryptConfigureContext @ stub BCryptConfigureContextFunction @ stub BCryptCreateContext @@ -27,12 +27,12 @@ @ stdcall BCryptGenRandom(ptr ptr long long) @ stub BCryptGenerateKeyPair @ stub BCryptGenerateSymmetricKey -@ stub BCryptGetFipsAlgorithmMode +@ stdcall BCryptGetFipsAlgorithmMode(ptr) @ stub BCryptGetProperty @ stub BCryptHashData @ stub BCryptImportKey @ stub BCryptImportKeyPair -@ stub BCryptOpenAlgorithmProvider +@ stdcall BCryptOpenAlgorithmProvider(ptr wstr wstr long) @ stub BCryptQueryContextConfiguration @ stub BCryptQueryContextFunctionConfiguration @ stub BCryptQueryContextFunctionProperty Modified: trunk/reactos/dll/win32/bcrypt/bcrypt_main.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/dll/win32/bcrypt/bcrypt_ma…
============================================================================== --- trunk/reactos/dll/win32/bcrypt/bcrypt_main.c [iso-8859-1] (original) +++ trunk/reactos/dll/win32/bcrypt/bcrypt_main.c [iso-8859-1] Sat Sep 27 00:03:33 2014 @@ -29,20 +29,6 @@ #include <bcrypt.h> WINE_DEFAULT_DEBUG_CHANNEL(bcrypt); - -BOOL WINAPI DllMain(HINSTANCE hInstDLL, DWORD fdwReason, LPVOID lpv) -{ - TRACE("fdwReason %u\n", fdwReason); - - switch(fdwReason) - { - case DLL_PROCESS_ATTACH: - DisableThreadLibraryCalls(hInstDLL); - break; - } - - return TRUE; -} NTSTATUS WINAPI BCryptEnumAlgorithms(ULONG dwAlgOperations, ULONG *pAlgCount, BCRYPT_ALGORITHM_IDENTIFIER **ppAlgList, ULONG dwFlags) @@ -90,3 +76,34 @@ FIXME("called with unsupported parameters, returning error\n"); return STATUS_NOT_IMPLEMENTED; } + +NTSTATUS WINAPI BCryptOpenAlgorithmProvider(BCRYPT_ALG_HANDLE *algorithm, LPCWSTR algorithmId, + LPCWSTR implementation, DWORD flags) +{ + FIXME("%p, %s, %s, %08x - stub\n", algorithm, wine_dbgstr_w(algorithmId), wine_dbgstr_w(implementation), flags); + + if (!algorithm) + return STATUS_INVALID_PARAMETER; + + *algorithm = NULL; + + return STATUS_NOT_IMPLEMENTED; +} + +NTSTATUS WINAPI BCryptCloseAlgorithmProvider(BCRYPT_ALG_HANDLE algorithm, DWORD flags) +{ + FIXME("%p, %08x - stub\n", algorithm, flags); + + return STATUS_NOT_IMPLEMENTED; +} + +NTSTATUS WINAPI BCryptGetFipsAlgorithmMode(BOOLEAN *enabled) +{ + FIXME("%p - semi-stub\n", enabled); + + if (!enabled) + return STATUS_INVALID_PARAMETER; + + *enabled = FALSE; + return STATUS_SUCCESS; +} Modified: trunk/reactos/media/doc/README.WINE URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/media/doc/README.WINE?rev=…
============================================================================== --- trunk/reactos/media/doc/README.WINE [iso-8859-1] (original) +++ trunk/reactos/media/doc/README.WINE [iso-8859-1] Sat Sep 27 00:03:33 2014 @@ -55,7 +55,7 @@ reactos/dll/win32/atl80 # Synced to Wine-1.7.27 reactos/dll/win32/atl100 # Synced to Wine-1.7.27 reactos/dll/win32/avifil32 # Synced to Wine-1.7.17 -reactos/dll/win32/bcrypt # Synced to Wine-1.7.17 +reactos/dll/win32/bcrypt # Synced to Wine-1.7.27 reactos/dll/win32/browseui # Out of sync reactos/dll/win32/cabinet # Synced to Wine-1.7.17 reactos/dll/win32/clusapi # Synced to Wine-1.7.17
10 years, 3 months
1
0
0
0
[ekohl] 64318: [LSASRV] Fix memory related issues in calls to LsaEnumerateLogonSessions. - Initialize ClientBaseAddress to NULL because we do not need to allocate a fixed memory page. - Protect Len...
by ekohl@svn.reactos.org
Author: ekohl Date: Fri Sep 26 23:46:59 2014 New Revision: 64318 URL:
http://svn.reactos.org/svn/reactos?rev=64318&view=rev
Log: [LSASRV] Fix memory related issues in calls to LsaEnumerateLogonSessions. - Initialize ClientBaseAddress to NULL because we do not need to allocate a fixed memory page. - Protect Length from being overwitten by NtWriteVirtualMemory. Modified: trunk/reactos/dll/win32/lsasrv/session.c Modified: trunk/reactos/dll/win32/lsasrv/session.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/dll/win32/lsasrv/session.c…
============================================================================== --- trunk/reactos/dll/win32/lsasrv/session.c [iso-8859-1] (original) +++ trunk/reactos/dll/win32/lsasrv/session.c [iso-8859-1] Fri Sep 26 23:46:59 2014 @@ -131,8 +131,8 @@ PLIST_ENTRY SessionEntry; PLSAP_LOGON_SESSION CurrentSession; PLUID SessionList; - ULONG i, Length; - PVOID ClientBaseAddress; + ULONG i, Length, MemSize; + PVOID ClientBaseAddress = NULL; NTSTATUS Status; TRACE("LsapEnumLogonSessions()\n"); @@ -175,10 +175,11 @@ goto done; } + MemSize = Length; Status = NtAllocateVirtualMemory(ProcessHandle, &ClientBaseAddress, 0, - &Length, + &MemSize, MEM_COMMIT, PAGE_READWRITE); if (!NT_SUCCESS(Status))
10 years, 3 months
1
0
0
0
[hbelusca] 64317: [NTVDM]: Improve diagnostics.
by hbelusca@svn.reactos.org
Author: hbelusca Date: Fri Sep 26 22:39:21 2014 New Revision: 64317 URL:
http://svn.reactos.org/svn/reactos?rev=64317&view=rev
Log: [NTVDM]: Improve diagnostics. Modified: trunk/reactos/subsystems/ntvdm/hardware/vga.c Modified: trunk/reactos/subsystems/ntvdm/hardware/vga.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/ntvdm/hardware/…
============================================================================== --- trunk/reactos/subsystems/ntvdm/hardware/vga.c [iso-8859-1] (original) +++ trunk/reactos/subsystems/ntvdm/hardware/vga.c [iso-8859-1] Fri Sep 26 22:39:21 2014 @@ -1117,7 +1117,7 @@ /* Enter new text mode */ if (!VgaEnterTextMode(&Resolution)) { - DisplayMessage(L"An unexpected VGA error occurred while switching into text mode."); + DisplayMessage(L"An unexpected VGA error occurred while switching into text mode. Error: %u", GetLastError()); EmulatorTerminate(); return; } @@ -1127,7 +1127,7 @@ /* Enter graphics mode */ if (!VgaEnterGraphicsMode(&Resolution)) { - DisplayMessage(L"An unexpected VGA error occurred while switching into graphics mode."); + DisplayMessage(L"An unexpected VGA error occurred while switching into graphics mode. Error: %u", GetLastError()); EmulatorTerminate(); return; }
10 years, 3 months
1
0
0
0
[pschweitzer] 64316: [NTFS] - Divert NtfsLookupFile() as NtfsLookupFileAt() to allow opening relatives to a current MFT record. - Reimplement NtfsLookupFile() using NtfsLookupFileAt()
by pschweitzer@svn.reactos.org
Author: pschweitzer Date: Fri Sep 26 18:12:24 2014 New Revision: 64316 URL:
http://svn.reactos.org/svn/reactos?rev=64316&view=rev
Log: [NTFS] - Divert NtfsLookupFile() as NtfsLookupFileAt() to allow opening relatives to a current MFT record. - Reimplement NtfsLookupFile() using NtfsLookupFileAt() Modified: trunk/reactos/drivers/filesystems/ntfs/mft.c trunk/reactos/drivers/filesystems/ntfs/ntfs.h Modified: trunk/reactos/drivers/filesystems/ntfs/mft.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/m…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/mft.c [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/mft.c [iso-8859-1] Fri Sep 26 18:12:24 2014 @@ -645,54 +645,62 @@ } NTSTATUS +NtfsLookupFileAt(PDEVICE_EXTENSION Vcb, + PUNICODE_STRING PathName, + PFILE_RECORD_HEADER *FileRecord, + PNTFS_ATTR_CONTEXT *DataContext, + ULONGLONG CurrentMFTIndex) +{ + UNICODE_STRING Current, Remaining; + NTSTATUS Status; + + DPRINT1("NtfsLookupFileAt(%p, %wZ, %p, %p, %I64x)\n", Vcb, PathName, FileRecord, DataContext, CurrentMFTIndex); + + FsRtlDissectName(*PathName, &Current, &Remaining); + + while (Current.Length != 0) + { + DPRINT1("Lookup: %wZ\n", &Current); + + Status = NtfsFindMftRecord(Vcb, CurrentMFTIndex, &Current, &CurrentMFTIndex); + if (!NT_SUCCESS(Status)) + { + return Status; + } + + FsRtlDissectName(*PathName, &Current, &Remaining); + } + + *FileRecord = ExAllocatePoolWithTag(NonPagedPool, Vcb->NtfsInfo.BytesPerFileRecord, TAG_NTFS); + if (*FileRecord == NULL) + { + DPRINT("NtfsLookupFile: Can't allocate MFT record\n"); + return STATUS_INSUFFICIENT_RESOURCES; + } + + Status = ReadFileRecord(Vcb, CurrentMFTIndex, *FileRecord); + if (!NT_SUCCESS(Status)) + { + DPRINT("NtfsLookupFile: Can't read MFT record\n"); + return Status; + } + + Status = FindAttribute(Vcb, *FileRecord, AttributeData, PathName, DataContext); + if (!NT_SUCCESS(Status)) + { + DPRINT("NtfsLookupFile: Can't find data attribute\n"); + return Status; + } + + return STATUS_SUCCESS; +} + +NTSTATUS NtfsLookupFile(PDEVICE_EXTENSION Vcb, PUNICODE_STRING PathName, PFILE_RECORD_HEADER *FileRecord, PNTFS_ATTR_CONTEXT *DataContext) { - ULONGLONG CurrentMFTIndex; - UNICODE_STRING Current, Remaining; - NTSTATUS Status; - - DPRINT1("NtfsLookupFile(%p, %wZ, %p)\n", Vcb, PathName, FileRecord); - - CurrentMFTIndex = NTFS_FILE_ROOT; - FsRtlDissectName(*PathName, &Current, &Remaining); - - while (Current.Length != 0) - { - DPRINT1("Lookup: %wZ\n", &Current); - - Status = NtfsFindMftRecord(Vcb, CurrentMFTIndex, &Current, &CurrentMFTIndex); - if (!NT_SUCCESS(Status)) - { - return Status; - } - - FsRtlDissectName(*PathName, &Current, &Remaining); - } - - *FileRecord = ExAllocatePoolWithTag(NonPagedPool, Vcb->NtfsInfo.BytesPerFileRecord, TAG_NTFS); - if (*FileRecord == NULL) - { - DPRINT("NtfsLookupFile: Can't allocate MFT record\n"); - return STATUS_INSUFFICIENT_RESOURCES; - } - - Status = ReadFileRecord(Vcb, CurrentMFTIndex, *FileRecord); - if (!NT_SUCCESS(Status)) - { - DPRINT("NtfsLookupFile: Can't read MFT record\n"); - return Status; - } - - Status = FindAttribute(Vcb, *FileRecord, AttributeData, PathName, DataContext); - if (!NT_SUCCESS(Status)) - { - DPRINT("NtfsLookupFile: Can't find data attribute\n"); - return Status; - } - - return STATUS_SUCCESS; + return NtfsLookupFileAt(Vcb, PathName, FileRecord, DataContext, NTFS_FILE_ROOT); } /* EOF */ Modified: trunk/reactos/drivers/filesystems/ntfs/ntfs.h URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/n…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/ntfs.h [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/ntfs.h [iso-8859-1] Fri Sep 26 18:12:24 2014 @@ -634,6 +634,13 @@ PFILE_RECORD_HEADER *FileRecord, PNTFS_ATTR_CONTEXT *DataContext); +NTSTATUS +NtfsLookupFileAt(PDEVICE_EXTENSION Vcb, + PUNICODE_STRING PathName, + PFILE_RECORD_HEADER *FileRecord, + PNTFS_ATTR_CONTEXT *DataContext, + ULONGLONG CurrentMFTIndex); + /* misc.c */ BOOLEAN
10 years, 3 months
1
0
0
0
[pschweitzer] 64315: [NTFS] Also store the MFT index in the FCB
by pschweitzer@svn.reactos.org
Author: pschweitzer Date: Fri Sep 26 17:49:05 2014 New Revision: 64315 URL:
http://svn.reactos.org/svn/reactos?rev=64315&view=rev
Log: [NTFS] Also store the MFT index in the FCB Modified: trunk/reactos/drivers/filesystems/ntfs/fcb.c trunk/reactos/drivers/filesystems/ntfs/fsctl.c trunk/reactos/drivers/filesystems/ntfs/ntfs.h Modified: trunk/reactos/drivers/filesystems/ntfs/fcb.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/f…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/fcb.c [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/fcb.c [iso-8859-1] Fri Sep 26 17:49:05 2014 @@ -288,6 +288,7 @@ Fcb->RFCB.FileSize.QuadPart = PAGE_SIZE;//Vcb->CdInfo.RootSize; Fcb->RFCB.ValidDataLength.QuadPart = PAGE_SIZE;//Vcb->CdInfo.RootSize; Fcb->RFCB.AllocationSize.QuadPart = PAGE_SIZE;//Vcb->CdInfo.RootSize; + Fcb->MFTIndex = NTFS_FILE_ROOT; NtfsFCBInitializeCache(Vcb, Fcb); NtfsAddFCBToTable(Vcb, Fcb); Modified: trunk/reactos/drivers/filesystems/ntfs/fsctl.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/f…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/fsctl.c [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/fsctl.c [iso-8859-1] Fri Sep 26 17:49:05 2014 @@ -344,6 +344,7 @@ VolumeFcb->RFCB.FileSize.QuadPart = DeviceExt->NtfsInfo.SectorCount * DeviceExt->NtfsInfo.BytesPerSector; VolumeFcb->RFCB.ValidDataLength = VolumeFcb->RFCB.FileSize; VolumeFcb->RFCB.AllocationSize = VolumeFcb->RFCB.FileSize; + VolumeFcb->MFTIndex = 0; DeviceExt->VolumeFcb = VolumeFcb; /* Get volume information */ Modified: trunk/reactos/drivers/filesystems/ntfs/ntfs.h URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/n…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/ntfs.h [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/ntfs.h [iso-8859-1] Fri Sep 26 17:49:05 2014 @@ -137,6 +137,8 @@ LONG RefCount; ULONG Flags; + + ULONGLONG MFTIndex; // DIR_RECORD Entry;
10 years, 3 months
1
0
0
0
[dquintana] 64314: [BROWSEUI] * Implement SHCreateFromDesktop and supporting functions, and move those implementations to their own file. [SHELL32] * Handle message 1035 from the desktop window. [S...
by dquintana@svn.reactos.org
Author: dquintana Date: Fri Sep 26 14:47:07 2014 New Revision: 64314 URL:
http://svn.reactos.org/svn/reactos?rev=64314&view=rev
Log: [BROWSEUI] * Implement SHCreateFromDesktop and supporting functions, and move those implementations to their own file. [SHELL32] * Handle message 1035 from the desktop window. [SHLWAPI] * Fix a bug in SHAllocShared, where source and destination parameters were reversed. [EXPLORER-NEW] * Use SHCreateFromDesktop to open the new window. NOTE: There appears to be some more problems with the SH*Shared implementation, beyond the swapped parameters, which prevent the opening of the new windows. These functions will have to be revised and the corrected implementation sent to WINE. Added: branches/shell-experiments/dll/win32/browseui/desktopipc.cpp (with props) Modified: branches/shell-experiments/base/shell/explorer-new/explorer.c branches/shell-experiments/base/shell/explorer-new/traywnd.c branches/shell-experiments/base/shell/filebrowser/CMakeLists.txt branches/shell-experiments/base/shell/filebrowser/filebrowser.c branches/shell-experiments/dll/win32/browseui/CMakeLists.txt branches/shell-experiments/dll/win32/browseui/browseuiord.cpp branches/shell-experiments/dll/win32/browseui/shellbrowser.cpp branches/shell-experiments/dll/win32/shell32/desktop.cpp branches/shell-experiments/dll/win32/shell32/undocshell.h branches/shell-experiments/dll/win32/shlwapi/ordinal.c branches/shell-experiments/include/psdk/shlwapi.h branches/shell-experiments/include/psdk/shlwapi_undoc.h Modified: branches/shell-experiments/base/shell/explorer-new/explorer.c URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/base/shell/ex…
============================================================================== --- branches/shell-experiments/base/shell/explorer-new/explorer.c [iso-8859-1] (original) +++ branches/shell-experiments/base/shell/explorer-new/explorer.c [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -383,6 +383,25 @@ DbgPrint("Explorer starting... Commandline: %S\n", lpCmdLine); + /* + * Set our shutdown parameters: we want to shutdown the very last, + * but before any TaskMgr instance (which has a shutdown level of 1). + */ + SetProcessShutdownParameters(2, 0); + + if (GetShellWindow() == NULL) + CreateShellDesktop = TRUE; + + /* FIXME - initialize SSO Thread */ + + if (!CreateShellDesktop) + { + EXPLORER_CMDLINE_PARSE_RESULTS parseResults = { 0 }; + + if (SHExplorerParseCmdLine(&parseResults)) + return SHCreateFromDesktop(&parseResults); + } + if (RegOpenKey(HKEY_CURRENT_USER, TEXT("Software\\Microsoft\\Windows\\CurrentVersion\\Explorer"), &hkExplorer) != ERROR_SUCCESS) @@ -407,72 +426,33 @@ InitCommonControls(); OleInitialize(NULL); - /* - * Set our shutdown parameters: we want to shutdown the very last, - * but before any TaskMgr instance (which has a shutdown level of 1). - */ - SetProcessShutdownParameters(2, 0); - ProcessStartupItems(); - if (GetShellWindow() == NULL) - CreateShellDesktop = TRUE; - - /* FIXME - initialize SSO Thread */ - - if (CreateShellDesktop) - { - /* Initialize shell dde support */ - ShellDDEInit(TRUE); - - /* Initialize shell icons */ - FileIconInit(TRUE); - - /* Initialize CLSID_ShellWindows class */ - WinList_Init(); - - if (RegisterTrayWindowClass() && RegisterTaskSwitchWndClass()) - { - Tray = CreateTrayWindow(); - /* This not only hides the minimized window captions in the bottom - left screen corner, but is also needed in order to receive - HSHELL_* notification messages (which are required for taskbar - buttons to work right) */ - HideMinimizedWindows(TRUE); - - if (Tray != NULL) - hShellDesktop = DesktopCreateWindow(Tray); - } - - /* WinXP: Notify msgina to hide the welcome screen */ - if (!SetShellReadyEvent(TEXT("msgina: ShellReadyEvent"))) - SetShellReadyEvent(TEXT("Global\\msgina: ShellReadyEvent")); - } - else - { - HRESULT hr; - EXPLORER_CMDLINE_PARSE_RESULTS parseResults = { 0 }; - - if (!SHExplorerParseCmdLine(&parseResults)) - return 0; - - // TODO: Handle the case where .strPath was assigned instead of .pidlPath - - if (parseResults.dwFlags & SH_EXPLORER_CMDLINE_FLAG_IDLIST) - { - TRACE("Trying to open browser window... \n"); - - hr = SHOpenNewFrame(parseResults.pidlPath, NULL, 0, 0); - if (FAILED(hr)) - return 0; - - /* FIXME: we should wait a bit here and see if a window was created. If not we should exit this process. */ - Sleep(1000); - ExitThread(0); - - return 0; - } - } + /* Initialize shell dde support */ + ShellDDEInit(TRUE); + + /* Initialize shell icons */ + FileIconInit(TRUE); + + /* Initialize CLSID_ShellWindows class */ + WinList_Init(); + + if (RegisterTrayWindowClass() && RegisterTaskSwitchWndClass()) + { + Tray = CreateTrayWindow(); + /* This not only hides the minimized window captions in the bottom + left screen corner, but is also needed in order to receive + HSHELL_* notification messages (which are required for taskbar + buttons to work right) */ + HideMinimizedWindows(TRUE); + + if (Tray != NULL) + hShellDesktop = DesktopCreateWindow(Tray); + } + + /* WinXP: Notify msgina to hide the welcome screen */ + if (!SetShellReadyEvent(TEXT("msgina: ShellReadyEvent"))) + SetShellReadyEvent(TEXT("Global\\msgina: ShellReadyEvent")); if (Tray != NULL) { Modified: branches/shell-experiments/base/shell/explorer-new/traywnd.c URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/base/shell/ex…
============================================================================== --- branches/shell-experiments/base/shell/explorer-new/traywnd.c [iso-8859-1] (original) +++ branches/shell-experiments/base/shell/explorer-new/traywnd.c [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -2199,7 +2199,8 @@ } } -static void ProcessMouseTracking(ITrayWindowImpl * This) +static void +ProcessMouseTracking(ITrayWindowImpl * This) { RECT rcCurrent; POINT pt; @@ -2249,7 +2250,8 @@ } } -static void ProcessAutoHide(ITrayWindowImpl * This) +static void +ProcessAutoHide(ITrayWindowImpl * This) { RECT rc = This->rcTrayWnd[This->Position]; INT w = This->TraySize.cx - GetSystemMetrics(SM_CXBORDER) * 2 - 1; Modified: branches/shell-experiments/base/shell/filebrowser/CMakeLists.txt URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/base/shell/fi…
============================================================================== --- branches/shell-experiments/base/shell/filebrowser/CMakeLists.txt [iso-8859-1] (original) +++ branches/shell-experiments/base/shell/filebrowser/CMakeLists.txt [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -12,4 +12,4 @@ msvcrt kernel32) -add_cd_file(TARGET explorer DESTINATION reactos FOR all) +add_cd_file(TARGET filebrowser DESTINATION reactos FOR all) Modified: branches/shell-experiments/base/shell/filebrowser/filebrowser.c URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/base/shell/fi…
============================================================================== --- branches/shell-experiments/base/shell/filebrowser/filebrowser.c [iso-8859-1] (original) +++ branches/shell-experiments/base/shell/filebrowser/filebrowser.c [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -23,115 +23,18 @@ #include <windows.h> #include <shobjidl.h> #include <shlobj.h> +#include <shlwapi.h> +#include <shlwapi_undoc.h> +#include <stdio.h> typedef HRESULT (WINAPI *SH_OPEN_NEW_FRAME)(LPITEMIDLIST pidl, IUnknown *paramC, long param10, long param14); int _tmain(int argc, _TCHAR* argv[]) { - WCHAR root[MAX_PATH]; - HRESULT hr; - LPSHELLFOLDER pDesktopFolder = NULL; - LPITEMIDLIST pidlRoot = NULL; - typedef HRESULT(WINAPI *SH_OPEN_NEW_FRAME)(LPITEMIDLIST pidl, IUnknown *paramC, long param10, long param14); - SH_OPEN_NEW_FRAME SHOpenNewFrame; + EXPLORER_CMDLINE_PARSE_RESULTS parseResults = { 0 }; - HMODULE hBrowseui = LoadLibraryW(L"browseui.dll"); + if (SHExplorerParseCmdLine(&parseResults)) + return SHCreateFromDesktop(&parseResults); - if (!hBrowseui) - return 1; - - - if (argc < 2) - { - SH_OPEN_NEW_FRAME SHOpenNewFrame = (SH_OPEN_NEW_FRAME) GetProcAddress(hBrowseui, (LPCSTR) 103); - LPITEMIDLIST pidlDrives; - SHGetSpecialFolderLocation(NULL, CSIDL_DRIVES, &pidlDrives); - SHOpenNewFrame((LPITEMIDLIST) pidlDrives, NULL, 0, 0); - } - else - { - /* A shell is already loaded. Parse the command line arguments - and unless we need to do something specific simply display - the desktop in a separate explorer window */ - /* FIXME */ - - /* Commandline switches: - * - * /n Open a new window, even if an existing one still exists. - * /e Start with the explorer sidebar shown. - * /root,<object> Open a window for the given object path. - * /select,<object> Open a window with the given object selected. - */ - - /* FIXME: Do it right */ - WCHAR* tmp = wcsstr(argv[1], L"/root,"); - if (tmp) - { - WCHAR* tmp2; - - tmp += 6; // skip to beginning of path - tmp2 = wcschr(tmp, L','); - - if (tmp2) - { - wcsncpy(root, tmp, tmp2 - tmp); - } - else - { - wcscpy(root, tmp); - } - } - else - { - wcscpy(root, argv[1]); - } - - if (root[0] == L'"') - { - int len = wcslen(root) - 2; - wcsncpy(root, root + 1, len); - root[len] = 0; - } - - if (wcslen(root) > 0) - { - LPITEMIDLIST pidl; - ULONG chEaten; - ULONG dwAttributes; - - if (SUCCEEDED(SHGetDesktopFolder(&pDesktopFolder))) - { - hr = pDesktopFolder->lpVtbl->ParseDisplayName(pDesktopFolder, - NULL, - NULL, - root, - &chEaten, - &pidl, - &dwAttributes); - if (SUCCEEDED(hr)) - { - pidlRoot = pidl; - } - } - } - - if (!pidlRoot) - { - hr = SHGetSpecialFolderLocation(NULL, CSIDL_DRIVES, &pidlRoot); - if (FAILED(hr)) - return 0; - } - - SHOpenNewFrame = (SH_OPEN_NEW_FRAME) GetProcAddress(hBrowseui, (LPCSTR) 103); - - hr = SHOpenNewFrame(pidlRoot, (IUnknown*) pDesktopFolder, 0, 0); - if (FAILED(hr)) - return 0; - } - - /* FIXME: we should wait a bit here and see if a window was created. If not we should exit this process. */ - Sleep(1000); - - ExitThread(0); + return 0; } - Modified: branches/shell-experiments/dll/win32/browseui/CMakeLists.txt URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/dll/win32/bro…
============================================================================== --- branches/shell-experiments/dll/win32/browseui/CMakeLists.txt [iso-8859-1] (original) +++ branches/shell-experiments/dll/win32/browseui/CMakeLists.txt [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -22,6 +22,7 @@ browseui.cpp browseuiord.cpp commonbrowser.cpp + desktopipc.cpp globalfoldersettings.cpp internettoolbar.cpp parsecmdline.cpp Modified: branches/shell-experiments/dll/win32/browseui/browseuiord.cpp URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/dll/win32/bro…
============================================================================== --- branches/shell-experiments/dll/win32/browseui/browseuiord.cpp [iso-8859-1] (original) +++ branches/shell-experiments/dll/win32/browseui/browseuiord.cpp [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -20,8 +20,6 @@ #include "precomp.h" -extern DWORD WINAPI BrowserThreadProc(LPVOID lpThreadParameter); - /************************************************************************* * InitOCHostClass [BROWSEUI.101] */ @@ -31,28 +29,11 @@ } /************************************************************************* - * SHOpenFolderWindow [BROWSEUI.102] - */ -extern "C" long WINAPI SHOpenFolderWindow(IEThreadParamBlock *param8) -{ - return 0; -} - -/************************************************************************* * SHCreateSavedWindows [BROWSEUI.105] * Called to recreate explorer windows from previous session */ extern "C" void WINAPI SHCreateSavedWindows() { -} - -/************************************************************************* - * SHCreateFromDesktop [BROWSEUI.106] - * parameter is a FolderInfo - */ -extern "C" long WINAPI SHCreateFromDesktop(long param8) -{ - return -1; } /************************************************************************* @@ -92,93 +73,11 @@ } /************************************************************************* - * SHCreateIETHREADPARAM [BROWSEUI.123] - */ -extern "C" IEThreadParamBlock *WINAPI SHCreateIETHREADPARAM( - long param8, long paramC, IUnknown *param10, IUnknown *param14) -{ - IEThreadParamBlock *result; - - result = (IEThreadParamBlock *)LocalAlloc(LMEM_ZEROINIT, 256); - if (result == NULL) - return NULL; - result->offset0 = param8; - result->offset8 = paramC; - result->offsetC = param10; - if (param10 != NULL) - param10->AddRef(); - result->offset14 = param14; - if (param14 != NULL) - param14->AddRef(); - return result; -} - -/************************************************************************* - * SHCloneIETHREADPARAM [BROWSEUI.124] - */ -extern "C" IEThreadParamBlock *WINAPI SHCloneIETHREADPARAM(IEThreadParamBlock *param) -{ - IEThreadParamBlock *result; - - result = (IEThreadParamBlock *)LocalAlloc(LMEM_FIXED, 256); - if (result == NULL) - return NULL; - memcpy(result, param, 0x40 * 4); - if (result->directoryPIDL != NULL) - result->directoryPIDL = ILClone(result->directoryPIDL); - if (result->offset7C != NULL) - result->offset7C = ILClone(result->offset7C); - if (result->offset80 != NULL) - result->offset80 = ILClone(result->offset80); - if (result->offset70 != NULL) - result->offset70->AddRef(); -#if 0 - if (result->offsetC != NULL) - result->offsetC->Method2C(); -#endif - return result; -} - -/************************************************************************* * SHParseIECommandLine [BROWSEUI.125] */ extern "C" long WINAPI SHParseIECommandLine(long param8, long paramC) { return -1; -} - -/************************************************************************* - * SHDestroyIETHREADPARAM [BROWSEUI.126] - */ -extern "C" void WINAPI SHDestroyIETHREADPARAM(IEThreadParamBlock *param) -{ - if (param == NULL) - return; - if (param->directoryPIDL != NULL) - ILFree(param->directoryPIDL); - if (param->offset7C != NULL) - ILFree(param->offset7C); - if ((param->offset4 & 0x80000) == 0 && param->offset80 != NULL) - ILFree(param->offset80); - if (param->offset14 != NULL) - param->offset14->Release(); - if (param->offset70 != NULL) - param->offset70->Release(); - if (param->offset78 != NULL) - param->offset78->Release(); - if (param->offsetC != NULL) - param->offsetC->Release(); - if (param->offsetF8 != NULL) - param->offsetF8->Release(); - LocalFree(param); -} - -/************************************************************************* - * SHOnCWMCommandLine [BROWSEUI.127] - */ -extern "C" HRESULT WINAPI SHOnCWMCommandLine(long param8) -{ - return E_NOTIMPL; } /************************************************************************* @@ -261,36 +160,3 @@ { return TRUE; } - -// 75FA56C1h -// (pidl, 0, -1, 1) -// this function should handle creating a new process if needed, but I'm leaving that out for now -// this function always opens a new window - it does NOT check for duplicates -/************************************************************************* - * SHOpenNewFrame [BROWSEUI.103] - */ -extern "C" HRESULT WINAPI SHOpenNewFrame(LPITEMIDLIST pidl, IUnknown *paramC, long param10, long param14) -{ - IEThreadParamBlock *parameters; - HANDLE threadHandle; - DWORD threadID; - - parameters = SHCreateIETHREADPARAM(0, 1, paramC, NULL); - if (parameters == NULL) - { - ILFree(pidl); - return E_OUTOFMEMORY; - } - if (paramC != NULL) - parameters->offset10 = param10; - parameters->directoryPIDL = pidl; - parameters->offset4 = param14; - threadHandle = CreateThread(NULL, 0x10000, BrowserThreadProc, parameters, 0, &threadID); - if (threadHandle != NULL) - { - CloseHandle(threadHandle); - return S_OK; - } - SHDestroyIETHREADPARAM(parameters); - return E_FAIL; -} Added: branches/shell-experiments/dll/win32/browseui/desktopipc.cpp URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/dll/win32/bro…
============================================================================== --- branches/shell-experiments/dll/win32/browseui/desktopipc.cpp (added) +++ branches/shell-experiments/dll/win32/browseui/desktopipc.cpp [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -0,0 +1,591 @@ +#include "precomp.h" +#include <shlwapi.h> +#include <shlwapi_undoc.h> + +#define PROXY_DESKTOP_CLASS L"Proxy Desktop" + +BOOL g_SeparateFolders = FALSE; + +// fields indented more are unknown ;P +struct HNFBlock +{ + UINT cbSize; + DWORD offset4; + DWORD offset8; + DWORD offsetC; + DWORD offset10; + DWORD offset14; + DWORD offset18; + DWORD offset1C; + DWORD offset20; + DWORD offset24; + DWORD offset28; + DWORD offset2C; + DWORD offset30; + UINT directoryPidlLength; + UINT pidlSize7C; + UINT pidlSize80; + UINT pathLength; +}; + +extern DWORD WINAPI BrowserThreadProc(LPVOID lpThreadParameter); + +class CProxyDesktop : + public CComObjectRootEx<CComMultiThreadModelNoCS>, + public CWindowImpl < CProxyDesktop, CWindow, CFrameWinTraits > +{ + IEThreadParamBlock * m_Parameters; + + LPITEMIDLIST m_rootPidl; + +public: + CProxyDesktop(IEThreadParamBlock * parameters) : + m_Parameters(parameters) + { + + } + + virtual ~CProxyDesktop() + { + } + + LRESULT OnMessage1037(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled) + { + DbgPrint("Proxy Desktop message 1037.\n"); + bHandled = TRUE; + return TRUE; + } + + LRESULT OnOpenNewWindow(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled) + { + DbgPrint("Proxy Desktop message 1035 received.\n"); + bHandled = TRUE; + SHOnCWMCommandLine((HANDLE) lParam); + return 0; + } + + DECLARE_WND_CLASS_EX(PROXY_DESKTOP_CLASS, CS_SAVEBITS | CS_DROPSHADOW, COLOR_3DFACE) + + BEGIN_MSG_MAP(CProxyDesktop) + MESSAGE_HANDLER(WM_EXPLORER_1037, OnMessage1037) + MESSAGE_HANDLER(WM_EXPLORER_OPEN_NEW_WINDOW, OnOpenNewWindow) + END_MSG_MAP() +}; + +static CProxyDesktop * CreateProxyDesktop(IEThreadParamBlock * parameters) +{ + return new CProxyDesktop(parameters); +} + +HWND FindShellProxy(LPITEMIDLIST pidl) +{ + if (!g_SeparateFolders) + { + HWND shell = GetShellWindow(); + + if (shell) + { + DbgPrint("Found main desktop.\n"); + return shell; + } + } + else + { + DbgPrint("Separate folders setting enabled. Ignoring main desktop.\n"); + } + + HWND proxy = FindWindow(PROXY_DESKTOP_CLASS, NULL); + if (proxy) + { + DbgPrint("Found proxy desktop.\n"); + return proxy; + } + + return NULL; +} + +HANDLE MakeSharedPacket(IEThreadParamBlock * threadParams, LPCWSTR strPath, int dwProcessId) +{ + HNFBlock* hnfData; + UINT sharedBlockSize = sizeof(*hnfData); + UINT directoryPidlLength = 0; + UINT pidlSize7C = 0; + UINT pidlSize80 = 0; + UINT pathLength = 0; + LPITEMIDLIST pidl80 = threadParams->offset80; + + // Count the total length of the message packet + + // directory PIDL + if (threadParams->directoryPIDL) + { + directoryPidlLength = ILGetSize(threadParams->directoryPIDL); + sharedBlockSize += directoryPidlLength; + DbgPrint("directoryPidlLength=%d\n", directoryPidlLength); + } + + // another PIDL + if (threadParams->offset7C) + { + pidlSize7C = ILGetSize(threadParams->offset7C); + sharedBlockSize += pidlSize7C; + DbgPrint("pidlSize7C=%d\n", pidlSize7C); + } + + // This flag indicates the presence of another pidl? + if (!(threadParams->offset84 & 0x8000)) + { + if (pidl80) + { + pidlSize80 = ILGetSize(pidl80); + sharedBlockSize += pidlSize80; + DbgPrint("pidlSize80=%d\n", pidlSize7C); + } + } + else + { + DbgPrint("pidl80 sent by value = %p\n", pidl80); + pidlSize80 = 4; + sharedBlockSize += pidlSize80; + } + + // The path string + if (strPath) + { + pathLength = 2 * lstrlenW(strPath) + 2; + sharedBlockSize += pathLength; + DbgPrint("pathLength=%d\n", pidlSize7C); + } + + DbgPrint("sharedBlockSize=%d\n", sharedBlockSize); + + // Allocate and fill the shared section + HANDLE hShared = SHAllocShared(0, sharedBlockSize, dwProcessId); + if (!hShared) + { + DbgPrint("Shared section alloc error.\n"); + return 0; + } + + PBYTE target = (PBYTE) SHLockShared(hShared, dwProcessId); + if (!target) + { + DbgPrint("Shared section lock error. %d\n", GetLastError()); + SHFreeShared(hShared, dwProcessId); + return 0; + } + + // Basic information + hnfData = (HNFBlock*) target; + hnfData->cbSize = sharedBlockSize; + hnfData->offset4 = (DWORD) (threadParams->dwFlags); + hnfData->offset8 = (DWORD) (threadParams->offset8); + hnfData->offsetC = (DWORD) (threadParams->offset74); + hnfData->offset10 = (DWORD) (threadParams->offsetD8); + hnfData->offset14 = (DWORD) (threadParams->offset84); + hnfData->offset18 = (DWORD) (threadParams->offset88); + hnfData->offset1C = (DWORD) (threadParams->offset8C); + hnfData->offset20 = (DWORD) (threadParams->offset90); + hnfData->offset24 = (DWORD) (threadParams->offset94); + hnfData->offset28 = (DWORD) (threadParams->offset98); + hnfData->offset2C = (DWORD) (threadParams->offset9C); + hnfData->offset30 = (DWORD) (threadParams->offsetA0); + hnfData->directoryPidlLength = 0; + hnfData->pidlSize7C = 0; + hnfData->pidlSize80 = 0; + hnfData->pathLength = 0; + target += sizeof(*hnfData); + + // Copy the directory pidl contents + if (threadParams->directoryPIDL) + { + memcpy(target, threadParams->directoryPIDL, directoryPidlLength); + target += directoryPidlLength; + hnfData->directoryPidlLength = directoryPidlLength; + } + + // Copy the other pidl contents + if (threadParams->offset7C) + { + memcpy(target, threadParams->offset7C, pidlSize7C); + target += pidlSize7C; + hnfData->pidlSize7C = pidlSize7C; + } + + // copy the third pidl + if (threadParams->offset84 & 0x8000) + { + *(LPITEMIDLIST*) target = pidl80; + target += pidlSize80; + hnfData->pidlSize80 = pidlSize80; + } + else if (pidl80) + { + memcpy(target, pidl80, pidlSize80); + target += pidlSize80; + hnfData->pidlSize80 = pidlSize80; + } + + // and finally the path string + if (strPath) + { + memcpy(target, strPath, pathLength); + hnfData->pathLength = pathLength; + } + + SHUnlockShared(hnfData); + + return hShared; +} + +PIE_THREAD_PARAM_BLOCK ParseSharedPacket(HANDLE hData) +{ + HNFBlock * hnfData; + PBYTE block; + int pid; + PIE_THREAD_PARAM_BLOCK params = NULL; + + if (!hData) + goto cleanup0; + + pid = GetCurrentProcessId(); + block = (PBYTE) SHLockShared(hData, pid); + + hnfData = (HNFBlock *) block; + if (!block) + goto cleanup2; + + if (hnfData->cbSize < sizeof(HNFBlock)) + goto cleanup2; + + params = SHCreateIETHREADPARAM(0, hnfData->offset8, 0, 0); + if (!params) + goto cleanup2; + + params->dwFlags = hnfData->offset4; + params->offset8 = hnfData->offset8; + params->offset74 = hnfData->offsetC; + params->offsetD8 = hnfData->offset10; + params->offset84 = hnfData->offset14; + params->offset88 = hnfData->offset18; + params->offset8C = hnfData->offset1C; + params->offset90 = hnfData->offset20; + params->offset94 = hnfData->offset24; + params->offset98 = hnfData->offset28; + params->offset9C = hnfData->offset2C; + params->offsetA0 = hnfData->offset30; + + block += sizeof(*hnfData); + if (hnfData->directoryPidlLength) + { + LPITEMIDLIST pidl = NULL; + if (*block) + pidl = ILClone((LPITEMIDLIST) block); + params->directoryPIDL = pidl; + + block += hnfData->directoryPidlLength; + } + + if (hnfData->pidlSize7C) + { + LPITEMIDLIST pidl = NULL; + if (*block) + pidl = ILClone((LPITEMIDLIST) block); + params->offset7C = pidl; + + block += hnfData->pidlSize80; + } + + if (hnfData->pidlSize80) + { + if (!(params->offset84 & 0x8000)) + { + params->offset80 = *(LPITEMIDLIST *) block; + } + else + { + LPITEMIDLIST pidl = NULL; + if (*block) + pidl = ILClone((LPITEMIDLIST) block); + params->offset80 = pidl; + } + + block += hnfData->pidlSize80; + } + + if (hnfData->pathLength) + { + CComPtr<IShellFolder> psfDesktop; + PWSTR strPath = (PWSTR) block; + + if (FAILED(SHGetDesktopFolder(&psfDesktop))) + { + params->directoryPIDL = NULL; + goto cleanup0; + } + + if (FAILED(psfDesktop->ParseDisplayName(NULL, NULL, strPath, NULL, ¶ms->directoryPIDL, NULL))) + { + params->directoryPIDL = NULL; + goto cleanup0; + } + } + +cleanup2: + SHUnlockShared(hnfData); + SHFreeShared(hData, pid); + +cleanup0: + if (!params->directoryPIDL) + { + SHDestroyIETHREADPARAM(params); + return NULL; + } + + return params; +} + + +/************************************************************************* +* SHOnCWMCommandLine [BROWSEUI.127] +*/ +extern "C" BOOL WINAPI SHOnCWMCommandLine(HANDLE hSharedInfo) +{ + DbgPrint("SHOnCWMCommandLine\n"); + + PIE_THREAD_PARAM_BLOCK params = ParseSharedPacket(hSharedInfo); + + if (params) + return SHOpenFolderWindow(params); + + return FALSE; +} + +/************************************************************************* +* SHCreateIETHREADPARAM [BROWSEUI.123] +*/ +extern "C" IEThreadParamBlock *WINAPI SHCreateIETHREADPARAM( + long param8, long paramC, IUnknown *param10, IUnknown *param14) +{ + IEThreadParamBlock *result; + + DbgPrint("SHCreateIETHREADPARAM\n"); + + result = (IEThreadParamBlock *) LocalAlloc(LMEM_ZEROINIT, 256); + if (result == NULL) + return NULL; + result->offset0 = param8; + result->offset8 = paramC; + result->offsetC = param10; + if (param10 != NULL) + param10->AddRef(); + result->offset14 = param14; + if (param14 != NULL) + param14->AddRef(); + return result; +} + +/************************************************************************* +* SHCloneIETHREADPARAM [BROWSEUI.124] +*/ +extern "C" IEThreadParamBlock *WINAPI SHCloneIETHREADPARAM(IEThreadParamBlock *param) +{ + IEThreadParamBlock *result; + + DbgPrint("SHCloneIETHREADPARAM\n"); + + result = (IEThreadParamBlock *) LocalAlloc(LMEM_FIXED, 256); + if (result == NULL) + return NULL; + memcpy(result, param, 0x40 * 4); + if (result->directoryPIDL != NULL) + result->directoryPIDL = ILClone(result->directoryPIDL); + if (result->offset7C != NULL) + result->offset7C = ILClone(result->offset7C); + if (result->offset80 != NULL) + result->offset80 = ILClone(result->offset80); + if (result->offset70 != NULL) + result->offset70->AddRef(); +#if 0 + if (result->offsetC != NULL) + result->offsetC->Method2C(); +#endif + return result; +} + +/************************************************************************* +* SHDestroyIETHREADPARAM [BROWSEUI.126] +*/ +extern "C" void WINAPI SHDestroyIETHREADPARAM(IEThreadParamBlock *param) +{ + DbgPrint("SHDestroyIETHREADPARAM\n"); + + if (param == NULL) + return; + if (param->directoryPIDL != NULL) + ILFree(param->directoryPIDL); + if (param->offset7C != NULL) + ILFree(param->offset7C); + if ((param->dwFlags & 0x80000) == 0 && param->offset80 != NULL) + ILFree(param->offset80); + if (param->offset14 != NULL) + param->offset14->Release(); + if (param->offset70 != NULL) + param->offset70->Release(); + if (param->offset78 != NULL) + param->offset78->Release(); + if (param->offsetC != NULL) + param->offsetC->Release(); + if (param->offsetF8 != NULL) + param->offsetF8->Release(); + LocalFree(param); +} + +/************************************************************************* +* SHOpenFolderWindow [BROWSEUI.102] +* see SHOpenNewFrame below for remarks +*/ +extern "C" HRESULT WINAPI SHOpenFolderWindow(PIE_THREAD_PARAM_BLOCK parameters) +{ + HANDLE threadHandle; + DWORD threadID; + + DbgPrint("SHOpenFolderWindow\n"); + + threadHandle = CreateThread(NULL, 0x10000, BrowserThreadProc, parameters, 0, &threadID); + if (threadHandle != NULL) + { + CloseHandle(threadHandle); + return S_OK; + } + SHDestroyIETHREADPARAM(parameters); + return E_FAIL; +} + +// 75FA56C1h +// (pidl, 0, -1, 1) +// this function should handle creating a new process if needed, but I'm leaving that out for now +// this function always opens a new window - it does NOT check for duplicates +/************************************************************************* +* SHOpenNewFrame [BROWSEUI.103] +*/ +extern "C" HRESULT WINAPI SHOpenNewFrame(LPITEMIDLIST pidl, IUnknown *paramC, long param10, DWORD dwFlags) +{ + IEThreadParamBlock *parameters; + + DbgPrint("SHOpenNewFrame\n"); + + parameters = SHCreateIETHREADPARAM(0, 1, paramC, NULL); + if (parameters == NULL) + { + ILFree(pidl); + return E_OUTOFMEMORY; + } + if (paramC != NULL) + parameters->offset10 = param10; + parameters->directoryPIDL = pidl; + parameters->dwFlags = dwFlags; + + return SHOpenFolderWindow(parameters); +} + +/************************************************************************* +* SHCreateFromDesktop [BROWSEUI.106] +* parameter is a FolderInfo +*/ +BOOL WINAPI SHCreateFromDesktop(ExplorerCommandLineParseResults * parseResults) +{ + DbgPrint("SHCreateFromDesktop\n"); + + IEThreadParamBlock * parameters = SHCreateIETHREADPARAM(0, 0, 0, 0); + if (!parameters) + return FALSE; + + PCWSTR strPath = NULL; + if (parseResults->dwFlags & SH_EXPLORER_CMDLINE_FLAG_STRING) + { + if (parseResults->pidlPath) + { + WARN("strPath and pidlPath are both assigned. This shouldn't happen.\n"); + } + + strPath = parseResults->strPath; + } + + parameters->dwFlags = parseResults->dwFlags; + parameters->offset8 = parseResults->offsetC; + + LPITEMIDLIST pidl = parseResults->pidlPath ? ILClone(parseResults->pidlPath) : NULL; + if (!pidl && parseResults->dwFlags & SH_EXPLORER_CMDLINE_FLAG_STRING) + { + if (parseResults->strPath && parseResults->strPath[0]) + { + pidl = ILCreateFromPathW(parseResults->strPath); + } + } + + parameters->directoryPIDL = pidl; + + // Try to find the owner of the idlist, if we aren't running /SEPARATE + HWND desktop = NULL; + if (!(parseResults->dwFlags & SH_EXPLORER_CMDLINE_FLAG_SEPARATE)) + desktop = FindShellProxy(parameters->directoryPIDL); + + // If found, ask it to open the new window + if (desktop) + { + DbgPrint("Found desktop hwnd=%p\n", desktop); + + DWORD dwProcessId; + + GetWindowThreadProcessId(desktop, &dwProcessId); + AllowSetForegroundWindow(dwProcessId); + + HANDLE hShared = MakeSharedPacket(parameters, strPath, dwProcessId); + if (hShared) + { + DbgPrint("Sending open message...\n"); + + PostMessageW(desktop, WM_EXPLORER_OPEN_NEW_WINDOW, 0, (LPARAM) hShared); + } + + SHDestroyIETHREADPARAM(parameters); + return TRUE; + } + + DbgPrint("Desktop not found or separate flag requested.\n"); + + // Else, start our own message loop! + HRESULT hr = CoInitialize(NULL); + CProxyDesktop * proxy = CreateProxyDesktop(parameters); + if (proxy) + { + LONG refCount; + CComPtr<IUnknown> thread; + if (SHCreateThreadRef(&refCount, &thread) >= 0) + { + SHSetInstanceExplorer(thread); + if (strPath) + parameters->directoryPIDL = ILCreateFromPath(strPath); + SHOpenFolderWindow(parameters); + parameters = NULL; + thread.Release(); + } + + MSG Msg; + while (GetMessageW(&Msg, 0, 0, 0) && refCount) + { + TranslateMessage(&Msg); + DispatchMessageW(&Msg); + } + + delete proxy; + } + + if (SUCCEEDED(hr)) + CoUninitialize(); + + SHDestroyIETHREADPARAM(parameters); + + return TRUE; +} Propchange: branches/shell-experiments/dll/win32/browseui/desktopipc.cpp ------------------------------------------------------------------------------ svn:eol-style = native Modified: branches/shell-experiments/dll/win32/browseui/shellbrowser.cpp URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/dll/win32/bro…
============================================================================== --- branches/shell-experiments/dll/win32/browseui/shellbrowser.cpp [iso-8859-1] (original) +++ branches/shell-experiments/dll/win32/browseui/shellbrowser.cpp [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -3447,14 +3447,8 @@ { HRESULT hr; IEThreadParamBlock * parameters = (IEThreadParamBlock *) lpThreadParameter; - INITCOMMONCONTROLSEX iccex = - { - sizeof(iccex), - 0xFFFF /* everything! */ - }; OleInitialize(NULL); - InitCommonControlsEx(&iccex); ATLTRY(hr = ExplorerMessageLoop(parameters)); Modified: branches/shell-experiments/dll/win32/shell32/desktop.cpp URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/dll/win32/she…
============================================================================== --- branches/shell-experiments/dll/win32/shell32/desktop.cpp [iso-8859-1] (original) +++ branches/shell-experiments/dll/win32/shell32/desktop.cpp [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -475,6 +475,11 @@ break; } + case WM_EXPLORER_OPEN_NEW_WINDOW: + DbgPrint("Proxy Desktop message 1035 received.\n"); + SHOnCWMCommandLine((HANDLE)lParam); + break; + default: DefMsgHandler: Ret = DefWindowProcW(hwnd, uMsg, wParam, lParam); Modified: branches/shell-experiments/dll/win32/shell32/undocshell.h URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/dll/win32/she…
============================================================================== --- branches/shell-experiments/dll/win32/shell32/undocshell.h [iso-8859-1] (original) +++ branches/shell-experiments/dll/win32/shell32/undocshell.h [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -127,30 +127,6 @@ DWORD dwType); /**************************************************************************** - * Memory Routines - */ - -/* The Platform SDK's shlobj.h header defines similar functions with a - * leading underscore. However those are unusable because of the leading - * underscore, because they have an incorrect calling convention, and - * because these functions are not exported by name anyway. - */ -HANDLE WINAPI SHAllocShared( - LPVOID pv, - ULONG cb, - DWORD pid); - -BOOL WINAPI SHFreeShared( - HANDLE hMem, - DWORD pid); - -LPVOID WINAPI SHLockShared( - HANDLE hMem, - DWORD pid); - -BOOL WINAPI SHUnlockShared(LPVOID pv); - -/**************************************************************************** * Cabinet Window Messages */ Modified: branches/shell-experiments/dll/win32/shlwapi/ordinal.c URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/dll/win32/shl…
============================================================================== --- branches/shell-experiments/dll/win32/shlwapi/ordinal.c [iso-8859-1] (original) +++ branches/shell-experiments/dll/win32/shlwapi/ordinal.c [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -71,7 +71,7 @@ if (dwDstProcId == dwMyProcId) hDst = GetCurrentProcess(); else - hDst = OpenProcess(PROCESS_DUP_HANDLE, 0, dwDstProcId); + hDst = OpenProcess(PROCESS_DUP_HANDLE, FALSE, dwDstProcId); if (hDst) { @@ -79,12 +79,12 @@ if (dwSrcProcId == dwMyProcId) hSrc = GetCurrentProcess(); else - hSrc = OpenProcess(PROCESS_DUP_HANDLE, 0, dwSrcProcId); + hSrc = OpenProcess(PROCESS_DUP_HANDLE, FALSE, dwSrcProcId); if (hSrc) { /* Make handle available to dest process */ - if (!DuplicateHandle(hDst, hShared, hSrc, &hRet, + if (!DuplicateHandle(hSrc, hShared, hDst, &hRet, dwAccess, 0, dwOptions | DUPLICATE_SAME_ACCESS)) hRet = NULL; @@ -175,18 +175,32 @@ { HANDLE hDup; LPVOID pMapped; + DWORD thisProcessId = GetCurrentProcessId(); TRACE("(%p %d)\n", hShared, dwProcId); - /* Get handle to shared memory for current process */ - hDup = SHLWAPI_DupSharedHandle(hShared, dwProcId, GetCurrentProcessId(), - FILE_MAP_ALL_ACCESS, 0); + if (dwProcId != thisProcessId) + { + /* Get handle to shared memory for current process */ + hDup = SHLWAPI_DupSharedHandle(hShared, dwProcId, GetCurrentProcessId(), + FILE_MAP_ALL_ACCESS, 0); + } + else + { + hDup = hShared; + } + /* Get View */ pMapped = MapViewOfFile(hDup, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, 0); - CloseHandle(hDup); + + if (dwProcId != thisProcessId) + { + CloseHandle(hDup); + } if (pMapped) - return (char *) pMapped + sizeof(DWORD); /* Hide size */ + return (char *) pMapped + sizeof(DWORD); /* Hide size */ + return NULL; } @@ -231,7 +245,7 @@ /* Get a copy of the handle for our process, closing the source handle */ hClose = SHLWAPI_DupSharedHandle(hShared, dwProcId, GetCurrentProcessId(), - FILE_MAP_ALL_ACCESS,DUPLICATE_CLOSE_SOURCE); + FILE_MAP_ALL_ACCESS, DUPLICATE_CLOSE_SOURCE); /* Close local copy */ return CloseHandle(hClose); } Modified: branches/shell-experiments/include/psdk/shlwapi.h URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/include/psdk/…
============================================================================== --- branches/shell-experiments/include/psdk/shlwapi.h [iso-8859-1] (original) +++ branches/shell-experiments/include/psdk/shlwapi.h [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -1863,6 +1863,16 @@ #endif /* NO_SHLWAPI_STREAM */ #ifndef NO_SHLWAPI_SHARED + +// These functions are only included in this file starting with the Windows 7 platform SDK + +HANDLE +WINAPI +SHAllocShared( + _In_opt_ const void *pvData, + _In_ DWORD dwSize, + _In_ DWORD dwDestinationProcessId + ); PVOID WINAPI Modified: branches/shell-experiments/include/psdk/shlwapi_undoc.h URL:
http://svn.reactos.org/svn/reactos/branches/shell-experiments/include/psdk/…
============================================================================== --- branches/shell-experiments/include/psdk/shlwapi_undoc.h [iso-8859-1] (original) +++ branches/shell-experiments/include/psdk/shlwapi_undoc.h [iso-8859-1] Fri Sep 26 14:47:07 2014 @@ -27,40 +27,50 @@ typedef struct IEThreadParamBlock { - long offset0; - long offset4; - long offset8; - IUnknown *offsetC; - long offset10; - IUnknown *offset14; - LPITEMIDLIST directoryPIDL; - char filler1[84]; // unknown contents - IUnknown *offset70; - long filler2; // unknown contents - IUnknown *offset78; - LPITEMIDLIST offset7C; - LPITEMIDLIST offset80; - char filler3[116]; // unknown contents - IUnknown *offsetF8; // instance explorer - long filler4; // unknown contents + long offset0; + DWORD dwFlags; + long offset8; + IUnknown * offsetC; + long offset10; + IUnknown * offset14; + LPITEMIDLIST directoryPIDL; // 0x18 + char offset1C[0x70-0x1C]; // unknown contents -- 0x1C..0x6c + IUnknown * offset70; + long offset74; // unknown contents + IUnknown * offset78; + LPITEMIDLIST offset7C; + LPITEMIDLIST offset80; + LONG offset84; + LONG offset88; + LONG offset8C; + LONG offset90; + LONG offset94; + LONG offset98; + LONG offset9C; + LONG offsetA0; + char offsetA4[0xD8-0xA4]; // unknown contents -- 0xA4..0xD8 + LONG offsetD8; + char offsetDC[0xF8-0xDC]; // unknown contents -- 0xDC..0xF8 + IUnknown * offsetF8; // instance explorer + LONG offsetFC; // unknown contents } IE_THREAD_PARAM_BLOCK, *PIE_THREAD_PARAM_BLOCK; typedef struct ExplorerCommandLineParseResults { - LPWSTR strPath; - LPITEMIDLIST pidlPath; - DWORD dwFlags; - DWORD unk_12; - DWORD unk_16; - DWORD unk_20; - DWORD unk_24; - DWORD unk_28; - LPITEMIDLIST pidlRoot; - DWORD unk_36; - DWORD unk_40; - DWORD unk_44; - DWORD unk_48; - GUID guidInproc; + LPWSTR strPath; + LPITEMIDLIST pidlPath; + DWORD dwFlags; + DWORD offsetC; + DWORD offset10; + DWORD offset14; + DWORD offset18; + DWORD offset1C; + LPITEMIDLIST pidlRoot; + DWORD offset24; + DWORD offset28; + DWORD offset2C; + DWORD offset30; + GUID guidInproc; } EXPLORER_CMDLINE_PARSE_RESULTS, *PEXPLORER_CMDLINE_PARSE_RESULTS; #define SH_EXPLORER_CMDLINE_FLAG_ONE 0x00000001 @@ -81,8 +91,17 @@ // unknown/unused 0x00008000 // unknown/unused 0x00010000 #define SH_EXPLORER_CMDLINE_FLAG_SEPARATE 0x00020000 +// unknown/unused 0x00040000 +// unknown/unused 0x00080000 +// unknown/unused 0x00100000 +// unknown/unused 0x00200000 +// unknown/unused 0x00400000 +// unknown/unused 0x00800000 +// unknown/unused 0x01000000 #define SH_EXPLORER_CMDLINE_FLAG_STRING 0x02000000 +#define WM_EXPLORER_OPEN_NEW_WINDOW (WM_USER+11) +#define WM_EXPLORER_1037 (WM_USER+13) BOOL WINAPI SHAboutInfoA(LPSTR lpszDest, DWORD dwDestLen); BOOL WINAPI SHAboutInfoW(LPWSTR lpszDest, DWORD dwDestLen); @@ -122,9 +141,9 @@ BOOL WINAPI SHIsChildOrSelf(HWND hParent, HWND hChild); void WINAPI InitOCHostClass(long param8); -long WINAPI SHOpenFolderWindow(PIE_THREAD_PARAM_BLOCK param8); +long WINAPI SHOpenFolderWindow(PIE_THREAD_PARAM_BLOCK parameters); void WINAPI SHCreateSavedWindows(void); -long WINAPI SHCreateFromDesktop(long param8); +BOOL WINAPI SHCreateFromDesktop(PEXPLORER_CMDLINE_PARSE_RESULTS parseResults); UINT WINAPI SHExplorerParseCmdLine(PEXPLORER_CMDLINE_PARSE_RESULTS pParseResults); void WINAPI UEMRegisterNotify(long param8, long paramC); HRESULT WINAPI SHCreateBandForPidl(LPCITEMIDLIST param8, IUnknown *paramC, BOOL param10); @@ -134,7 +153,7 @@ PIE_THREAD_PARAM_BLOCK WINAPI SHCloneIETHREADPARAM(PIE_THREAD_PARAM_BLOCK param); long WINAPI SHParseIECommandLine(long param8, long paramC); void WINAPI SHDestroyIETHREADPARAM(PIE_THREAD_PARAM_BLOCK param); -HRESULT WINAPI SHOnCWMCommandLine(long param8); +BOOL WINAPI SHOnCWMCommandLine(HANDLE hSharedInfo); LPITEMIDLIST WINAPI Channel_GetFolderPidl(void); IUnknown *WINAPI ChannelBand_Create(LPITEMIDLIST pidl); HRESULT WINAPI Channels_SetBandInfoSFB(IUnknown *param8); @@ -145,7 +164,7 @@ HRESULT WINAPI SHEnumClassesOfCategories(long param8, long paramC, long param10, long param14, long param18); HRESULT WINAPI SHWriteClassesOfCategories(long param8, long paramC, long param10, long param14, long param18, long param1C, long param20); BOOL WINAPI SHIsExplorerBrowser(); -HRESULT WINAPI SHOpenNewFrame(LPITEMIDLIST pidl, IUnknown *paramC, long param10, long param14); +HRESULT WINAPI SHOpenNewFrame(LPITEMIDLIST pidl, IUnknown *paramC, long param10, DWORD dwFlags); #ifdef __cplusplus } /* extern "C" */
10 years, 3 months
1
0
0
0
[pschweitzer] 64313: [NTFS] - Import structures and defines from FreeLdr NTFS driver header - Import lot of code from FreeLdr NTFS driver to handle MFT & attributes - Remove code that has been over...
by pschweitzer@svn.reactos.org
Author: pschweitzer Date: Fri Sep 26 13:57:29 2014 New Revision: 64313 URL:
http://svn.reactos.org/svn/reactos?rev=64313&view=rev
Log: [NTFS] - Import structures and defines from FreeLdr NTFS driver header - Import lot of code from FreeLdr NTFS driver to handle MFT & attributes - Remove code that has been overtaken by FreeLdr code - Adapt & port code from FreeLdr (allocation, status, data structures) - Adapt old code to the new functions defined from FreeLdr code - Open the MFT during volume mount and keep in VCB for further use - Implement a function to lookup a file in the MFT given its full path Modified: trunk/reactos/drivers/filesystems/ntfs/attrib.c trunk/reactos/drivers/filesystems/ntfs/fsctl.c trunk/reactos/drivers/filesystems/ntfs/mft.c trunk/reactos/drivers/filesystems/ntfs/ntfs.h Modified: trunk/reactos/drivers/filesystems/ntfs/attrib.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/a…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/attrib.c [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/attrib.c [iso-8859-1] Fri Sep 26 13:57:29 2014 @@ -33,127 +33,106 @@ /* FUNCTIONS ****************************************************************/ -static -ULONG -RunLength(PUCHAR run) -{ - return(*run & 0x0f) + ((*run >> 4) & 0x0f) + 1; -} - - -static -LONGLONG -RunLCN(PUCHAR run) -{ - UCHAR n1 = *run & 0x0f; - UCHAR n2 = (*run >> 4) & 0x0f; - LONGLONG lcn = (n2 == 0) ? 0 : (CHAR)(run[n1 + n2]); - LONG i = 0; - - for (i = n1 +n2 - 1; i > n1; i--) - lcn = (lcn << 8) + run[i]; - return lcn; -} - - -static -ULONGLONG -RunCount(PUCHAR run) -{ - UCHAR n = *run & 0xf; - ULONGLONG count = 0; - ULONG i = 0; - - for (i = n; i > 0; i--) - count = (count << 8) + run[i]; - return count; -} - +PUCHAR +DecodeRun(PUCHAR DataRun, + LONGLONG *DataRunOffset, + ULONGLONG *DataRunLength) +{ + UCHAR DataRunOffsetSize; + UCHAR DataRunLengthSize; + CHAR i; + + DataRunOffsetSize = (*DataRun >> 4) & 0xF; + DataRunLengthSize = *DataRun & 0xF; + *DataRunOffset = 0; + *DataRunLength = 0; + DataRun++; + for (i = 0; i < DataRunLengthSize; i++) + { + *DataRunLength += ((ULONG64)*DataRun) << (i * 8); + DataRun++; + } + + /* NTFS 3+ sparse files */ + if (DataRunOffsetSize == 0) + { + *DataRunOffset = -1; + } + else + { + for (i = 0; i < DataRunOffsetSize - 1; i++) + { + *DataRunOffset += ((ULONG64)*DataRun) << (i * 8); + DataRun++; + } + /* The last byte contains sign so we must process it different way. */ + *DataRunOffset = ((LONG64)(CHAR)(*(DataRun++)) << (i * 8)) + *DataRunOffset; + } + + DPRINT("DataRunOffsetSize: %x\n", DataRunOffsetSize); + DPRINT("DataRunLengthSize: %x\n", DataRunLengthSize); + DPRINT("DataRunOffset: %x\n", *DataRunOffset); + DPRINT("DataRunLength: %x\n", *DataRunLength); + + return DataRun; +} BOOLEAN -FindRun(PNONRESIDENT_ATTRIBUTE NresAttr, +FindRun(PNTFS_ATTR_RECORD NresAttr, ULONGLONG vcn, PULONGLONG lcn, PULONGLONG count) { - PUCHAR run; - ULONGLONG base = NresAttr->StartVcn; - - if (vcn < NresAttr->StartVcn || vcn > NresAttr->LastVcn) + if (vcn < NresAttr->NonResident.LowestVCN || vcn > NresAttr->NonResident.HighestVCN) return FALSE; - *lcn = 0; - - for (run = (PUCHAR)((ULONG_PTR)NresAttr + NresAttr->RunArrayOffset); - *run != 0; run += RunLength(run)) - { - *lcn += RunLCN(run); - *count = RunCount(run); - - if (base <= vcn && vcn < base + *count) - { - *lcn = (RunLCN(run) == 0) ? 0 : *lcn + vcn - base; - *count -= (ULONG)(vcn - base); - - return TRUE; - } - else - { - base += *count; - } - } - - return FALSE; -} - - -static -VOID -NtfsDumpFileNameAttribute(PATTRIBUTE Attribute) -{ - PRESIDENT_ATTRIBUTE ResAttr; + DecodeRun((PUCHAR)((ULONG_PTR)NresAttr + NresAttr->NonResident.MappingPairsOffset), (PLONGLONG)lcn, count); + + return TRUE; +} + + +static +VOID +NtfsDumpFileNameAttribute(PNTFS_ATTR_RECORD Attribute) +{ PFILENAME_ATTRIBUTE FileNameAttr; DbgPrint(" $FILE_NAME "); - ResAttr = (PRESIDENT_ATTRIBUTE)Attribute; -// DbgPrint(" Length %lu Offset %hu ", ResAttr->ValueLength, ResAttr->ValueOffset); - - FileNameAttr = (PFILENAME_ATTRIBUTE)((ULONG_PTR)ResAttr + ResAttr->ValueOffset); +// DbgPrint(" Length %lu Offset %hu ", Attribute->Resident.ValueLength, Attribute->Resident.ValueOffset); + + FileNameAttr = (PFILENAME_ATTRIBUTE)((ULONG_PTR)Attribute + Attribute->Resident.ValueOffset); DbgPrint(" '%.*S' ", FileNameAttr->NameLength, FileNameAttr->Name); } static VOID -NtfsDumpVolumeNameAttribute(PATTRIBUTE Attribute) -{ - PRESIDENT_ATTRIBUTE ResAttr; +NtfsDumpVolumeNameAttribute(PNTFS_ATTR_RECORD Attribute) +{ PWCHAR VolumeName; DbgPrint(" $VOLUME_NAME "); - ResAttr = (PRESIDENT_ATTRIBUTE)Attribute; -// DbgPrint(" Length %lu Offset %hu ", ResAttr->ValueLength, ResAttr->ValueOffset); - - VolumeName = (PWCHAR)((ULONG_PTR)ResAttr + ResAttr->ValueOffset); - DbgPrint(" '%.*S' ", ResAttr->ValueLength / sizeof(WCHAR), VolumeName); -} - - -static -VOID -NtfsDumpVolumeInformationAttribute(PATTRIBUTE Attribute) -{ - PRESIDENT_ATTRIBUTE ResAttr; +// DbgPrint(" Length %lu Offset %hu ", Attribute->Resident.ValueLength, Attribute->Resident.ValueOffset); + + VolumeName = (PWCHAR)((ULONG_PTR)Attribute + Attribute->Resident.ValueOffset); + DbgPrint(" '%.*S' ", Attribute->Resident.ValueLength / sizeof(WCHAR), VolumeName); +} + + +static +VOID +NtfsDumpVolumeInformationAttribute(PNTFS_ATTR_RECORD Attribute) +{ PVOLINFO_ATTRIBUTE VolInfoAttr; DbgPrint(" $VOLUME_INFORMATION "); - ResAttr = (PRESIDENT_ATTRIBUTE)Attribute; -// DbgPrint(" Length %lu Offset %hu ", ResAttr->ValueLength, ResAttr->ValueOffset); - - VolInfoAttr = (PVOLINFO_ATTRIBUTE)((ULONG_PTR)ResAttr + ResAttr->ValueOffset); +// DbgPrint(" Length %lu Offset %hu ", Attribute->Resident.ValueLength, Attribute->Resident.ValueOffset); + + VolInfoAttr = (PVOLINFO_ATTRIBUTE)((ULONG_PTR)Attribute + Attribute->Resident.ValueOffset); DbgPrint(" NTFS Version %u.%u Flags 0x%04hx ", VolInfoAttr->MajorVersion, VolInfoAttr->MinorVersion, @@ -163,13 +142,11 @@ static VOID -NtfsDumpIndexRootAttribute(PATTRIBUTE Attribute) -{ - PRESIDENT_ATTRIBUTE ResAttr; +NtfsDumpIndexRootAttribute(PNTFS_ATTR_RECORD Attribute) +{ PINDEX_ROOT_ATTRIBUTE IndexRootAttr; - ResAttr = (PRESIDENT_ATTRIBUTE)Attribute; - IndexRootAttr = (PINDEX_ROOT_ATTRIBUTE)((ULONG_PTR)ResAttr + ResAttr->ValueOffset); + IndexRootAttr = (PINDEX_ROOT_ATTRIBUTE)((ULONG_PTR)Attribute + Attribute->Resident.ValueOffset); if (IndexRootAttr->AttributeType == AttributeFileName) ASSERT(IndexRootAttr->CollationRule == COLLATION_FILE_NAME); @@ -190,15 +167,14 @@ static VOID -NtfsDumpAttribute (PATTRIBUTE Attribute) -{ - PNONRESIDENT_ATTRIBUTE NresAttr; +NtfsDumpAttribute(PNTFS_ATTR_RECORD Attribute) +{ UNICODE_STRING Name; ULONGLONG lcn = 0; ULONGLONG runcount = 0; - switch (Attribute->AttributeType) + switch (Attribute->Type) { case AttributeFileName: NtfsDumpFileNameAttribute(Attribute); @@ -267,7 +243,7 @@ default: DbgPrint(" Attribute %lx ", - Attribute->AttributeType); + Attribute->Type); break; } @@ -281,16 +257,14 @@ } DbgPrint("(%s)\n", - Attribute->Nonresident ? "non-resident" : "resident"); - - if (Attribute->Nonresident) - { - NresAttr = (PNONRESIDENT_ATTRIBUTE)Attribute; - - FindRun(NresAttr,0,&lcn, &runcount); + Attribute->IsNonResident ? "non-resident" : "resident"); + + if (Attribute->IsNonResident) + { + FindRun(Attribute,0,&lcn, &runcount); DbgPrint(" AllocatedSize %I64u DataSize %I64u\n", - NresAttr->AllocatedSize, NresAttr->DataSize); + Attribute->NonResident.AllocatedSize, Attribute->NonResident.DataSize); DbgPrint(" logical clusters: %I64u - %I64u\n", lcn, lcn + runcount - 1); } @@ -300,15 +274,15 @@ VOID NtfsDumpFileAttributes(PFILE_RECORD_HEADER FileRecord) { - PATTRIBUTE Attribute; - - Attribute = (PATTRIBUTE)((ULONG_PTR)FileRecord + FileRecord->AttributeOffset); - while (Attribute < (PATTRIBUTE)((ULONG_PTR)FileRecord + FileRecord->BytesInUse) && - Attribute->AttributeType != (ATTRIBUTE_TYPE)-1) + PNTFS_ATTR_RECORD Attribute; + + Attribute = (PNTFS_ATTR_RECORD)((ULONG_PTR)FileRecord + FileRecord->AttributeOffset); + while (Attribute < (PNTFS_ATTR_RECORD)((ULONG_PTR)FileRecord + FileRecord->BytesInUse) && + Attribute->Type != (ATTRIBUTE_TYPE)-1) { NtfsDumpAttribute(Attribute); - Attribute = (PATTRIBUTE)((ULONG_PTR)Attribute + Attribute->Length); + Attribute = (PNTFS_ATTR_RECORD)((ULONG_PTR)Attribute + Attribute->Length); } } Modified: trunk/reactos/drivers/filesystems/ntfs/fsctl.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/f…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/fsctl.c [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/fsctl.c [iso-8859-1] Fri Sep 26 13:57:29 2014 @@ -34,6 +34,8 @@ #define NDEBUG #include <debug.h> +UNICODE_STRING EmptyName = RTL_CONSTANT_STRING(L""); + /* FUNCTIONS ****************************************************************/ /* @@ -173,14 +175,14 @@ PDEVICE_EXTENSION DeviceExt) { DISK_GEOMETRY DiskGeometry; - PFILE_RECORD_HEADER MftRecord; PFILE_RECORD_HEADER VolumeRecord; PVOLINFO_ATTRIBUTE VolumeInfo; PBOOT_SECTOR BootSector; - PATTRIBUTE Attribute; ULONG Size; PNTFS_INFO NtfsInfo = &DeviceExt->NtfsInfo; NTSTATUS Status; + PNTFS_ATTR_CONTEXT AttrCtxt; + PNTFS_ATTR_RECORD Attribute; PNTFS_FCB VolumeFcb; PWSTR VolumeNameU; @@ -251,10 +253,10 @@ ExFreePool(BootSector); - MftRecord = ExAllocatePoolWithTag(NonPagedPool, - NtfsInfo->BytesPerFileRecord, - TAG_NTFS); - if (MftRecord == NULL) + DeviceExt->MasterFileTable = ExAllocatePoolWithTag(NonPagedPool, + NtfsInfo->BytesPerFileRecord, + TAG_NTFS); + if (DeviceExt->MasterFileTable == NULL) { return STATUS_INSUFFICIENT_RESOURCES; } @@ -263,11 +265,20 @@ NtfsInfo->MftStart.u.LowPart * NtfsInfo->SectorsPerCluster, NtfsInfo->BytesPerFileRecord / NtfsInfo->BytesPerSector, NtfsInfo->BytesPerSector, - (PVOID)MftRecord, + (PVOID)DeviceExt->MasterFileTable, TRUE); if (!NT_SUCCESS(Status)) { - ExFreePool(MftRecord); + DPRINT1("Failed reading MFT.\n"); + ExFreePool(DeviceExt->MasterFileTable); + return Status; + } + + Status = FindAttribute(DeviceExt, DeviceExt->MasterFileTable, AttributeData, &EmptyName, &DeviceExt->MFTContext); + if (!NT_SUCCESS(Status)) + { + DPRINT1("Can't find data attribute for Master File Table.\n"); + ExFreePool(DeviceExt->MasterFileTable); return Status; } @@ -276,40 +287,41 @@ TAG_NTFS); if (VolumeRecord == NULL) { - ExFreePool(MftRecord); + DPRINT1("Allocation failed for volume record\n"); + ExFreePool(DeviceExt->MasterFileTable); return STATUS_INSUFFICIENT_RESOURCES; } /* Read Volume File (MFT index 3) */ DeviceExt->StorageDevice = DeviceObject; Status = ReadFileRecord(DeviceExt, - 3, - VolumeRecord, - MftRecord); - if (!NT_SUCCESS(Status)) - { + NTFS_FILE_VOLUME, + VolumeRecord); + if (!NT_SUCCESS(Status)) + { + DPRINT1("Failed reading volume file\n"); ExFreePool(VolumeRecord); - ExFreePool(MftRecord); + ExFreePool(DeviceExt->MasterFileTable); return Status; } /* Enumerate attributes */ - NtfsDumpFileAttributes (MftRecord); + NtfsDumpFileAttributes(DeviceExt->MasterFileTable); /* Enumerate attributes */ - NtfsDumpFileAttributes (VolumeRecord); + NtfsDumpFileAttributes(VolumeRecord); /* Get volume name */ - Attribute = FindAttribute (VolumeRecord, AttributeVolumeName, NULL); - DPRINT("Attribute %p\n", Attribute); - - if (Attribute != NULL && ((PRESIDENT_ATTRIBUTE)Attribute)->ValueLength != 0) - { - DPRINT("Data length %lu\n", AttributeDataLength (Attribute)); + Status = FindAttribute(DeviceExt, VolumeRecord, AttributeVolumeName, &EmptyName, &AttrCtxt); + + if (NT_SUCCESS(Status) && AttrCtxt->Record.Resident.ValueLength != 0) + { + Attribute = &AttrCtxt->Record; + DPRINT("Data length %lu\n", AttributeDataLength(Attribute)); NtfsInfo->VolumeLabelLength = - min (((PRESIDENT_ATTRIBUTE)Attribute)->ValueLength, MAXIMUM_VOLUME_LABEL_LENGTH); + min (Attribute->Resident.ValueLength, MAXIMUM_VOLUME_LABEL_LENGTH); RtlCopyMemory(NtfsInfo->VolumeLabel, - (PVOID)((ULONG_PTR)Attribute + ((PRESIDENT_ATTRIBUTE)Attribute)->ValueOffset), + (PVOID)((ULONG_PTR)Attribute + Attribute->Resident.ValueOffset), NtfsInfo->VolumeLabelLength); VolumeNameU = NtfsInfo->VolumeLabel; } @@ -322,8 +334,9 @@ VolumeFcb = NtfsCreateFCB(VolumeNameU, DeviceExt); if (VolumeFcb == NULL) { + DPRINT1("Failed allocating volume FCB\n"); ExFreePool(VolumeRecord); - ExFreePool(MftRecord); + ExFreePool(DeviceExt->MasterFileTable); return STATUS_INSUFFICIENT_RESOURCES; } @@ -334,20 +347,19 @@ DeviceExt->VolumeFcb = VolumeFcb; /* Get volume information */ - Attribute = FindAttribute (VolumeRecord, AttributeVolumeInformation, NULL); - DPRINT("Attribute %p\n", Attribute); - - if (Attribute != NULL && ((PRESIDENT_ATTRIBUTE)Attribute)->ValueLength != 0) - { + Status = FindAttribute(DeviceExt, VolumeRecord, AttributeVolumeInformation, &EmptyName, &AttrCtxt); + + if (NT_SUCCESS(Status) && AttrCtxt->Record.Resident.ValueLength != 0) + { + Attribute = &AttrCtxt->Record; DPRINT("Data length %lu\n", AttributeDataLength (Attribute)); - VolumeInfo = (PVOID)((ULONG_PTR)Attribute + ((PRESIDENT_ATTRIBUTE)Attribute)->ValueOffset); + VolumeInfo = (PVOID)((ULONG_PTR)Attribute + Attribute->Resident.ValueOffset); NtfsInfo->MajorVersion = VolumeInfo->MajorVersion; NtfsInfo->MinorVersion = VolumeInfo->MinorVersion; NtfsInfo->Flags = VolumeInfo->Flags; } - ExFreePool(MftRecord); ExFreePool(VolumeRecord); return Status; Modified: trunk/reactos/drivers/filesystems/ntfs/mft.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/m…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/mft.c [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/mft.c [iso-8859-1] Fri Sep 26 13:57:29 2014 @@ -31,277 +31,413 @@ #define NDEBUG #include <debug.h> +UNICODE_STRING IndexOfFileNames = RTL_CONSTANT_STRING(L"$I30"); + /* FUNCTIONS ****************************************************************/ +PNTFS_ATTR_CONTEXT +PrepareAttributeContext(PNTFS_ATTR_RECORD AttrRecord) +{ + PNTFS_ATTR_CONTEXT Context; + + Context = ExAllocatePoolWithTag(NonPagedPool, + FIELD_OFFSET(NTFS_ATTR_CONTEXT, Record) + AttrRecord->Length, + TAG_NTFS); + RtlCopyMemory(&Context->Record, AttrRecord, AttrRecord->Length); + if (AttrRecord->IsNonResident) + { + LONGLONG DataRunOffset; + ULONGLONG DataRunLength; + + Context->CacheRun = (PUCHAR)&Context->Record + Context->Record.NonResident.MappingPairsOffset; + Context->CacheRunOffset = 0; + Context->CacheRun = DecodeRun(Context->CacheRun, &DataRunOffset, &DataRunLength); + Context->CacheRunLength = DataRunLength; + if (DataRunOffset != -1) + { + /* Normal run. */ + Context->CacheRunStartLCN = + Context->CacheRunLastLCN = DataRunOffset; + } + else + { + /* Sparse run. */ + Context->CacheRunStartLCN = -1; + Context->CacheRunLastLCN = 0; + } + Context->CacheRunCurrentOffset = 0; + } + + return Context; +} + + +VOID +ReleaseAttributeContext(PNTFS_ATTR_CONTEXT Context) +{ + ExFreePoolWithTag(Context, TAG_NTFS); +} + + +PNTFS_ATTR_CONTEXT +FindAttributeHelper(PDEVICE_EXTENSION Vcb, + PNTFS_ATTR_RECORD AttrRecord, + PNTFS_ATTR_RECORD AttrRecordEnd, + ULONG Type, + const WCHAR *Name, + ULONG NameLength) +{ + DPRINT("FindAttributeHelper(%p, %p, %p, 0x%x, %s, %u)\n", Vcb, AttrRecord, AttrRecordEnd, Type, Name, NameLength); + + while (AttrRecord < AttrRecordEnd) + { + DPRINT("AttrRecord->Type = 0x%x\n", AttrRecord->Type); + + if (AttrRecord->Type == AttributeEnd) + break; + + if (AttrRecord->Type == AttributeAttributeList) + { + PNTFS_ATTR_CONTEXT Context; + PNTFS_ATTR_CONTEXT ListContext; + PVOID ListBuffer; + ULONGLONG ListSize; + PNTFS_ATTR_RECORD ListAttrRecord; + PNTFS_ATTR_RECORD ListAttrRecordEnd; + + // Do not handle non-resident yet + ASSERT(!(AttrRecord->IsNonResident & 1)); + + ListContext = PrepareAttributeContext(AttrRecord); + + ListSize = AttributeDataLength(&ListContext->Record); + if(ListSize <= 0xFFFFFFFF) + ListBuffer = ExAllocatePoolWithTag(NonPagedPool, (ULONG)ListSize, TAG_NTFS); + else + ListBuffer = NULL; + + if(!ListBuffer) + { + DPRINT("Failed to allocate memory: %x\n", (ULONG)ListSize); + continue; + } + + ListAttrRecord = (PNTFS_ATTR_RECORD)ListBuffer; + ListAttrRecordEnd = (PNTFS_ATTR_RECORD)((PCHAR)ListBuffer + ListSize); + + if (ReadAttribute(Vcb, ListContext, 0, ListBuffer, (ULONG)ListSize) == ListSize) + { + Context = FindAttributeHelper(Vcb, ListAttrRecord, ListAttrRecordEnd, + Type, Name, NameLength); + + ReleaseAttributeContext(ListContext); + ExFreePoolWithTag(ListBuffer, TAG_NTFS); + + if (Context != NULL) + { + DPRINT("Found context = %p\n", Context); + return Context; + } + } + } + + if (AttrRecord->Type == Type) + { + DPRINT("%d, %d\n", AttrRecord->NameLength, NameLength); + if (AttrRecord->NameLength == NameLength) + { + PWCHAR AttrName; + + AttrName = (PWCHAR)((PCHAR)AttrRecord + AttrRecord->NameOffset); + DPRINT("%s, %s\n", AttrName, Name); + if (RtlCompareMemory(AttrName, Name, NameLength << 1) == (NameLength << 1)) + { + /* Found it, fill up the context and return. */ + DPRINT("Found context\n"); + return PrepareAttributeContext(AttrRecord); + } + } + } + + if (AttrRecord->Length == 0) + { + DPRINT("Null length attribute record\n"); + return NULL; + } + AttrRecord = (PNTFS_ATTR_RECORD)((PCHAR)AttrRecord + AttrRecord->Length); + } + + DPRINT("Ended\n"); + return NULL; +} + + NTSTATUS -NtfsOpenMft(PDEVICE_EXTENSION Vcb) -{ -// PVOID Bitmap; - PFILE_RECORD_HEADER MftRecord; - PFILE_RECORD_HEADER FileRecord; -// PATTRIBUTE Attribute; -// PATTRIBUTE AttrData; -// PRESIDENT_ATTRIBUTE ResAttr; - +FindAttribute(PDEVICE_EXTENSION Vcb, + PFILE_RECORD_HEADER MftRecord, + ULONG Type, + PUNICODE_STRING Name, + PNTFS_ATTR_CONTEXT * AttrCtx) +{ + PNTFS_ATTR_RECORD AttrRecord; + PNTFS_ATTR_RECORD AttrRecordEnd; + + DPRINT("NtfsFindAttribute(%p, %p, %u, %s)\n", Vcb, MftRecord, Type, Name); + + AttrRecord = (PNTFS_ATTR_RECORD)((PCHAR)MftRecord + MftRecord->AttributeOffset); + AttrRecordEnd = (PNTFS_ATTR_RECORD)((PCHAR)MftRecord + Vcb->NtfsInfo.BytesPerFileRecord); + + *AttrCtx = FindAttributeHelper(Vcb, AttrRecord, AttrRecordEnd, Type, Name->Buffer, Name->Length); + if (*AttrCtx == NULL) + { + return STATUS_OBJECT_NAME_NOT_FOUND; + } + + return STATUS_SUCCESS; +} + + +ULONG +AttributeAllocatedLength(PNTFS_ATTR_RECORD AttrRecord) +{ + if (AttrRecord->IsNonResident) + return AttrRecord->NonResident.AllocatedSize; + else + return AttrRecord->Resident.ValueLength; +} + + +ULONGLONG +AttributeDataLength(PNTFS_ATTR_RECORD AttrRecord) +{ + if (AttrRecord->IsNonResident) + return AttrRecord->NonResident.DataSize; + else + return AttrRecord->Resident.ValueLength; +} + + +ULONG +ReadAttribute(PDEVICE_EXTENSION Vcb, + PNTFS_ATTR_CONTEXT Context, + ULONGLONG Offset, + PCHAR Buffer, + ULONG Length) +{ + ULONGLONG LastLCN; + PUCHAR DataRun; + LONGLONG DataRunOffset; + ULONGLONG DataRunLength; + LONGLONG DataRunStartLCN; + ULONGLONG CurrentOffset; + ULONG ReadLength; + ULONG AlreadyRead; NTSTATUS Status; - ULONG BytesPerFileRecord; - ULONG n; - ULONG i; - - DPRINT1("NtfsOpenMft() called\n"); - - BytesPerFileRecord = Vcb->NtfsInfo.BytesPerFileRecord; - - MftRecord = ExAllocatePoolWithTag(NonPagedPool, - BytesPerFileRecord, - TAG_NTFS); - if (MftRecord == NULL) - { - return STATUS_INSUFFICIENT_RESOURCES; - } - - Status = NtfsReadSectors(Vcb->StorageDevice, - Vcb->NtfsInfo.MftStart.u.LowPart * Vcb->NtfsInfo.SectorsPerCluster, - BytesPerFileRecord / Vcb->NtfsInfo.BytesPerSector, - Vcb->NtfsInfo.BytesPerSector, - (PVOID)MftRecord, - FALSE); - if (!NT_SUCCESS(Status)) - { - ExFreePool(MftRecord); - return Status; - } - - FixupUpdateSequenceArray(MftRecord); - -// Attribute = FindAttribute(MftRecord, AttributeBitmap, 0); - - /* Get number of file records*/ - n = AttributeDataLength(FindAttribute(MftRecord, AttributeData, 0)) / BytesPerFileRecord; - - FileRecord = ExAllocatePoolWithTag(NonPagedPool, - BytesPerFileRecord, - TAG_NTFS); - if (FileRecord == NULL) - { - ExFreePool(MftRecord); - return STATUS_INSUFFICIENT_RESOURCES; - } - - /* Enumerate MFT Records */ - DPRINT("Enumerate MFT records\n"); - for (i = 0; i < n; i++) - { - ReadFileRecord(Vcb, - i, - FileRecord, - MftRecord); - - if (FileRecord->Ntfs.Type == NRH_FILE_TYPE && - (FileRecord->Flags & FRH_IN_USE)) - { - DPRINT("\nFile %lu\n\n", i); - - /* Enumerate attributtes */ - NtfsDumpFileAttributes (FileRecord); - DbgPrint("\n\n"); - } - } - - ExFreePool(FileRecord); - ExFreePool(MftRecord); - - return Status; -} - - -PATTRIBUTE -FindAttribute(PFILE_RECORD_HEADER FileRecord, - ATTRIBUTE_TYPE Type, - PWSTR name) -{ - PATTRIBUTE Attribute; - - UNREFERENCED_PARAMETER(name); - - Attribute = (PATTRIBUTE)((ULONG_PTR)FileRecord + FileRecord->AttributeOffset); - while (Attribute < (PATTRIBUTE)((ULONG_PTR)FileRecord + FileRecord->BytesInUse) && - Attribute->AttributeType != (ATTRIBUTE_TYPE)-1) - { - if (Attribute->AttributeType == Type) - { - return Attribute; - } - - Attribute = (PATTRIBUTE)((ULONG_PTR)Attribute + Attribute->Length); - } - - return NULL; -} - - -ULONG -AttributeAllocatedLength(PATTRIBUTE Attribute) -{ - if (Attribute->Nonresident) - { - return ((PNONRESIDENT_ATTRIBUTE)Attribute)->AllocatedSize; - } - - return ((PRESIDENT_ATTRIBUTE)Attribute)->ValueLength; -} - - -ULONG -AttributeDataLength(PATTRIBUTE Attribute) -{ - if (Attribute->Nonresident) - { - return ((PNONRESIDENT_ATTRIBUTE)Attribute)->DataSize; - } - - return ((PRESIDENT_ATTRIBUTE)Attribute)->ValueLength; -} - - -VOID -ReadAttribute(PATTRIBUTE attr, - PVOID buffer, - PDEVICE_EXTENSION Vcb, - PDEVICE_OBJECT DeviceObject) -{ - PNONRESIDENT_ATTRIBUTE NresAttr = (PNONRESIDENT_ATTRIBUTE)attr; - - UNREFERENCED_PARAMETER(DeviceObject); - - if (attr->Nonresident == FALSE) - { - memcpy(buffer, - (PVOID)((ULONG_PTR)attr + ((PRESIDENT_ATTRIBUTE)attr)->ValueOffset), - ((PRESIDENT_ATTRIBUTE)attr)->ValueLength); - } - - ReadExternalAttribute(Vcb, - NresAttr, - 0, - (ULONG)(NresAttr->LastVcn) + 1, - buffer); + + if (!Context->Record.IsNonResident) + { + if (Offset > Context->Record.Resident.ValueLength) + return 0; + if (Offset + Length > Context->Record.Resident.ValueLength) + Length = (ULONG)(Context->Record.Resident.ValueLength - Offset); + RtlCopyMemory(Buffer, (PCHAR)&Context->Record + Context->Record.Resident.ValueOffset + Offset, Length); + return Length; + } + + /* + * Non-resident attribute + */ + + /* + * I. Find the corresponding start data run. + */ + + AlreadyRead = 0; + + // FIXME: Cache seems to be non-working. Disable it for now + //if(Context->CacheRunOffset <= Offset && Offset < Context->CacheRunOffset + Context->CacheRunLength * Volume->ClusterSize) + if (0) + { + DataRun = Context->CacheRun; + LastLCN = Context->CacheRunLastLCN; + DataRunStartLCN = Context->CacheRunStartLCN; + DataRunLength = Context->CacheRunLength; + CurrentOffset = Context->CacheRunCurrentOffset; + } + else + { + LastLCN = 0; + DataRun = (PUCHAR)&Context->Record + Context->Record.NonResident.MappingPairsOffset; + CurrentOffset = 0; + + while (1) + { + DataRun = DecodeRun(DataRun, &DataRunOffset, &DataRunLength); + if (DataRunOffset != -1) + { + /* Normal data run. */ + DataRunStartLCN = LastLCN + DataRunOffset; + LastLCN = DataRunStartLCN; + } + else + { + /* Sparse data run. */ + DataRunStartLCN = -1; + } + + if (Offset >= CurrentOffset && + Offset < CurrentOffset + (DataRunLength * Vcb->NtfsInfo.BytesPerCluster)) + { + break; + } + + if (*DataRun == 0) + { + return AlreadyRead; + } + + CurrentOffset += DataRunLength * Vcb->NtfsInfo.BytesPerCluster; + } + } + + /* + * II. Go through the run list and read the data + */ + + ReadLength = (ULONG)min(DataRunLength * Vcb->NtfsInfo.BytesPerCluster - (Offset - CurrentOffset), Length); + if (DataRunStartLCN == -1) + RtlZeroMemory(Buffer, ReadLength); + Status = NtfsReadDisk(Vcb->StorageDevice, + DataRunStartLCN * Vcb->NtfsInfo.BytesPerCluster + Offset - CurrentOffset, + ReadLength, + (PVOID)Buffer, + FALSE); + if (NT_SUCCESS(Status)) + { + Length -= ReadLength; + Buffer += ReadLength; + AlreadyRead += ReadLength; + + if (ReadLength == DataRunLength * Vcb->NtfsInfo.BytesPerCluster - (Offset - CurrentOffset)) + { + CurrentOffset += DataRunLength * Vcb->NtfsInfo.BytesPerCluster; + DataRun = DecodeRun(DataRun, &DataRunOffset, &DataRunLength); + if (DataRunLength != (ULONGLONG)-1) + { + DataRunStartLCN = LastLCN + DataRunOffset; + LastLCN = DataRunStartLCN; + } + else + DataRunStartLCN = -1; + + if (*DataRun == 0) + return AlreadyRead; + } + + while (Length > 0) + { + ReadLength = (ULONG)min(DataRunLength * Vcb->NtfsInfo.BytesPerCluster, Length); + if (DataRunStartLCN == -1) + RtlZeroMemory(Buffer, ReadLength); + else + { + Status = NtfsReadDisk(Vcb->StorageDevice, + DataRunStartLCN * Vcb->NtfsInfo.BytesPerCluster, + ReadLength, + (PVOID)Buffer, + FALSE); + if (!NT_SUCCESS(Status)) + break; + } + + Length -= ReadLength; + Buffer += ReadLength; + AlreadyRead += ReadLength; + + /* We finished this request, but there still data in this data run. */ + if (Length == 0 && ReadLength != DataRunLength * Vcb->NtfsInfo.BytesPerCluster) + break; + + /* + * Go to next run in the list. + */ + + if (*DataRun == 0) + break; + CurrentOffset += DataRunLength * Vcb->NtfsInfo.BytesPerCluster; + DataRun = DecodeRun(DataRun, &DataRunOffset, &DataRunLength); + if (DataRunOffset != -1) + { + /* Normal data run. */ + DataRunStartLCN = LastLCN + DataRunOffset; + LastLCN = DataRunStartLCN; + } + else + { + /* Sparse data run. */ + DataRunStartLCN = -1; + } + } /* while */ + + } /* if Disk */ + + Context->CacheRun = DataRun; + Context->CacheRunOffset = Offset + AlreadyRead; + Context->CacheRunStartLCN = DataRunStartLCN; + Context->CacheRunLength = DataRunLength; + Context->CacheRunLastLCN = LastLCN; + Context->CacheRunCurrentOffset = CurrentOffset; + + return AlreadyRead; } NTSTATUS ReadFileRecord(PDEVICE_EXTENSION Vcb, - ULONG index, - PFILE_RECORD_HEADER file, - PFILE_RECORD_HEADER Mft) -{ - PVOID p; - ULONG BytesPerFileRecord = Vcb->NtfsInfo.BytesPerFileRecord; - ULONG clusters = max(BytesPerFileRecord / Vcb->NtfsInfo.BytesPerCluster, 1); - ULONGLONG vcn = index * BytesPerFileRecord / Vcb->NtfsInfo.BytesPerCluster; - LONG m = (Vcb->NtfsInfo.BytesPerCluster / BytesPerFileRecord) - 1; - ULONG n = m > 0 ? (index & m) : 0; - - p = ExAllocatePoolWithTag(NonPagedPool, - clusters * Vcb->NtfsInfo.BytesPerCluster, - TAG_NTFS); - - ReadVCN (Vcb, Mft, AttributeData, vcn, clusters, p); - - memcpy(file, - (PVOID)((ULONG_PTR)p + n * BytesPerFileRecord), - BytesPerFileRecord); - - ExFreePool(p); - - FixupUpdateSequenceArray(file); + ULONGLONG index, + PFILE_RECORD_HEADER file) +{ + ULONGLONG BytesRead; + + BytesRead = ReadAttribute(Vcb, Vcb->MFTContext, index * Vcb->NtfsInfo.BytesPerFileRecord, (PCHAR)file, Vcb->NtfsInfo.BytesPerFileRecord); + if (BytesRead != Vcb->NtfsInfo.BytesPerFileRecord) + { + DPRINT1("ReadFileRecord failed: %u read, %u expected\n", BytesRead, Vcb->NtfsInfo.BytesPerFileRecord); + return STATUS_PARTIAL_COPY; + } + + /* Apply update sequence array fixups. */ + return FixupUpdateSequenceArray(Vcb, &file->Ntfs); +} + + +NTSTATUS +FixupUpdateSequenceArray(PDEVICE_EXTENSION Vcb, + PNTFS_RECORD_HEADER Record) +{ + USHORT *USA; + USHORT USANumber; + USHORT USACount; + USHORT *Block; + + USA = (USHORT*)((PCHAR)Record + Record->UsaOffset); + USANumber = *(USA++); + USACount = Record->UsaCount - 1; /* Exclude the USA Number. */ + Block = (USHORT*)((PCHAR)Record + Vcb->NtfsInfo.BytesPerSector - 2); + + while (USACount) + { + if (*Block != USANumber) + { + DPRINT1("Mismatch with USA: %u read, %u expected\n" , *Block, USANumber); + return STATUS_UNSUCCESSFUL; + } + *Block = *(USA++); + Block = (USHORT*)((PCHAR)Block + Vcb->NtfsInfo.BytesPerSector); + USACount--; + } return STATUS_SUCCESS; -} - - -VOID -ReadExternalAttribute(PDEVICE_EXTENSION Vcb, - PNONRESIDENT_ATTRIBUTE NresAttr, - ULONGLONG vcn, - ULONG count, - PVOID buffer) -{ - ULONGLONG lcn; - ULONGLONG runcount; - ULONG readcount; - ULONG left; - ULONG n; - - PUCHAR bytes = (PUCHAR)buffer; - - for (left = count; left > 0; left -= readcount) - { - FindRun(NresAttr, vcn, &lcn, &runcount); - -// readcount = (ULONG)(__min(runcount, left)); - readcount = (ULONG)min(runcount, left); - - - n = readcount * Vcb->NtfsInfo.BytesPerCluster; - - if (lcn == 0) - memset(bytes, 0, n); - else - ReadLCN(Vcb, lcn, readcount, bytes); - - vcn += readcount; - bytes += n; - } -} - - -VOID -ReadVCN(PDEVICE_EXTENSION Vcb, - PFILE_RECORD_HEADER file, - ATTRIBUTE_TYPE type, - ULONGLONG vcn, - ULONG count, - PVOID buffer) -{ - PNONRESIDENT_ATTRIBUTE NresAttr; - PATTRIBUTE attr; - - attr = FindAttribute(file, type, 0); - - NresAttr = (PNONRESIDENT_ATTRIBUTE) attr; - - if (NresAttr == 0 || (vcn < NresAttr->StartVcn ||vcn > NresAttr->LastVcn)) - { -// PATTRIBUTE attrList = FindAttribute(file,AttributeAttributeList,0); - DbgPrint("Exeption \n"); -// KeDebugCheck(0); - } - - ReadExternalAttribute(Vcb, NresAttr, vcn, count, buffer); -} - - -#if 0 -BOOL bitset(PUCHAR bitmap, ULONG i) -{ - return (bitmap[i>>3] & (1 << (i & 7))) !=0; -} -#endif - - -VOID -FixupUpdateSequenceArray(PFILE_RECORD_HEADER file) -{ - PUSHORT usa = (PUSHORT)((ULONG_PTR)file + file->Ntfs.UsaOffset); - PUSHORT sector = (PUSHORT)file; - ULONG i; - - for (i = 1; i < file->Ntfs.UsaCount; i++) - { - sector[255] = usa[i]; - sector += 256; - } } @@ -323,4 +459,240 @@ FALSE); } + +BOOLEAN +CompareFileName(PUNICODE_STRING FileName, + PINDEX_ENTRY_ATTRIBUTE IndexEntry) +{ + UNICODE_STRING EntryName; + + EntryName.Buffer = IndexEntry->FileName.Name; + EntryName.Length = + EntryName.MaximumLength = IndexEntry->FileName.NameLength; + + return (RtlCompareUnicodeString(FileName, &EntryName, !!(IndexEntry->FileName.NameType != NTFS_FILE_NAME_POSIX)) == TRUE); +} + + +NTSTATUS +NtfsFindMftRecord(PDEVICE_EXTENSION Vcb, ULONGLONG MFTIndex, PUNICODE_STRING FileName, ULONGLONG *OutMFTIndex) +{ + PFILE_RECORD_HEADER MftRecord; + //ULONG Magic; + PNTFS_ATTR_CONTEXT IndexRootCtx; + PNTFS_ATTR_CONTEXT IndexBitmapCtx; + PNTFS_ATTR_CONTEXT IndexAllocationCtx; + PINDEX_ROOT_ATTRIBUTE IndexRoot; + ULONGLONG BitmapDataSize; + ULONGLONG IndexAllocationSize; + PCHAR BitmapData; + PCHAR IndexRecord; + PINDEX_ENTRY_ATTRIBUTE IndexEntry, IndexEntryEnd; + ULONG RecordOffset; + ULONG IndexBlockSize; + NTSTATUS Status; + + MftRecord = ExAllocatePoolWithTag(NonPagedPool, + Vcb->NtfsInfo.BytesPerFileRecord, + TAG_NTFS); + if (MftRecord == NULL) + { + return STATUS_INSUFFICIENT_RESOURCES; + } + + if (ReadFileRecord(Vcb, MFTIndex, MftRecord)) + { + //Magic = MftRecord->Magic; + + Status = FindAttribute(Vcb, MftRecord, AttributeIndexRoot, &IndexOfFileNames, &IndexRootCtx); + if (!NT_SUCCESS(Status)) + { + ExFreePoolWithTag(MftRecord, TAG_NTFS); + return Status; + } + + IndexRecord = ExAllocatePoolWithTag(NonPagedPool, Vcb->NtfsInfo.BytesPerIndexRecord, TAG_NTFS); + if (IndexRecord == NULL) + { + ExFreePoolWithTag(MftRecord, TAG_NTFS); + return STATUS_INSUFFICIENT_RESOURCES; + } + + ReadAttribute(Vcb, IndexRootCtx, 0, IndexRecord, Vcb->NtfsInfo.BytesPerIndexRecord); + IndexRoot = (PINDEX_ROOT_ATTRIBUTE)IndexRecord; + IndexEntry = (PINDEX_ENTRY_ATTRIBUTE)((PCHAR)&IndexRoot->Header + IndexRoot->Header.FirstEntryOffset); + /* Index root is always resident. */ + IndexEntryEnd = (PINDEX_ENTRY_ATTRIBUTE)(IndexRecord + IndexRootCtx->Record.Resident.ValueLength); + ReleaseAttributeContext(IndexRootCtx); + + DPRINT("IndexRecordSize: %x IndexBlockSize: %x\n", Vcb->NtfsInfo.BytesPerIndexRecord, IndexRoot->SizeOfEntry); + + while (IndexEntry < IndexEntryEnd && + !(IndexEntry->Flags & NTFS_INDEX_ENTRY_END)) + { + if (CompareFileName(FileName, IndexEntry)) + { + *OutMFTIndex = IndexEntry->Data.Directory.IndexedFile; + ExFreePoolWithTag(IndexRecord, TAG_NTFS); + ExFreePoolWithTag(MftRecord, TAG_NTFS); + return STATUS_SUCCESS; + } + IndexEntry = (PINDEX_ENTRY_ATTRIBUTE)((PCHAR)IndexEntry + IndexEntry->Length); + } + + if (IndexRoot->Header.Flags & INDEX_ROOT_LARGE) + { + DPRINT("Large Index!\n"); + + IndexBlockSize = IndexRoot->SizeOfEntry; + + Status = FindAttribute(Vcb, MftRecord, AttributeBitmap, &IndexOfFileNames, &IndexBitmapCtx); + if (!NT_SUCCESS(Status)) + { + DPRINT("Corrupted filesystem!\n"); + ExFreePoolWithTag(MftRecord, TAG_NTFS); + return Status; + } + BitmapDataSize = AttributeDataLength(&IndexBitmapCtx->Record); + DPRINT("BitmapDataSize: %x\n", (ULONG)BitmapDataSize); + if(BitmapDataSize <= 0xFFFFFFFF) + BitmapData = ExAllocatePoolWithTag(NonPagedPool, (ULONG)BitmapDataSize, TAG_NTFS); + else + BitmapData = NULL; + + if (BitmapData == NULL) + { + ExFreePoolWithTag(IndexRecord, TAG_NTFS); + ExFreePoolWithTag(MftRecord, TAG_NTFS); + return STATUS_INSUFFICIENT_RESOURCES; + } + ReadAttribute(Vcb, IndexBitmapCtx, 0, BitmapData, (ULONG)BitmapDataSize); + ReleaseAttributeContext(IndexBitmapCtx); + + Status = FindAttribute(Vcb, MftRecord, AttributeIndexAllocation, &IndexOfFileNames, &IndexAllocationCtx); + if (!NT_SUCCESS(Status)) + { + DPRINT("Corrupted filesystem!\n"); + ExFreePoolWithTag(BitmapData, TAG_NTFS); + ExFreePoolWithTag(IndexRecord, TAG_NTFS); + ExFreePoolWithTag(MftRecord, TAG_NTFS); + return Status; + } + IndexAllocationSize = AttributeDataLength(&IndexAllocationCtx->Record); + + RecordOffset = 0; + + for (;;) + { + DPRINT("RecordOffset: %x IndexAllocationSize: %x\n", RecordOffset, IndexAllocationSize); + for (; RecordOffset < IndexAllocationSize;) + { + UCHAR Bit = 1 << ((RecordOffset / IndexBlockSize) & 7); + ULONG Byte = (RecordOffset / IndexBlockSize) >> 3; + if ((BitmapData[Byte] & Bit)) + break; + RecordOffset += IndexBlockSize; + } + + if (RecordOffset >= IndexAllocationSize) + { + break; + } + + ReadAttribute(Vcb, IndexAllocationCtx, RecordOffset, IndexRecord, IndexBlockSize); + + if (!FixupUpdateSequenceArray(Vcb, &((PFILE_RECORD_HEADER)IndexRecord)->Ntfs)) + { + break; + } + + /* FIXME */ + IndexEntry = (PINDEX_ENTRY_ATTRIBUTE)(IndexRecord + 0x18 + *(USHORT *)(IndexRecord + 0x18)); + IndexEntryEnd = (PINDEX_ENTRY_ATTRIBUTE)(IndexRecord + IndexBlockSize); + + while (IndexEntry < IndexEntryEnd && + !(IndexEntry->Flags & NTFS_INDEX_ENTRY_END)) + { + if (CompareFileName(FileName, IndexEntry)) + { + DPRINT("File found\n"); + *OutMFTIndex = IndexEntry->Data.Directory.IndexedFile; + ExFreePoolWithTag(BitmapData, TAG_NTFS); + ExFreePoolWithTag(IndexRecord, TAG_NTFS); + ExFreePoolWithTag(MftRecord, TAG_NTFS); + ReleaseAttributeContext(IndexAllocationCtx); + return STATUS_SUCCESS; + } + IndexEntry = (PINDEX_ENTRY_ATTRIBUTE)((PCHAR)IndexEntry + IndexEntry->Length); + } + + RecordOffset += IndexBlockSize; + } + + ReleaseAttributeContext(IndexAllocationCtx); + ExFreePoolWithTag(BitmapData, TAG_NTFS); + } + + ExFreePoolWithTag(IndexRecord, TAG_NTFS); + } + else + { + DPRINT("Can't read MFT record\n"); + } + ExFreePoolWithTag(MftRecord, TAG_NTFS); + + return STATUS_OBJECT_PATH_NOT_FOUND; +} + +NTSTATUS +NtfsLookupFile(PDEVICE_EXTENSION Vcb, + PUNICODE_STRING PathName, + PFILE_RECORD_HEADER *FileRecord, + PNTFS_ATTR_CONTEXT *DataContext) +{ + ULONGLONG CurrentMFTIndex; + UNICODE_STRING Current, Remaining; + NTSTATUS Status; + + DPRINT1("NtfsLookupFile(%p, %wZ, %p)\n", Vcb, PathName, FileRecord); + + CurrentMFTIndex = NTFS_FILE_ROOT; + FsRtlDissectName(*PathName, &Current, &Remaining); + + while (Current.Length != 0) + { + DPRINT1("Lookup: %wZ\n", &Current); + + Status = NtfsFindMftRecord(Vcb, CurrentMFTIndex, &Current, &CurrentMFTIndex); + if (!NT_SUCCESS(Status)) + { + return Status; + } + + FsRtlDissectName(*PathName, &Current, &Remaining); + } + + *FileRecord = ExAllocatePoolWithTag(NonPagedPool, Vcb->NtfsInfo.BytesPerFileRecord, TAG_NTFS); + if (*FileRecord == NULL) + { + DPRINT("NtfsLookupFile: Can't allocate MFT record\n"); + return STATUS_INSUFFICIENT_RESOURCES; + } + + Status = ReadFileRecord(Vcb, CurrentMFTIndex, *FileRecord); + if (!NT_SUCCESS(Status)) + { + DPRINT("NtfsLookupFile: Can't read MFT record\n"); + return Status; + } + + Status = FindAttribute(Vcb, *FileRecord, AttributeData, PathName, DataContext); + if (!NT_SUCCESS(Status)) + { + DPRINT("NtfsLookupFile: Can't find data attribute\n"); + return Status; + } + + return STATUS_SUCCESS; +} /* EOF */ Modified: trunk/reactos/drivers/filesystems/ntfs/ntfs.h URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/filesystems/ntfs/n…
============================================================================== --- trunk/reactos/drivers/filesystems/ntfs/ntfs.h [iso-8859-1] (original) +++ trunk/reactos/drivers/filesystems/ntfs/ntfs.h [iso-8859-1] Fri Sep 26 13:57:29 2014 @@ -86,7 +86,6 @@ ULONG Size; } NTFSIDENTIFIER, *PNTFSIDENTIFIER; - typedef struct { NTFSIDENTIFIER Identifier; @@ -101,6 +100,8 @@ PDEVICE_OBJECT StorageDevice; PFILE_OBJECT StreamFileObject; + struct _NTFS_ATTR_CONTEXT* MFTContext; + struct _FILE_RECORD_HEADER* MasterFileTable; struct _FCB *VolumeFcb; NTFS_INFO NtfsInfo; @@ -186,8 +187,22 @@ AttributeEAInformation = 0xD0, AttributeEA = 0xE0, AttributePropertySet = 0xF0, - AttributeLoggedUtilityStream = 0x100 + AttributeLoggedUtilityStream = 0x100, + AttributeEnd = 0xFFFFFFFF } ATTRIBUTE_TYPE, *PATTRIBUTE_TYPE; + +#define NTFS_FILE_MFT 0 +#define NTFS_FILE_MFTMIRR 1 +#define NTFS_FILE_LOGFILE 2 +#define NTFS_FILE_VOLUME 3 +#define NTFS_FILE_ATTRDEF 4 +#define NTFS_FILE_ROOT 5 +#define NTFS_FILE_BITMAP 6 +#define NTFS_FILE_BOOT 7 +#define NTFS_FILE_BADCLUS 8 +#define NTFS_FILE_QUOTA 9 +#define NTFS_FILE_UPCASE 10 +#define NTFS_FILE_EXTEND 11 #define COLLATION_BINARY 0x00 #define COLLATION_FILE_NAME 0x01 @@ -200,6 +215,14 @@ #define INDEX_ROOT_SMALL 0x0 #define INDEX_ROOT_LARGE 0x1 +#define NTFS_INDEX_ENTRY_NODE 1 +#define NTFS_INDEX_ENTRY_END 2 + +#define NTFS_FILE_NAME_POSIX 0 +#define NTFS_FILE_NAME_WIN32 1 +#define NTFS_FILE_NAME_DOS 2 +#define NTFS_FILE_NAME_WIN32_AND_DOS 3 + typedef struct { ULONG Type; /* Magic number 'FILE' */ @@ -212,7 +235,7 @@ #define NRH_FILE_TYPE 0x454C4946 /* 'FILE' */ -typedef struct +typedef struct _FILE_RECORD_HEADER { NTFS_RECORD_HEADER Ntfs; USHORT SequenceNumber; /* Sequence number */ @@ -236,39 +259,38 @@ typedef struct { - ATTRIBUTE_TYPE AttributeType; - ULONG Length; - BOOLEAN Nonresident; - UCHAR NameLength; - USHORT NameOffset; - USHORT Flags; - USHORT AttributeNumber; -} ATTRIBUTE, *PATTRIBUTE; - -typedef struct -{ - ATTRIBUTE Attribute; - ULONG ValueLength; - USHORT ValueOffset; - UCHAR Flags; -// UCHAR Padding0; -} RESIDENT_ATTRIBUTE, *PRESIDENT_ATTRIBUTE; - -typedef struct -{ - ATTRIBUTE Attribute; - ULONGLONG StartVcn; // LowVcn - ULONGLONG LastVcn; // HighVcn - USHORT RunArrayOffset; - USHORT CompressionUnit; - ULONG Padding0; - UCHAR IndexedFlag; - ULONGLONG AllocatedSize; - ULONGLONG DataSize; - ULONGLONG InitializedSize; - ULONGLONG CompressedSize; -} NONRESIDENT_ATTRIBUTE, *PNONRESIDENT_ATTRIBUTE; - + ULONG Type; + ULONG Length; + UCHAR IsNonResident; + UCHAR NameLength; + USHORT NameOffset; + USHORT Flags; + USHORT Instance; + union + { + // Resident attributes + struct + { + ULONG ValueLength; + USHORT ValueOffset; + UCHAR Flags; + UCHAR Reserved; + } Resident; + // Non-resident attributes + struct + { + ULONGLONG LowestVCN; + ULONGLONG HighestVCN; + USHORT MappingPairsOffset; + USHORT CompressionUnit; + UCHAR Reserved[4]; + LONGLONG AllocatedSize; + LONGLONG DataSize; + LONGLONG InitializedSize; + LONGLONG CompressedSize; + } NonResident; + }; +} NTFS_ATTR_RECORD, *PNTFS_ATTR_RECORD; typedef struct { @@ -337,6 +359,28 @@ typedef struct { + union + { + struct + { + ULONGLONG IndexedFile; + } Directory; + struct + { + USHORT DataOffset; + USHORT DataLength; + ULONG Reserved; + } ViewIndex; + } Data; + USHORT Length; + USHORT KeyLength; + USHORT Flags; + USHORT Reserved; + FILENAME_ATTRIBUTE FileName; +} INDEX_ENTRY_ATTRIBUTE, *PINDEX_ENTRY_ATTRIBUTE; + +typedef struct +{ ULONGLONG Unknown1; UCHAR MajorVersion; UCHAR MinorVersion; @@ -357,6 +401,16 @@ NTSTATUS SavedExceptionCode; } NTFS_IRP_CONTEXT, *PNTFS_IRP_CONTEXT; +typedef struct _NTFS_ATTR_CONTEXT +{ + PUCHAR CacheRun; + ULONGLONG CacheRunOffset; + LONGLONG CacheRunStartLCN; + ULONGLONG CacheRunLength; + LONGLONG CacheRunLastLCN; + ULONGLONG CacheRunCurrentOffset; + NTFS_ATTR_RECORD Record; +} NTFS_ATTR_CONTEXT, *PNTFS_ATTR_CONTEXT; extern PNTFS_GLOBAL_DATA NtfsGlobalData; @@ -369,15 +423,10 @@ //VOID //NtfsDumpAttribute(PATTRIBUTE Attribute); -//LONGLONG RunLCN(PUCHAR run); - -//ULONG RunLength(PUCHAR run); - -BOOLEAN -FindRun(PNONRESIDENT_ATTRIBUTE NresAttr, - ULONGLONG vcn, - PULONGLONG lcn, - PULONGLONG count); +PUCHAR +DecodeRun(PUCHAR DataRun, + LONGLONG *DataRunOffset, + ULONGLONG *DataRunLength); VOID NtfsDumpFileAttributes(PFILE_RECORD_HEADER FileRecord); @@ -529,35 +578,30 @@ /* mft.c */ -NTSTATUS -NtfsOpenMft(PDEVICE_EXTENSION Vcb); - - -VOID -ReadAttribute(PATTRIBUTE attr, - PVOID buffer, - PDEVICE_EXTENSION Vcb, - PDEVICE_OBJECT DeviceObject); - ULONG -AttributeDataLength(PATTRIBUTE attr); +ReadAttribute(PDEVICE_EXTENSION Vcb, + PNTFS_ATTR_CONTEXT Context, + ULONGLONG Offset, + PCHAR Buffer, + ULONG Length); + +ULONGLONG +AttributeDataLength(PNTFS_ATTR_RECORD AttrRecord); ULONG -AttributeAllocatedLength(PATTRIBUTE Attribute); +AttributeAllocatedLength(PNTFS_ATTR_RECORD AttrRecord); NTSTATUS ReadFileRecord(PDEVICE_EXTENSION Vcb, - ULONG index, - PFILE_RECORD_HEADER file, - PFILE_RECORD_HEADER Mft); - -PATTRIBUTE -FindAttribute(PFILE_RECORD_HEADER file, - ATTRIBUTE_TYPE type, - PWSTR name); - -ULONG -AttributeLengthAllocated(PATTRIBUTE attr); + ULONGLONG index, + PFILE_RECORD_HEADER file); + +NTSTATUS +FindAttribute(PDEVICE_EXTENSION Vcb, + PFILE_RECORD_HEADER MftRecord, + ULONG Type, + PUNICODE_STRING Name, + PNTFS_ATTR_CONTEXT * AttrCtx); VOID ReadVCN(PDEVICE_EXTENSION Vcb, @@ -567,15 +611,9 @@ ULONG count, PVOID buffer); -VOID -FixupUpdateSequenceArray(PFILE_RECORD_HEADER file); - -VOID -ReadExternalAttribute(PDEVICE_EXTENSION Vcb, - PNONRESIDENT_ATTRIBUTE NresAttr, - ULONGLONG vcn, - ULONG count, - PVOID buffer); +NTSTATUS +FixupUpdateSequenceArray(PDEVICE_EXTENSION Vcb, + PNTFS_RECORD_HEADER Record); NTSTATUS ReadLCN(PDEVICE_EXTENSION Vcb, @@ -588,6 +626,11 @@ PDEVICE_EXTENSION Vcb, PDEVICE_OBJECT DeviceObject); +NTSTATUS +NtfsLookupFile(PDEVICE_EXTENSION Vcb, + PUNICODE_STRING PathName, + PFILE_RECORD_HEADER *FileRecord, + PNTFS_ATTR_CONTEXT *DataContext); /* misc.c */
10 years, 3 months
1
0
0
0
[jgardou] 64312: [SPEC2DEF] - Actually commit what was advertised in r64281
by jgardou@svn.reactos.org
Author: jgardou Date: Fri Sep 26 12:43:27 2014 New Revision: 64312 URL:
http://svn.reactos.org/svn/reactos?rev=64312&view=rev
Log: [SPEC2DEF] - Actually commit what was advertised in r64281 Modified: trunk/reactos/tools/spec2def/spec2def.c Modified: trunk/reactos/tools/spec2def/spec2def.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/tools/spec2def/spec2def.c?…
============================================================================== --- trunk/reactos/tools/spec2def/spec2def.c [iso-8859-1] (original) +++ trunk/reactos/tools/spec2def/spec2def.c [iso-8859-1] Fri Sep 26 12:43:27 2014 @@ -282,7 +282,7 @@ { fprintf(file, "\tint retval;\n"); } - fprintf(file, "\tif(TRACE_ON(relay))\n\t\tDPRINTF(\"%s: %.*s(", + fprintf(file, "\tif (TRACE_ON(relay))\n\t\tDPRINTF(\"%s: %.*s(", pszDllName, pexp->strName.len, pexp->strName.buf); } @@ -350,13 +350,13 @@ { if (pexp->uFlags & FL_RET64) { - fprintf(file, "\tif(TRACE_ON(relay))\n\t\t(\"%s: %.*s: retval = %%\"PRIx64\"\\n\", retval);\n", + fprintf(file, "\tif (TRACE_ON(relay))\n\t\tDPRINTF(\"%s: %.*s: retval = %%\"PRIx64\"\\n\", retval);\n", pszDllName, pexp->strName.len, pexp->strName.buf); } else { - fprintf(file, "\tTRACE_(relay)(\"%.*s: retval = 0x%%lx\\n\", retval);\n", - pexp->strName.len, pexp->strName.buf); + fprintf(file, "\tif (TRACE_ON(relay))\n\t\tDPRINTF(\"%s: %.*s: retval = 0x%%lx\\n\", retval);\n", + pszDllName, pexp->strName.len, pexp->strName.buf); } fprintf(file, "\treturn retval;\n}\n\n"); }
10 years, 3 months
1
0
0
0
[jgardou] 64311: [WIN32K] - Simplify IntRemoveWindowProp - Complain loudly if a NULL list entry sneaks into a window property list. CORE-8562
by jgardou@svn.reactos.org
Author: jgardou Date: Fri Sep 26 12:43:12 2014 New Revision: 64311 URL:
http://svn.reactos.org/svn/reactos?rev=64311&view=rev
Log: [WIN32K] - Simplify IntRemoveWindowProp - Complain loudly if a NULL list entry sneaks into a window property list. CORE-8562 Modified: trunk/reactos/tools/spec2def/spec2def.c trunk/reactos/win32ss/user/ntuser/prop.c Modified: trunk/reactos/tools/spec2def/spec2def.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/tools/spec2def/spec2def.c?…
============================================================================== --- trunk/reactos/tools/spec2def/spec2def.c [iso-8859-1] (original) +++ trunk/reactos/tools/spec2def/spec2def.c [iso-8859-1] Fri Sep 26 12:43:12 2014 @@ -38,6 +38,7 @@ typedef int (*PFNOUTLINE)(FILE *, EXPORT *); int gbMSComp = 0; int gbImportLib = 0; +int gbTracing = 0; int giArch = ARCH_X86; char *pszArchString = "i386"; char *pszArchString2; @@ -52,6 +53,9 @@ FL_STUB = 2, FL_NONAME = 4, FL_ORDINAL = 8, + FL_NORELAY = 16, + FL_RET64 = 32, + FL_REGISTER = 64, }; enum @@ -161,52 +165,126 @@ OutputHeader_stub(FILE *file) { fprintf(file, "/* This file is autogenerated, do not edit. */\n\n" - "#include <stubs.h>\n\n"); + "#include <stubs.h>\n"); + + if (gbTracing) + { + fprintf(file, "#include <wine/debug.h>\n"); + fprintf(file, "#include <inttypes.h>\n"); + fprintf(file, "WINE_DECLARE_DEBUG_CHANNEL(relay);\n"); + } + + fprintf(file, "\n"); } int OutputLine_stub(FILE *file, EXPORT *pexp) { int i; + int bRelay = 0; + int bInPrototype; if (pexp->nCallingConvention != CC_STUB && - (pexp->uFlags & FL_STUB) == 0) return 0; - - fprintf(file, "int "); - if ((giArch == ARCH_X86) && - pexp->nCallingConvention == CC_STDCALL) - { - fprintf(file, "__stdcall "); - } - - /* Check for C++ */ - if (pexp->strName.buf[0] == '?') - { - fprintf(file, "stub_function%d(", pexp->nNumber); + (pexp->uFlags & FL_STUB) == 0) + { + /* Only relay trace stdcall C functions */ + if (!gbTracing || (pexp->nCallingConvention != CC_STDCALL) + || (pexp->uFlags & FL_NORELAY) + || (pexp->strName.buf[0] == '?')) + { + return 0; + } + bRelay = 1; + } + + /* Declare the "real" function */ + if (bRelay) + { + fprintf(file, "extern "); + bInPrototype = 1; + } + + do + { + if (pexp->uFlags & FL_REGISTER) + { + /* FIXME: Not sure this is right */ + fprintf(file, "void "); + } + else if (pexp->uFlags & FL_RET64) + { + fprintf(file, "__int64 "); + } + else + { + fprintf(file, "int "); + } + + if ((giArch == ARCH_X86) && + pexp->nCallingConvention == CC_STDCALL) + { + fprintf(file, "__stdcall "); + } + + /* Check for C++ */ + if (pexp->strName.buf[0] == '?') + { + fprintf(file, "stub_function%d(", pexp->nNumber); + } + else + { + if (!bRelay || bInPrototype) + fprintf(file, "%.*s(", pexp->strName.len, pexp->strName.buf); + else + fprintf(file, "$relaytrace$%.*s(", pexp->strName.len, pexp->strName.buf); + } + + for (i = 0; i < pexp->nArgCount; i++) + { + if (i != 0) fprintf(file, ", "); + switch (pexp->anArgs[i]) + { + case ARG_LONG: fprintf(file, "long"); break; + case ARG_PTR: fprintf(file, "void*"); break; + case ARG_STR: fprintf(file, "char*"); break; + case ARG_WSTR: fprintf(file, "wchar_t*"); break; + case ARG_DBL: fprintf(file, "double"); break; + case ARG_INT64 : fprintf(file, "__int64"); break; + case ARG_INT128 : fprintf(file, "__int128"); break; + case ARG_FLOAT: fprintf(file, "float"); break; + } + fprintf(file, " a%d", i); + } + + if (bInPrototype) + { + fprintf(file, ");\n\n"); + } + } while (bInPrototype--); + + if (!bRelay) + { + fprintf(file, ")\n{\n\tDbgPrint(\"WARNING: calling stub %.*s(", + pexp->strName.len, pexp->strName.buf); } else { - fprintf(file, "%.*s(", pexp->strName.len, pexp->strName.buf); - } - - for (i = 0; i < pexp->nArgCount; i++) - { - if (i != 0) fprintf(file, ", "); - switch (pexp->anArgs[i]) - { - case ARG_LONG: fprintf(file, "long"); break; - case ARG_PTR: fprintf(file, "void*"); break; - case ARG_STR: fprintf(file, "char*"); break; - case ARG_WSTR: fprintf(file, "wchar_t*"); break; - case ARG_DBL: - case ARG_INT64 : fprintf(file, "__int64"); break; - case ARG_INT128 : fprintf(file, "__int128"); break; - case ARG_FLOAT: fprintf(file, "float"); break; - } - fprintf(file, " a%d", i); - } - fprintf(file, ")\n{\n\tDbgPrint(\"WARNING: calling stub %.*s(", - pexp->strName.len, pexp->strName.buf); + fprintf(file, ")\n{\n"); + if (pexp->uFlags & FL_REGISTER) + { + /* No return value */ + } + else if (pexp->uFlags & FL_RET64) + { + fprintf(file, "\t__int64 retval;\n"); + } + else + { + fprintf(file, "\tint retval;\n"); + } + fprintf(file, "\tif(TRACE_ON(relay))\n\t\tDPRINTF(\"%s: %.*s(", + pszDllName, pexp->strName.len, pexp->strName.buf); + } for (i = 0; i < pexp->nArgCount; i++) { @@ -246,8 +324,42 @@ { fprintf(file, "\t__wine_spec_unimplemented_stub(\"%s\", __FUNCTION__);\n", pszDllName); } - - fprintf(file, "\treturn 0;\n}\n\n"); + else if (bRelay) + { + if (pexp->uFlags & FL_REGISTER) + { + fprintf(file,"\t"); + } + else + { + fprintf(file, "\tretval = "); + } + fprintf(file, "%.*s(", pexp->strName.len, pexp->strName.buf); + + for (i = 0; i < pexp->nArgCount; i++) + { + if (i != 0) fprintf(file, ", "); + fprintf(file, "a%d", i); + } + fprintf(file, ");\n"); + } + + if (!bRelay) + fprintf(file, "\treturn 0;\n}\n\n"); + else if ((pexp->uFlags & FL_REGISTER) == 0) + { + if (pexp->uFlags & FL_RET64) + { + fprintf(file, "\tif(TRACE_ON(relay))\n\t\t(\"%s: %.*s: retval = %%\"PRIx64\"\\n\", retval);\n", + pszDllName, pexp->strName.len, pexp->strName.buf); + } + else + { + fprintf(file, "\tTRACE_(relay)(\"%.*s: retval = 0x%%lx\\n\", retval);\n", + pexp->strName.len, pexp->strName.buf); + } + fprintf(file, "\treturn retval;\n}\n\n"); + } return 1; } @@ -458,11 +570,18 @@ /* C++ stubs are forwarded to C stubs */ fprintf(fileDest, "=stub_function%d", pexp->nNumber); } + else if (gbTracing && ((pexp->uFlags & FL_NORELAY) == 0) && (pexp->nCallingConvention == CC_STDCALL) && + (pexp->strName.buf[0] != '?')) + { + /* Redirect it to the relay-tracing trampoline */ + fprintf(fileDest, "=$relaytrace$%.*s", pexp->strName.len, pexp->strName.buf); + } } void OutputLine_def_GCC(FILE *fileDest, EXPORT *pexp) { + int bTracing = 0; /* Print the function name, with decoration for export libs */ PrintName(fileDest, pexp, &pexp->strName, gbImportLib); DbgPrint("Generating def line for '%.*s'\n", pexp->strName.len, pexp->strName.buf); @@ -482,6 +601,19 @@ { /* C++ stubs are forwarded to C stubs */ fprintf(fileDest, "=stub_function%d", pexp->nNumber); + } + else if (gbTracing && ((pexp->uFlags & FL_NORELAY) == 0) && (pexp->nCallingConvention == CC_STDCALL) && + (pexp->strName.buf[0] != '?')) + { + /* Redirect it to the relay-tracing trampoline */ + char buf[256]; + STRING strTarget; + fprintf(fileDest, "="); + sprintf(buf, "$relaytrace$%.*s", pexp->strName.len, pexp->strName.buf); + strTarget.buf = buf; + strTarget.len = pexp->strName.len + 12; + PrintName(fileDest, pexp, &strTarget, 1); + bTracing = 1; } /* Special handling for stdcall and fastcall */ @@ -500,7 +632,7 @@ fprintf(fileDest, "==%.*s", pexp->strName.len, pexp->strName.buf); } } - else if (!pexp->strTarget.buf) + else if ((!pexp->strTarget.buf) && !(bTracing)) { /* Write a forwarder to the actual decorated symbol */ fprintf(fileDest, "="); @@ -694,11 +826,17 @@ { exp.uFlags |= FL_STUB; } - else if (CompareToken(pc, "-norelay") || - CompareToken(pc, "-register") || - CompareToken(pc, "-ret64")) - { - /* silently ignore these */ + else if (CompareToken(pc, "-norelay")) + { + exp.uFlags |= FL_NORELAY; + } + else if (CompareToken(pc, "-ret64")) + { + exp.uFlags |= FL_RET64; + } + else if (CompareToken(pc, "-register")) + { + exp.uFlags |= FL_REGISTER; } else { @@ -862,6 +1000,9 @@ fprintf(stderr, "error: line %d, additional tokens after ')'\n", nLine); return -17; } + + /* Don't relay-trace forwarded functions */ + exp.uFlags |= FL_NORELAY; } else { @@ -886,16 +1027,17 @@ void usage(void) { - printf("syntax: spec2pdef [<options> ...] <spec file>\n" + printf("syntax: spec2def [<options> ...] <spec file>\n" "Possible options:\n" - " -h --help prints this screen\n" - " -l=<file> generates an asm lib stub\n" - " -d=<file> generates a def file\n" - " -s=<file> generates a stub file\n" - " --ms msvc compatibility\n" - " -n=<name> name of the dll\n" - " --implib generate a def file for an import library\n" - " -a=<arch> Set architecture to <arch>. (i386, x86_64, arm)\n"); + " -h --help prints this screen\n" + " -l=<file> generates an asm lib stub\n" + " -d=<file> generates a def file\n" + " -s=<file> generates a stub file\n" + " --ms msvc compatibility\n" + " -n=<name> name of the dll\n" + " --implib generate a def file for an import library\n" + " -a=<arch> Set architecture to <arch>. (i386, x86_64, arm)\n" + " --with-tracing generates wine-like \"+relay\" trace trampolines. (necessitates -s)\n"); } int main(int argc, char *argv[]) @@ -945,6 +1087,15 @@ { gbMSComp = 1; } + else if ((strcasecmp(argv[i], "--with-tracing") == 0)) + { + if (!pszStubFileName) + { + fprintf(stderr, "Error: cannot use --with-tracing without -s option.\n"); + return -1; + } + gbTracing = 1; + } else if (argv[i][1] == 'a' && argv[i][2] == '=') { pszArchString = argv[i] + 3; Modified: trunk/reactos/win32ss/user/ntuser/prop.c URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/prop.c…
============================================================================== --- trunk/reactos/win32ss/user/ntuser/prop.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/prop.c [iso-8859-1] Fri Sep 26 12:43:12 2014 @@ -19,9 +19,18 @@ int i; ListEntry = Window->PropListHead.Flink; + for (i = 0; i < Window->PropListItems; i++ ) { Property = CONTAINING_RECORD(ListEntry, PROPERTY, PropListEntry); + + if (ListEntry == NULL) + { + ERR("Corrupted (or uninitialized?) property list for window %p. Prop count %d. Atom %d.\n", + Window, Window->PropListItems, Atom); + return NULL; + } + if (Property->Atom == Atom) { return(Property); @@ -84,16 +93,14 @@ { PLIST_ENTRY ListEntry; PPROPERTY Property; - int i, Count = Window->PropListItems; - - ListEntry = Window->PropListHead.Flink; - for (i = 0; i < Count; i++ ) - { - Property = CONTAINING_RECORD(ListEntry, PROPERTY, PropListEntry); - ListEntry = ListEntry->Flink; - RemoveEntryList(&Property->PropListEntry); - UserHeapFree(Property); - Window->PropListItems--; + + while (!IsListEmpty(&Window->PropListHead)) + { + ListEntry = Window->PropListHead.Flink; + Property = CONTAINING_RECORD(ListEntry, PROPERTY, PropListEntry); + RemoveEntryList(&Property->PropListEntry); + UserHeapFree(Property); + Window->PropListItems--; } return; }
10 years, 3 months
1
0
0
0
← Newer
1
...
9
10
11
12
13
14
15
...
42
Older →
Jump to page:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
Results per page:
10
25
50
100
200