[+] File System devices API

[+] AuFS::EFSDeviceType
[+] AuFS::EFSBusType
[+] AuFS::LogicalUsedResponse
[+] AuFS::LogicalOffsetResponse
[+] AuFS::FSLogicalPartition
[+] AuFS::FSDevice
[+] AuFS::GetRootFromPath
[+] AuFS::GetDeviceFromPath
[+] AuFS::GetDeviceFromRoot
[+] AuFS::GetLogicalMountFromPath
[+] AuFS::TrySimplifyDevicePath
[+] AuFS::GetPerformanceBufferSizeFromPath
[+] AuFS::GetPhysicalSectorSizeFromPath
[+] AuFS::GetLogicalSectorSizeFromPath
[+] AuFS::GetLogicalUsedFromPath
[+] AuFS::GetLogicalUsedFromLogicalDevice
[+] AuFS::GetDeviceSizeInBytes
[+] AuFS::GetDeviceModel
[+] AuFS::GetFSDeviceByFilePath
[+] AuFS::GetFSDeviceByDevice
[+] AuFS::GetFSDevices
[+] AuFS::GetFSDevicesCachedUnsafe
[+] AuFS::ResetDeviceCache
[+] FSPlatformDevices.cpp
[+] FSPlatformDevices.NT.cpp
(holding back Linux)
This commit is contained in:
Reece Wilson 2023-12-05 18:44:38 +00:00
parent b65d0032dd
commit b35b290afd
7 changed files with 1429 additions and 0 deletions

View File

@ -0,0 +1,99 @@
/***
Copyright (C) 2023 Jamie Reece Wilson (a/k/a "Reece"). All rights reserved.
File: Devices.hpp
Date: 2023-08-11
Date: 2023-12-05
Author: Reece
***/
#pragma once
namespace Aurora::IO::FS
{
AUE_DEFINE(EFSDeviceType, (
eDeviceDisk,
eDeviceSCSI,
eDeviceCD,
eDeviceUSBMass,
eDeviceFloppy,
eDeviceNetworkMount,
eDeviceRamDisk,
eDeviceROMWindow,
eDeviceUnknown
))
AUE_DEFINE(EFSBusType, (
eBusGeneric,
eBusSCSI,
eBusSATA,
eBusUSB,
eBusNetwork
))
struct LogicalUsedResponse
{
AuUInt64 uLogicalSize {};
AuUInt64 uLogicalUsed {};
};
struct LogicalOffsetResponse
{
AuUInt64 uLogicalSize {};
AuUInt64 uLogicalOffset {};
};
struct FSLogicalPartition
{
AuString devicePath;
AuString logicalMount;
AuList<AuString> filesystemMountPoints;
AuOptional<AuString> name;
LogicalUsedResponse space;
LogicalOffsetResponse offset;
bool bIsReadOnly {};
uuids::uuid uuid;
// ... ?
};
struct FSDevice
{
EFSDeviceType type;
EFSBusType bus;
AuString devicePath;
AuString productModel;
AuOptional<AuString> altLabel;
AuOptional<AuString> altProductDescription;
AuList<FSLogicalPartition> partitions;
AuUInt64 uFSDeviceSizeInBytes {};
AuUInt64 uFSDevicePageSizeInBytes {};
uuids::uuid uuid;
};
AUKN_SYM AuString GetRootFromPath(const AuString &fileOrDirPath);
AUKN_SYM AuResult<AuString> GetDeviceFromPath(const AuString &fileOrDirPath);
AUKN_SYM AuResult<AuString> GetDeviceFromRoot(const AuString &root);
AUKN_SYM AuResult<AuString> GetLogicalMountFromPath(const AuString &fileOrDirPath);
AUKN_SYM AuString TrySimplifyDevicePath(const AuString &deviceOrLogicalMountPath);
// max: unbuffered pipe io
AUKN_SYM AuUInt32 GetPerformanceBufferSizeFromPath(const AuString &fileOrDirPath);
// min: unbuffered pipe io
AUKN_SYM AuUInt32 GetPhysicalSectorSizeFromPath(const AuString &fileOrDirPath);
// min viable sector size with abstractions on top of the disk
AUKN_SYM AuUInt32 GetLogicalSectorSizeFromPath(const AuString &fileOrDirPath);
AUKN_SYM LogicalUsedResponse GetLogicalUsedFromPath(const AuString &fileOrDirPath);
AUKN_SYM LogicalUsedResponse GetLogicalUsedFromLogicalDevice(const AuString &logicalMountPath);
AUKN_SYM AuUInt64 GetDeviceSizeInBytes(const AuString& physicalDevicePath);
AUKN_SYM AuResult<AuString> GetDeviceModel(const AuString& physicalDevicePath);
AUKN_SYM AuResult<FSDevice> GetFSDeviceByFilePath(const AuString &fileOrDirPath);
AUKN_SYM AuResult<FSDevice> GetFSDeviceByDevice(const AuString &physicalDevicePath);
AUKN_SYM AuList<FSDevice> GetFSDevices();
AUKN_SYM const AuList<FSDevice> &GetFSDevicesCachedUnsafe();
AUKN_SYM void ResetDeviceCache();
}

View File

@ -106,6 +106,8 @@ namespace Aurora
ADD_LOAD_LIB(IPHelper); ADD_LOAD_LIB(IPHelper);
ADD_LOAD_LIB(COM); ADD_LOAD_LIB(COM);
ADD_LOAD_LIB(User32); ADD_LOAD_LIB(User32);
ADD_LOAD_LIB(SetupAPI);
ADD_LOAD_LIB(Router);
#define ADD_GET_PROC(name, proc) \ #define ADD_GET_PROC(name, proc) \
if (!IsBlocked(#proc)) \ if (!IsBlocked(#proc)) \
@ -177,6 +179,8 @@ namespace Aurora
ADD_GET_PROC(Nt, NtQueryInformationProcess) ADD_GET_PROC(Nt, NtQueryInformationProcess)
ADD_GET_PROC(Nt, NtNotifyChangeDirectoryFile) ADD_GET_PROC(Nt, NtNotifyChangeDirectoryFile)
ADD_GET_PROC(Nt, NtTerminateProcess) ADD_GET_PROC(Nt, NtTerminateProcess)
ADD_GET_PROC(Nt, NtQuerySymbolicLinkObject)
ADD_GET_PROC(Nt, NtOpenSymbolicLinkObject)
ADD_GET_PROC_BI(Kernel32, KernelBase, VirtualAlloc2) ADD_GET_PROC_BI(Kernel32, KernelBase, VirtualAlloc2)
ADD_GET_PROC_BI(Kernel32, KernelBase, MapViewOfFile3) ADD_GET_PROC_BI(Kernel32, KernelBase, MapViewOfFile3)
@ -280,6 +284,18 @@ namespace Aurora
ADD_GET_PROC(User32, SetPropW); ADD_GET_PROC(User32, SetPropW);
ADD_GET_PROC(User32, OpenClipboard); ADD_GET_PROC(User32, OpenClipboard);
ADD_GET_PROC(SetupAPI, SetupDiEnumDeviceInterfaces);
ADD_GET_PROC(SetupAPI, SetupDiDestroyDeviceInfoList);
ADD_GET_PROC(SetupAPI, SetupDiGetClassDevsW);
ADD_GET_PROC(SetupAPI, SetupDiGetDeviceRegistryPropertyA);
ADD_GET_PROC(SetupAPI, SetupDiGetDeviceInterfaceDetailW);
ADD_GET_PROC(Router, WNetCloseEnum);
ADD_GET_PROC(Router, WNetEnumResourceW);
ADD_GET_PROC(Router, WNetOpenEnumW);
ADD_GET_PROC(Router, WNetGetUniversalNameW);
if (pNtCreateKeyedEvent && if (pNtCreateKeyedEvent &&
Threading::Primitives::gKeyedEventHandle == INVALID_HANDLE_VALUE) Threading::Primitives::gKeyedEventHandle == INVALID_HANDLE_VALUE)
{ {

View File

@ -19,6 +19,10 @@ struct _IP_ADAPTER_INFO;
struct _CREATEFILE2_EXTENDED_PARAMETERS; struct _CREATEFILE2_EXTENDED_PARAMETERS;
struct _EXPLICIT_ACCESS_A; struct _EXPLICIT_ACCESS_A;
struct _ACL; struct _ACL;
struct _SP_DEVINFO_DATA;
struct _SP_DEVICE_INTERFACE_DATA;
struct _SP_DEVICE_INTERFACE_DETAIL_DATA_W;
struct _NETRESOURCEW;
enum _SE_OBJECT_TYPE; enum _SE_OBJECT_TYPE;
enum _MINIDUMP_TYPE; enum _MINIDUMP_TYPE;
@ -56,6 +60,8 @@ namespace Aurora
static const wchar_t *kIPHelperDllName { L"IPHLPAPI.dll" }; static const wchar_t *kIPHelperDllName { L"IPHLPAPI.dll" };
static const wchar_t *kCOMDllName { L"ole32.dll" }; static const wchar_t *kCOMDllName { L"ole32.dll" };
static const wchar_t *kUser32DllName { L"User32.dll" }; static const wchar_t *kUser32DllName { L"User32.dll" };
static const wchar_t *kSetupAPIDllName { L"SETUPAPI.dll" };
static const wchar_t *kRouterDllName { L"MPR.dll" };
struct WIN32_MEMORY_RANGE_ENTRY2 struct WIN32_MEMORY_RANGE_ENTRY2
{ {
@ -87,6 +93,18 @@ namespace Aurora
PVOID Address PVOID Address
); );
inline NTSTATUS(__stdcall *pNtQuerySymbolicLinkObject)(
HANDLE LinkHandle,
PUNICODE_STRING LinkTarget,
PULONG ReturnedLength
);
inline NTSTATUS(__stdcall *pNtOpenSymbolicLinkObject)(
PHANDLE LinkHandle,
ACCESS_MASK DesiredAccess,
POBJECT_ATTRIBUTES ObjectAttributes
);
inline DWORD(__stdcall *pNtDelayExecution)( inline DWORD(__stdcall *pNtDelayExecution)(
BOOLEAN Alertable, BOOLEAN Alertable,
PLARGE_INTEGER DelayInterval PLARGE_INTEGER DelayInterval
@ -750,6 +768,73 @@ namespace Aurora
HANDLE hData HANDLE hData
); );
// SETUPAPI.dll
inline BOOL(__stdcall *pSetupDiEnumDeviceInterfaces)(
PVOID DeviceInfoSet,
_SP_DEVINFO_DATA * DeviceInfoData,
const GUID * InterfaceClassGuid,
DWORD MemberIndex,
_SP_DEVICE_INTERFACE_DATA * DeviceInterfaceData
);
inline BOOL(__stdcall *pSetupDiDestroyDeviceInfoList)(
PVOID DeviceInfoSet
);
inline PVOID(__stdcall *pSetupDiGetClassDevsW)(
const GUID * ClassGuid,
PCWSTR Enumerator,
HWND hwndParent,
DWORD Flags
);
inline BOOL(__stdcall *pSetupDiGetDeviceRegistryPropertyA)(
PVOID DeviceInfoSet,
_SP_DEVINFO_DATA * DeviceInfoData,
DWORD Property,
PDWORD PropertyRegDataType,
PBYTE PropertyBuffer,
DWORD PropertyBufferSize,
PDWORD RequiredSize
);
inline BOOL(__stdcall *pSetupDiGetDeviceInterfaceDetailW)(
PVOID DeviceInfoSet,
_SP_DEVICE_INTERFACE_DATA * DeviceInterfaceData,
_SP_DEVICE_INTERFACE_DETAIL_DATA_W * DeviceInterfaceDetailData,
DWORD DeviceInterfaceDetailDataSize,
PDWORD RequiredSize,
_SP_DEVINFO_DATA * DeviceInfoData
);
// MPR.dll
inline DWORD(__stdcall *pWNetCloseEnum)(
HANDLE hEnum
);
inline DWORD(__stdcall *pWNetEnumResourceW)(
HANDLE hEnum,
LPDWORD lpcCount,
LPVOID lpBuffer,
LPDWORD lpBufferSize
);
inline DWORD(__stdcall *pWNetOpenEnumW)(
DWORD dwScope,
DWORD dwType,
DWORD dwUsage,
_NETRESOURCEW * lpNetResource,
LPHANDLE lphEnum
);
inline DWORD(__stdcall *pWNetGetUniversalNameW)(
LPCWSTR lpLocalPath,
DWORD dwInfoLevel,
LPVOID lpBuffer,
LPDWORD lpBufferSize
);
inline bool gUseNativeWaitMutex {}; inline bool gUseNativeWaitMutex {};
inline bool gUseNativeWaitCondvar {}; inline bool gUseNativeWaitCondvar {};
inline bool gUseNativeWaitSemapahore {}; inline bool gUseNativeWaitSemapahore {};

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,14 @@
/***
Copyright (C) 2023 Jamie Reece Wilson (a/k/a "Reece"). All rights reserved.
File: FSPlatformDevices.NT.hpp
Date: 2023-08-11
Date: 2023-12-05
Author: Reece
***/
#pragma once
namespace Aurora::IO::FS
{
}

View File

@ -0,0 +1,125 @@
/***
Copyright (C) 2023 Jamie Reece Wilson (a/k/a "Reece"). All rights reserved.
File: FSPlatformDevices.cpp
Date: 2023-08-11
Date: 2023-12-05
Author: Reece
***/
#include <Source/RuntimeInternal.hpp>
#include "FS.hpp"
#include "FSPlatformDevices.hpp"
namespace Aurora::IO::FS
{
void InitPlatformFSCacheAtLoad()
{
static AuInitOnce gInitOnce;
gInitOnce.Call([]()
{
ResetDeviceCache();
});
}
AUKN_SYM AuResult<AuString> GetDeviceModel(const AuString &physicalDevicePath)
{
InitPlatformFSCacheAtLoad();
AU_LOCK_GUARD(gFSDirMutex);
for (const auto &refFSDevice : gCachedDevices)
{
if (refFSDevice.devicePath == physicalDevicePath)
{
auto copy = refFSDevice.productModel;
return AuMove(copy);
}
}
return {};
}
AUKN_SYM AuResult<FSDevice> GetFSDeviceByFilePath(const AuString &path)
{
AuList<AuPair<AuUInt, const FSDevice *>> devs;
InitPlatformFSCacheAtLoad();
auto normalized = AuFS::NormalizePathRet(path);
if (normalized.empty())
{
return {};
}
{
AU_LOCK_GUARD(gFSDirMutex);
for (const auto &refFSDevice : gCachedDevices)
{
for (const auto &refPart : refFSDevice.partitions) // todo sort
{
for (const auto &refMnt : refPart.filesystemMountPoints) // todo sort
{
if (AuStartsWith(path, refMnt))
{
devs.push_back(AuMakePair(refMnt.size(), &refFSDevice));
}
}
}
}
}
if (devs.empty())
{
return {};
}
std::sort(devs.begin(),
devs.end(),
[](AuPair<AuUInt, const FSDevice *> a, AuPair<AuUInt, const FSDevice *> b)
{
return AuGet<0>(a) > AuGet<0>(b);
});
auto copy = AuGet<1>(devs[0]);
return AuMove(copy);
}
AUKN_SYM AuList<FSDevice> GetFSDevices()
{
InitPlatformFSCacheAtLoad();
AU_LOCK_GUARD(gFSDirMutex);
return gCachedDevices;
}
AUKN_SYM AuResult<FSDevice> GetFSDeviceByDevice(const AuString &physicalDevicePath)
{
InitPlatformFSCacheAtLoad();
AU_LOCK_GUARD(gFSDirMutex);
for (const auto &refFSDevice : gCachedDevices)
{
if (refFSDevice.devicePath == physicalDevicePath)
{
auto copy = refFSDevice;
return AuMove(copy);
}
}
return {};
}
AUKN_SYM const AuList<FSDevice> &GetFSDevicesCachedUnsafe()
{
InitPlatformFSCacheAtLoad();
return gCachedDevices;
}
AuList<FSDevice> SysGetFSDevices();
AUKN_SYM void ResetDeviceCache()
{
AU_LOCK_GUARD(gFSDirMutex);
gCachedDevices = AuMove(SysGetFSDevices());
}
}

View File

@ -0,0 +1,17 @@
/***
Copyright (C) 2023 Jamie Reece Wilson (a/k/a "Reece"). All rights reserved.
File: FSPlatformDevices.hpp
Date: 2023-08-11
Date: 2023-12-05
Author: Reece
***/
#pragma once
#include <Aurora/IO/FS/Devices.hpp>
namespace Aurora::IO::FS
{
inline AuList<FSDevice> gCachedDevices;
inline AuThreadPrimitives::CriticalSection gFSDirMutex;
}