Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
22 commits
Select commit Hold shift + click to select a range
901fce4
addition of service debug helpers
jessk-msft Jan 27, 2025
f662cbf
testing large service transmission
jessk-msft Jan 27, 2025
c0d28a3
large service transmission failing
jessk-msft Jan 27, 2025
de8d74e
addition of initial TestReadDirectoryChanges
jessk-msft Feb 15, 2025
a2ece3b
fixing TestReadDirectoryChanges to fail as expected
jessk-msft Feb 16, 2025
20b3eb6
initial filter support for FILE_OPEN_BY_FILE_ID
jessk-msft Feb 17, 2025
742664a
fixing TestDriver compilation
jessk-msft Feb 17, 2025
a75a507
fixing P4vfsGetFileIdByFileName driver support
jessk-msft Feb 17, 2025
ff9f6d0
addition of P4VFS_TEST_SERVER_ROOT folder override
jessk-msft Feb 18, 2025
d1b49da
testing open writable file by Id
jessk-msft Feb 19, 2025
30cb069
addition of driver P4vfsSetFileWritable by FileId
jessk-msft Feb 22, 2025
83a607e
directory notifications excluded when populate by STREAM
jessk-msft Feb 23, 2025
bc604cd
updating driver reparse comments
jessk-msft Feb 23, 2025
e3b0f27
passing TestReadDirectoryChanges and prep for 1.29.0.0
jessk-msft Feb 24, 2025
e7ee993
fixing SocketModelCommunicationTest and support for large messages
jessk-msft Feb 24, 2025
b61b419
improving random byte generation
jessk-msft Feb 27, 2025
ed4cd36
fixing additional tests
jessk-msft Mar 1, 2025
9f999e4
temporarily excluding attributes filter from directory change test wh…
jessk-msft Mar 1, 2025
94210d9
updating version with comments for attribute notification debugging
jessk-msft Mar 1, 2025
dd17df5
addition of setup registrykey configuration
jessk-msft Mar 2, 2025
6e0f19b
Update README.md
jessk-msft Mar 2, 2025
d2ebfd0
Update README.md
jessk-msft Mar 2, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
/source/P4VFS.Driver/*smv*
/source/P4VFS.Driver/Scripts/*.txt
/source/P4VFS.Driver/Scripts/*.etl
/source/P4VFS.Driver/Scripts/*.log
**/obj/
**/.vs/
**/.vscode/
2 changes: 1 addition & 1 deletion external/P4VFS/P4VFS.Module.cs
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ namespace Microsoft.P4VFS.External
{
public class P4vfsModule : Module
{
private const string P4VFS_SIGNED_VERSION = "1.28.0.0";
private const string P4VFS_SIGNED_VERSION = "1.28.3.0";
private const string P4VFS_SIGNED_ARTIFACTS_URL = "https://github.com/microsoft/p4vfs/releases/download";

public override string Name
Expand Down
28 changes: 28 additions & 0 deletions source/P4VFS.Console/P4VFS.Notes.txt
Original file line number Diff line number Diff line change
@@ -1,5 +1,33 @@
Microsoft P4VFS Release Notes

Version [1.29.0.0]
* Fixing virtual file hydration to be excluded from system directory notifications.
This avoids unecessary FILE_NOTIFY_INFORMATION or DirectoryWatcher events indicating
a virtual file has been modified, when it's only been hydrated as-expected on read.
This technique is common across filter drivers. This is only supported for STREAM
populate method (default). New unit test TestReadDirectoryChanges for verification.
* Additional unit test varible P4VFS_TEST_SERVER_ROOT for overriding the root directory
for the test servers. This better facilitates running all tests remotely on a local
virtual machine with including kernel mode debugging. Includes support for
RestartPerforceServer script to quick spin-up of existing server on override drive
* Reconfiguring our 32 bit driver allocation pool tags to 4-byte string "Pvs*"
* Fixing bug recieving large messages to/from the P4VFS.Service. This was typically
encountered when using global "-x <file>" with a file containing many arguments.
There's a new ReflectPackage message which is now used by SocketModelCommunicationTest
to stress test a wide range of message sizes
* Fixing unit tests deterministic random byte generation to more randomly include
zero as randomly as possible
* Support for additional registry keys to set defined in the setup application configuration
file (typically named P4VFS.Setup.xml residing in the same folder as the installer).
This is helpfull for setting possibly setting a version key to indicate what settings
template was also installed.

Version [1.28.4.0]
* Addition of optional service commandline argument to launch with debugger attached.
This is done as needed from admin command prompt "sc.exe start P4VFS.Service --break"
* Moving service logging system to initialize before ExtensionsInterop. This avoids
missed logging from service communication initialization.

Version [1.28.3.0]
* Fixing service initialization error if registry ImagePath value contains quotes
under key "HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\P4VFS.Service".
Expand Down
11 changes: 11 additions & 0 deletions source/P4VFS.Core/Include/FileOperations.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,17 @@ namespace Microsoft {
namespace P4VFS {
namespace FileOperations {

HRESULT
RestrictFileTimeChange(
HANDLE hFile
);

HRESULT
SetFileAttributesOnHandle(
HANDLE hFile,
DWORD dwFileAttributes
);

bool
SleepAndVerifyFileExists(
const WCHAR* filePath,
Expand Down
32 changes: 21 additions & 11 deletions source/P4VFS.Core/Source/FileOperations.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,23 @@ RestrictFileTimeChange(
return S_OK;
}

HRESULT
SetFileAttributesOnHandle(
HANDLE hFile,
DWORD dwFileAttributes
)
{
FILE_BASIC_INFO basicInfo = {0};
basicInfo.FileAttributes = dwFileAttributes;

if (!SetFileInformationByHandle(hFile, FileBasicInfo, &basicInfo, sizeof(basicInfo)))
{
return HRESULT_FROM_WIN32(GetLastError());
}

return S_OK;
}

bool
SleepAndVerifyFileExists(
const WCHAR* filePath,
Expand Down Expand Up @@ -1116,12 +1133,6 @@ PopulateFileByStream(
return hr;
}

if (SetFileAttributes(fileToPopulate.c_str(), dstFileAttributes & ~FILE_ATTRIBUTE_READONLY) == FALSE)
{
hr = HRESULT_FROM_WIN32(GetLastError());
return hr;
}

FileCore::FileStream* fileToPopulateFrom = srcFileStream;
if (fileToPopulateFrom == nullptr || fileToPopulateFrom->CanRead() == false)
{
Expand Down Expand Up @@ -1170,17 +1181,16 @@ PopulateFileByStream(
hr = RemoveSparseFileSizeOnHandle(dstFile.Handle());
if (FAILED(hr))
{
return hr;
return hr;
}

dstFile.Close();

if (!SetFileAttributes(fileToPopulate.c_str(), dstFileAttributes & ~(FILE_ATTRIBUTE_OFFLINE)))
hr = SetFileAttributesOnHandle(dstFile.Handle(), dstFileAttributes & ~(FILE_ATTRIBUTE_OFFLINE));
if (FAILED(hr))
{
hr = HRESULT_FROM_WIN32(GetLastError());
return hr;
}

dstFile.Close();
return S_OK;
}

Expand Down
11 changes: 6 additions & 5 deletions source/P4VFS.Core/Source/Pch.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,15 @@
// Licensed under the MIT license.
#pragma once

#pragma warning(disable: 4127) // conditional expression is constant
#pragma warning(disable: 4100) // unreferenced formal parameter
#pragma warning(disable: 4239) // Nonstandard extension used : 'token' : conversion from 'type' to 'type'
#pragma warning(disable: 4458) // Declaration of 'identifier' hides class member
#pragma warning(disable: 4127) // conditional expression is constant
#pragma warning(disable: 4100) // unreferenced formal parameter
#pragma warning(disable: 4239) // Nonstandard extension used : 'token' : conversion from 'type' to 'type'
#pragma warning(disable: 4458) // Declaration of 'identifier' hides class member
#pragma warning(disable: 6031) // Return value ignored
#pragma warning(disable: 6101) // A successful path through the function doesn't set the _Out_ annotated parameter.
#pragma warning(disable: 26444) // Avoid unnamed objects with custom construction and destruction
#pragma warning(disable: 26451) // Arithmetic overflow: Using operator '%operator%' on a %size1% byte value and then casting the result to a %size2% byte value
#pragma warning(disable: 26495) // Variable '%variable%' is uninitialized. Always initialize a member variable
#pragma warning(disable: 26495) // Variable '%variable%' is uninitialized. Always initialize a member variable
#pragma warning(disable: 26812) // Prefer 'enum class' over 'enum'
#pragma warning(disable: 26813) // Use 'bitwise and' to check if a flag is set.

Expand Down
28 changes: 23 additions & 5 deletions source/P4VFS.Core/Tests/TestDriver.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ typedef INT FLT_FILE_NAME_OPTIONS;
typedef VOID* PACCESS_STATE;
typedef INT FILE_INFORMATION_CLASS;
typedef HANDLE PEPROCESS;
typedef VOID* PESILO;

typedef struct _UNICODE_STRING {
USHORT Length;
Expand Down Expand Up @@ -60,7 +61,7 @@ typedef struct _IO_DRIVER_CREATE_CONTEXT
PVOID DeviceObjectHint;
PVOID TxnParameters;
#if (NTDDI_VERSION >= NTDDI_WIN10_RS1)
PVOID SiloContext;
PESILO SiloContext;
#endif
} IO_DRIVER_CREATE_CONTEXT, *PIO_DRIVER_CREATE_CONTEXT;

Expand Down Expand Up @@ -218,6 +219,11 @@ typedef struct _FILE_STANDARD_INFORMATION_EX {
BOOLEAN MetadataAttribute;
} FILE_STANDARD_INFORMATION_EX, *PFILE_STANDARD_INFORMATION_EX;

typedef struct _FILE_ID_INFORMATION {
ULONGLONG VolumeSerialNumber;
FILE_ID_128 FileId;
} FILE_ID_INFORMATION, *PFILE_ID_INFORMATION;

typedef enum _POOL_TYPE {
NonPagedPoolNx = 512,
} POOL_TYPE;
Expand All @@ -227,25 +233,28 @@ typedef enum _POOL_TYPE {
#define P4vfsTraceInfo(...) __noop
#define PAGED_CODE() __noop
#define FlagOn(_F,_SF) ((_F) & (_SF))
#define ClearFlag(_F,_SF) ((_F) &= ~(_SF))
#define ObDereferenceObject(f) __noop
#define PsGetCurrentProcess() GetCurrentProcess()
#define PsGetCurrentProcessId() GetCurrentProcessId()
#define PsGetCurrentThreadId() GetCurrentThreadId()
#define PsGetHostSilo() NULL
#define min(a,b) (((a) < (b)) ? (a) : (b))
#define max(a,b) (((a) > (b)) ? (a) : (b))
#define RtlUShortAdd UShortAdd

#define NT_SUCCESS(Status) (((NTSTATUS)(Status)) >= 0)
#define STATUS_SUCCESS ((NTSTATUS)0x00000000L)
#define STATUS_DATA_ERROR ((NTSTATUS)0xC000003EL)
#define STATUS_INSUFFICIENT_RESOURCES ((NTSTATUS)0xC000009AL)
#define STATUS_UNSUCCESSFUL ((NTSTATUS)0xC0000001L)
#define STATUS_BUFFER_OVERFLOW ((NTSTATUS)0x80000005L)
#define STATUS_BUFFER_TOO_SMALL ((NTSTATUS)0xC0000023L)
#define STATUS_PORT_DISCONNECTED ((NTSTATUS)0xC0000037L)
#define STATUS_MEMORY_NOT_ALLOCATED ((NTSTATUS)0xC00000A0L)
#define STATUS_DATA_ERROR ((NTSTATUS)0xC000003EL)
#define STATUS_INVALID_PORT_HANDLE ((NTSTATUS)0xC0000042L)
#define STATUS_INSUFFICIENT_RESOURCES ((NTSTATUS)0xC000009AL)
#define STATUS_MEMORY_NOT_ALLOCATED ((NTSTATUS)0xC00000A0L)
#define STATUS_NOT_ALL_ASSIGNED ((NTSTATUS)0x00000106L)
#define STATUS_INVALID_BUFFER_SIZE ((NTSTATUS)0xC0000206L)
#define STATUS_BUFFER_TOO_SMALL ((NTSTATUS)0xC0000023L)

#define IO_IGNORE_SHARE_ACCESS_CHECK 0x0800
#define FILE_SHARE_VALID_FLAGS 0x00000007
Expand All @@ -258,9 +267,11 @@ typedef enum _POOL_TYPE {
#define FileBasicInformation 4
#define FileStandardInformation 5
#define FileInternalInformation 6
#define FileIdInformation 59

#define FILE_OPEN 0x00000001
#define FILE_SYNCHRONOUS_IO_NONALERT 0x00000020
#define FILE_NON_DIRECTORY_FILE 0x00000040
#define FILE_NO_INTERMEDIATE_BUFFERING 0x00000008
#define FILE_OPEN_REPARSE_POINT 0x00200000
#define FILE_OPEN_BY_FILE_ID 0x00002000
Expand All @@ -280,8 +291,11 @@ std::function<NTSTATUS(PFLT_FILTER, PFLT_INSTANCE, PHANDLE, PFILE_OBJECT*, ACCES
std::function<VOID(PVOID)> FltObjectDereference;
std::function<NTSTATUS(HANDLE)> FltClose;
std::function<NTSTATUS(PFLT_INSTANCE, PFILE_OBJECT, PVOID, ULONG, FILE_INFORMATION_CLASS, PULONG)> FltQueryInformationFile;
std::function<NTSTATUS(PFLT_INSTANCE, PFILE_OBJECT, PVOID, ULONG, FILE_INFORMATION_CLASS)> FltSetInformationFile;
std::function<NTSTATUS(PFLT_INSTANCE, PFLT_VOLUME*)> FltGetVolumeFromInstance;
std::function<NTSTATUS(PFLT_VOLUME, PUNICODE_STRING, PULONG)> FltGetVolumeName;
std::function<NTSTATUS(PFLT_FILTER, PFILE_OBJECT, PFLT_VOLUME*)> FltGetVolumeFromFileObject;
std::function<NTSTATUS(PFLT_FILTER, PFLT_VOLUME, PCUNICODE_STRING, PFLT_INSTANCE*)> FltGetVolumeInstanceFromName;

std::function<PVOID(POOL_TYPE, SIZE_T, ULONG)> ExAllocatePoolZero;
std::function<VOID(PVOID, ULONG)> ExFreePoolWithTag;
Expand Down Expand Up @@ -431,7 +445,11 @@ static void InternalTestDriverReset(const TestContext& context)
FltObjectDereference = P4VFS_DEFAULT_FUNCTION_NTSTATUS();
FltClose = P4VFS_DEFAULT_FUNCTION_NTSTATUS();
FltQueryInformationFile = P4VFS_DEFAULT_FUNCTION_NTSTATUS();
FltSetInformationFile = P4VFS_DEFAULT_FUNCTION_NTSTATUS();
FltGetVolumeFromInstance = P4VFS_DEFAULT_FUNCTION_NTSTATUS();
FltGetVolumeName = P4VFS_DEFAULT_FUNCTION_NTSTATUS();
FltGetVolumeFromFileObject = P4VFS_DEFAULT_FUNCTION_NTSTATUS();
FltGetVolumeInstanceFromName = P4VFS_DEFAULT_FUNCTION_NTSTATUS();

ExAllocatePoolZero = [](POOL_TYPE, SIZE_T s, ULONG) -> PVOID { return GAlloc(s); };
ExFreePoolWithTag = [](PVOID p, ULONG) -> VOID { GFree(p); };
Expand Down
Loading
Loading